void forkentry(void *tf, unsigned long child_addrs ) { (void)child_addrs; int *temp; struct trapframe my_tf; int s = splhigh(); if((curthread->errflag)==1){ splx(s); sysexit(temp,tf); }else{ //DEBUG(1,"forkentry %d\n",curthread->ppid); memcpy(&my_tf, tf, sizeof(struct trapframe)); my_tf.tf_a3 = 0; my_tf.tf_epc +=4; my_tf.tf_v0 = 0; splx(s); kfree(tf); mips_usermode(&my_tf); } }
int main(int argc, char *argv[]) { int i; if (argc<2) printf("\n"); for(i=1; i<argc; ++i) printf("%s%s", argv[i], i+1 < argc ? " " : "\n"); sysexit(); }
void check_file_removed(const char *name, int fatal) { unlink(name); #if 0 if (access(name, 0) == 0) { if (fatal) cout << "FAIL: "; cout << "File \"" << name << "\" still exists after run\n"; if (fatal) sysexit(1); } #endif }
/* Entrée pour les appels système SYSENTER */ __attribute__ ((noreturn)) void sysenter_handler(regs *dump) { sti(); switch (dump->eax) { /* FOR INSERTING */ default: printf("Appel syscall vers fonction inexistante en %Y:%Y", dump->cs, dump->eip); break; } //dump->eflags &= ~(1 << 6); dump->eflags |= (1 << 6); setESP(dump); restcpu_user(); sysexit(); }
void syscallc(int user_eax, int arg1, char * arg2, int arg3) { switch (user_eax) { case SYSREAD_NUM: user_eax = sysread(arg1, arg2, arg3); break; case SYSWRITE_NUM: user_eax = syswrite(arg1, arg2, arg3); break; case SYSEXIT_NUM: user_eax = sysexit(arg1); break; default: printf("invalid syscall I.D.: %d\n", user_eax); break; } }
//Child when created will excute this function void md_forkentry(struct trapframe *tf) { //kprintf("Kernel level fork\n"); int s = splhigh(); int *temp; if((curthread->errflag)==1){ splx(s); sysexit(temp,tf); }else{ tf->tf_a3 = 0; tf->tf_epc +=4; tf->tf_v0 = 0; pid_array[(int)(curthread->ppid)] = curthread; splx(s); } /* * This function is provided as a reminder. You need to write * both it and the code that calls it. * * Thus, you can trash it and do things another way if you prefer. */ }
void abort(void) { fprintf(stderr, "Abort.\n"); sysexit(); }
static void syscall_handler (struct intr_frame* frame) { // -------- System Call Handler Overview -------- // Get system call number // switch statement using system call number // collect arguments for system call function if necessary // call system call function // set frame->eax to return value if necessary // ---------------------------------------------- uintptr_t* kpaddr_sp = (uintptr_t*) frame->esp; int syscall_num = -1; if(check_uptr(kpaddr_sp)) syscall_num = next_value(&kpaddr_sp); else sysexit(-1); switch(syscall_num) { case SYS_HALT: { // Terminates Pintos shutdown_power_off(); } break; case SYS_EXIT: { uintptr_t status = -1; if(check_uptr(kpaddr_sp)) status = next_value(&kpaddr_sp); sysexit(status); } break; case SYS_EXEC: //pid_t exec (const char *file); { const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); else sysexec(frame, file); } break; case SYS_WAIT: //int wait (pid_t); { uintptr_t childid = -1; if(check_uptr(kpaddr_sp)) childid = next_value(&kpaddr_sp); else sysexit(childid); int retval = process_wait((tid_t) childid); frame->eax = retval; } break; case SYS_CREATE: //bool create (const char *file, unsigned initial_size); { const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); uintptr_t size = 0; if(check_uptr(kpaddr_sp)) size = next_value(&kpaddr_sp); else sysexit(-1); syscreate(frame, file, size); } break; case SYS_REMOVE: //bool remove (const char *file); { const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); sysremove(frame, file); } break; case SYS_OPEN: { //int open (const char *file); const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); sysopen(frame, file); } break; case SYS_FILESIZE: { //int filesize (int fd); int fd = 0; if (check_uptr(kpaddr_sp)) fd = (int) next_value(&kpaddr_sp); else sysexit(-1); sysfilesize(frame, fd); } break; case SYS_READ: { //int read (int fd, void *buffer, unsigned length); int fd = 0; if (check_uptr(kpaddr_sp)) fd = (int) next_value(&kpaddr_sp); else sysexit(-1); const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); unsigned length = 0; if (check_uptr(kpaddr_sp)) length = (unsigned) next_value(&kpaddr_sp); else sysexit(-1); sysread(frame, fd, (void*) file, length); } break; case SYS_WRITE: { //int write (int fd, const void *buffer, unsigned length); uintptr_t fd = 0; if(check_uptr(kpaddr_sp)) fd = next_value(&kpaddr_sp); else sysexit(-1); const char* file = next_charptr(&kpaddr_sp); if(file == NULL) sysexit(-1); unsigned len = strlen(file); if(!check_buffer(file, len)) sysexit(-1); uintptr_t length = 0; if(check_uptr(kpaddr_sp)) length = next_value(&kpaddr_sp); else sysexit(-1); if(fd == CONSOLEWRITE) // Write to Console { while(length > 0) { if(length > MAX_SIZE) { putbuf (file, MAX_SIZE); file += MAX_SIZE; length -= MAX_SIZE; } else { putbuf (file, length); length = 0; } } } else { syswrite(frame, fd, file, length); } } break; case SYS_SEEK: { //void seek (int fd, unsigned position); int fd = 0; if (check_uptr(kpaddr_sp)) fd = (int) next_value(&kpaddr_sp); else sysexit(-1); unsigned position = 0; if (check_uptr(kpaddr_sp)) position = (unsigned) next_value(&kpaddr_sp); else sysexit(-1); sysseek(fd, position); } break; case SYS_TELL: { //unsigned tell (int fd); int fd = 0; if (check_uptr(kpaddr_sp)) fd = (int) next_value(&kpaddr_sp); else sysexit(-1); systell(frame, fd); } break; case SYS_CLOSE: { //void close (int fd); int fd = 0; if (check_uptr(kpaddr_sp)) fd = (int) next_value(&kpaddr_sp); else sysexit(-1); sysclose(fd); } break; default: { printf("Unrecognized System Call\n"); sysexit(-1); } break; } }
void mips_syscall(struct trapframe *tf) { int callno; int32_t retval; int err; int s,act; char *d; //convert user level pointers to user level pointers assert(curspl==0); callno = tf->tf_v0; /* * Initialize retval to 0. Many of the system calls don't * really return a value, just 0 for success and -1 on * error. Since retval is the value returned on success, * initialize it to 0 by default; thus it's not necessary to * deal with it except for calls that return other values, * like write. */ retval = 0; switch (callno) { case SYS_reboot: err = sys_reboot(tf->tf_a0); break; // syscall.h has all the callno numbers for differnt syscalls case SYS_fork: err = sysfork(&retval,tf); break; case SYS_getpid : err = sysgetpid(&retval); break; case SYS_write : s=splhigh(); char *c = (char *)tf->tf_a1; kprintf("%c",*c); retval = 1; splx(s); err=0; break; case SYS_read : d = (char *)kmalloc(sizeof(char)*((tf->tf_a2)+1)); //char *b; //b = (char *)kmalloc(sizeof(char)*((tf->tf_a2)+1)); d[0] = getch(); d[1] ='\0'; putch(d[0]); putch('\n'); s=splhigh(); copyoutstr(d,(userptr_t)(tf->tf_a1),(tf->tf_a2)+1,&act); //DEBUG(1,"actual: %d tf size: %d\n",act,(tf->tf_a2)+1); //copyinstr((tf->tf_a1),b,(tf->tf_a2)+1,&act); //DEBUG(1,"copied bacl:%s\n",b); err=0; kfree(d); retval = strlen(d)+1; splx(s); break; case SYS_waitpid : err = syswaitpid(tf->tf_a0,(int *)tf->tf_a1,tf->tf_a2,&retval); //syswaitpid(&retval); break; case SYS__exit : err = sysexit(&retval,tf); break; case SYS_execv: err=sysexecv((char*)tf->tf_a0, (char**)tf->tf_a1); break; case SYS_sbrk: err = sys_sbrk((int)tf->tf_a0, &retval); break; default: kprintf("Unknown syscall %d\n", callno); err = ENOSYS; break; } if (err) { /* * Return the error code. This gets converted at * userlevel to a return value of -1 and the error * code in errno. */ tf->tf_v0 = err; tf->tf_a3 = 1; /* signal an error */ } else { /* Success. */ tf->tf_v0 = retval; tf->tf_a3 = 0; /* signal no error */ } /* * Now, advance the program counter, to avoid restarting * the syscall over and over again. */ tf->tf_epc += 4; /* Make sure the syscall code didn't forget to lower spl */ assert(curspl==0); }