/* _ml_P_Process_waitpid : int * word -> int * int * int * * Wait for child processes to stop or terminate */ ml_val_t _ml_P_Process_waitpid (ml_state_t *msp, ml_val_t arg) { int pid; int status, how, val; ml_val_t r; pid = waitpid(REC_SELINT(arg, 0), &status, REC_SELWORD(arg, 1)); if (pid < 0) return RAISE_SYSERR(msp, pid); if (WIFEXITED(status)) { how = 0; val = WEXITSTATUS(status); } else if (WIFSIGNALED(status)) { how = 1; val = WTERMSIG(status); } else if (WIFSTOPPED(status)) { how = 2; val = WSTOPSIG(status); } else return RAISE_ERROR(msp, "unknown child status"); REC_ALLOC3(msp, r, INT_CtoML(pid), INT_CtoML(how), INT_CtoML(val)); return r; } /* end of _ml_P_Process_waitpid */
Val _lib7_P_SysDB_getgrnam (Task* task, Val arg) { //====================== // // Mythryl type: String -> (String, Unt, List(String)) // // Get group file entry by name. // // This fn gets bound as getgrname' in: // // src/lib/std/src/posix-1003.1b/posix-etc.pkg struct group* info = getgrnam( HEAP_STRING_AS_C_STRING( arg )); if (info == NULL) return RAISE_SYSERR(task, -1); Val gr_name = make_ascii_string_from_c_string( task, info->gr_name ); Val gr_gid; WORD_ALLOC (task, gr_gid, (Val_Sized_Unt)(info->gr_gid)); Val gr_mem = make_ascii_strings_from_vector_of_c_strings( task, info->gr_mem ); Val result; REC_ALLOC3(task, result, gr_name, gr_gid, gr_mem); return result; }
Val make_mythryl_signal_handler_arg ( //=============================== // Task* task, Val* resume_after_handling_signal ) { // We're handling a POSIX inteprocess signal for // // src/c/main/run-mythryl-code-and-runtime-eventloop.c // // Depending on platform, resume_after_handling_signal // is from one of // src/c/machine-dependent/prim.intel32.asm // src/c/machine-dependent/prim.intel32.masm // src/c/machine-dependent/prim.sun.asm // src/c/machine-dependent/prim.pwrpc32.asm // // Our job is to build the Mythryl argument record for // the Mythryl signal handler. The handler has type // // posix_interprocess_signal_handler : (Int, Int, Fate(Void)) -> X // // where // The first argument is the signal id // For example SIGALRM, // the second argument is the signal count // I.e., number of times signal has been recieved since last handled. // the third argument is the resumption fate. // // The return type is X because the Mythryl // signal handler should never return. // // NOTE: Maybe this should be combined with choose_signal??? XXX BUGGO FIXME Pthread* pthread = task->pthread; Val resume_fate = make_resumption_fate( task, resume_after_handling_signal ); // Allocate the Mythryl signal handler's argument record: // Val arg; REC_ALLOC3( task, arg, // TAGGED_INT_FROM_C_INT( pthread->next_posix_signal_id ), TAGGED_INT_FROM_C_INT( pthread->next_posix_signal_count ), resume_fate ); #ifdef SIGNAL_DEBUG debug_say( "make_mythryl_signal_handler_arg: resumeC = %#x, arg = %#x\n", resume_fate, arg ); #endif return arg; }
Val _lib7_P_Process_waitpid (Task* task, Val arg) { //======================= // // Mythryl type: (Int, Unt) -> (Int, Int, Int) // // Wait for child processes to stop or terminate. // // This fn gets bound as waitpid' in: // // src/lib/std/src/posix-1003.1b/posix-process.pkg int status; int how; int val; int pid; /* do { */ // Backed out 2010-02-26 CrT: See discussion at bottom of src/c/lib/socket/connect.c pid = waitpid(GET_TUPLE_SLOT_AS_INT(arg, 0), &status, TUPLE_GETWORD(arg, 1)); /* } while (pid < 0 && errno == EINTR); */ // Restart if interrupted by a SIGALRM or SIGCHLD or whatever. if (pid < 0) return RAISE_SYSERR(task, pid); if (WIFEXITED(status)) { // how = 0; val = WEXITSTATUS(status); } else if (WIFSIGNALED(status)) { how = 1; val = WTERMSIG(status); } else if (WIFSTOPPED(status)) { how = 2; val = WSTOPSIG(status); } else { return RAISE_ERROR(task, "unknown child status"); } Val result; REC_ALLOC3(task, result, TAGGED_INT_FROM_C_INT(pid), TAGGED_INT_FROM_C_INT(how), TAGGED_INT_FROM_C_INT(val)); return result; }
/* _lib7_NetDB_getprotbyname : String -> (String * String list * int) option */ lib7_val_t _lib7_NetDB_getprotbyname (lib7_state_t *lib7_state, lib7_val_t arg) { lib7_val_t name, aliases, res; struct protoent *pentry; pentry = getprotobyname (STR_LIB7toC(arg)); if (pentry == NULL) return OPTION_NONE; else { name = LIB7_CString (lib7_state, pentry->p_name); aliases = LIB7_CStringList (lib7_state, pentry->p_aliases); REC_ALLOC3 (lib7_state, res, name, aliases, INT_CtoLib7(pentry->p_proto)); OPTION_SOME (lib7_state, res, res); return res; } } /* end of _lib7_NetDB_getprotbyname */
/* MakeHandlerArg: * * Build the argument record for the Lib7 signal handler. * It has the type * * sigHandler : (Int, Int, Fate(Void)) -> X * * where * The first argument is the signal code, * the second argument is the signal count and * the third argument is the resumption fate. * * The Lib7 signal handler should never return. * NOTE: maybe this should be combined with ChooseSignal??? XXX BUGGO FIXME */ lib7_val_t MakeHandlerArg (lib7_state_t *lib7_state, lib7_val_t resume[]) { lib7_val_t resumeCont, arg; vproc_state_t *vsp = lib7_state->lib7_vproc; resumeCont = MakeResumeCont(lib7_state, resume); /* Allocate the Lib7 signal handler's argument record: */ REC_ALLOC3(lib7_state, arg, INT_CtoLib7(vsp->vp_sigCode), INT_CtoLib7(vsp->vp_sigCount), resumeCont); #ifdef SIGNAL_DEBUG SayDebug ("MakeHandlerArg: resumeC = %#x, arg = %#x\n", resumeCont, arg); #endif return arg; }
Val _lib7_NetDB_getrpcbynum (Task* task, Val arg) { //======================= // // Mythryl type: Int -> Null_Or( (String, List(String), Int) ) // // This fn is NOWHERE INVOKED. Nor listed in src/c/lib/socket/cfun-list.h Presumably should be either called or deleted: XXX BUGGO FIXME. struct rpcent* rentry = getrpcbynumber( TAGGED_INT_TO_C_INT( arg )); if (rentry == NULL) return OPTION_NULL; Val name = make_ascii_string_from_c_string( task, rentry->r_name ); Val aliases = make_ascii_strings_from_vector_of_c_strings( task, rentry->r_aliases); Val result; REC_ALLOC3( task, result, name, aliases, TAGGED_INT_FROM_C_INT(rentry->r_number)); OPTION_THE( task, result, result); return result; }