Committed on the Free edition of March Hare Software CVSNT Server. Upgrade to CVS Suite for more features and support: http://march-hare.com/cvsnt/ git-svn-id: http://moon:8086/svn/vhdl/trunk@786 cc03376c-175c-47c8-b038-4cd826a8556b
87 lines
1.2 KiB
C
87 lines
1.2 KiB
C
#include <stdio.h>
|
|
#include "libsys.h"
|
|
#include "xcpt.h"
|
|
|
|
/* 10 digits + 1 sign + 1 trailing nul */
|
|
static char itoa_buf[12];
|
|
|
|
char *itoa(int i)
|
|
{
|
|
char *pos = itoa_buf + sizeof(itoa_buf) - 1;
|
|
unsigned int u;
|
|
int negative = 0;
|
|
|
|
if (i < 0)
|
|
{
|
|
negative = 1;
|
|
u = ((unsigned int)(-(1+i))) + 1;
|
|
}
|
|
else
|
|
{
|
|
u = i;
|
|
}
|
|
|
|
*pos = 0;
|
|
|
|
do
|
|
{
|
|
*--pos = '0' + (u % 10);
|
|
u /= 10;
|
|
} while (u);
|
|
|
|
if (negative)
|
|
{
|
|
*--pos = '-';
|
|
}
|
|
|
|
return pos;
|
|
}
|
|
|
|
int syscalls_handler(struct xcptcontext * xcp)
|
|
{
|
|
int syscall_code;
|
|
char *pStr, buf[33];
|
|
|
|
syscall_code = xcp->regs[2];
|
|
|
|
switch(syscall_code)
|
|
{
|
|
case 1: // print integer
|
|
sputs(itoa(xcp->regs[4]));
|
|
break;
|
|
|
|
case 4: // print string
|
|
pStr = (char*)xcp->regs[4];
|
|
sputs(pStr);
|
|
break;
|
|
|
|
case 5: // read integer
|
|
pStr = fgets(buf, sizeof(buf), stdin);
|
|
xcp->regs[2] = atoi(pStr);
|
|
break;
|
|
|
|
case 8: // read string
|
|
pStr = (char*)xcp->regs[4];
|
|
fgets(pStr, xcp->regs[5], stdin);
|
|
break;
|
|
|
|
case 10: // exit
|
|
_exit(0);
|
|
break;
|
|
|
|
default:
|
|
sputs("\nUnknown syscall (");print_word(syscall_code);sputs(") at ");print_word(xcp->epc);sputs("\n");
|
|
break;
|
|
}
|
|
|
|
xcp->epc += 4; // set return address to instruction after syscall
|
|
|
|
return 0;
|
|
}
|
|
|
|
void syscalls_init(void)
|
|
{
|
|
xcpt_register(Syscall, syscalls_handler);
|
|
}
|
|
|