From: Ben Gras Date: Mon, 21 Sep 2009 14:49:04 +0000 (+0000) Subject: support for vm priv system. X-Git-Tag: v3.1.5~119 X-Git-Url: http://zhaoyanbai.com/repos/?a=commitdiff_plain;h=e40292757674c55206ab6cb0307422160eaa5843;p=minix.git support for vm priv system. fix NULL envp ptr. --- diff --git a/servers/rs/Makefile b/servers/rs/Makefile index 29185ecb2..8963584c2 100644 --- a/servers/rs/Makefile +++ b/servers/rs/Makefile @@ -27,7 +27,7 @@ $(UTIL): $(UTIL_OBJ) $(CC) -o $@ $(LDFLAGS) $(UTIL_OBJ) $(UTIL_LIBS) $(SERVER): $(OBJ) $(CC) -o $@ $(LDFLAGS) $(OBJ) $(LIBS) - install -S 200k $@ + install -S 32k $@ # install with other servers install: /bin/$(UTIL) /usr/sbin/$(SERVER) diff --git a/servers/rs/manager.c b/servers/rs/manager.c index 884f36480..b08caeb55 100644 --- a/servers/rs/manager.c +++ b/servers/rs/manager.c @@ -10,6 +10,7 @@ #include #include #include +#include #include #include #include @@ -398,7 +399,17 @@ message *m_ptr; /* request message pointer */ rp->r_set_resources= 1; /* new style, enforece * I/O resources */ - + if (sizeof(rp->r_vm) == sizeof(rs_start.rss_vm) && + sizeof(rp->r_vm[0]) == sizeof(rs_start.rss_vm[0])) + { + memcpy(rp->r_vm, rs_start.rss_vm, sizeof(rp->r_vm)); + } + else + { + printf("RS: do_start: internal inconsistency: bad size of r_vm\n"); + memset(rp->r_vm, '\0', sizeof(rp->r_vm)); + } + /* All information was gathered. Now try to start the system service. */ r = start_service(rp, 0, &ep); m_ptr->RS_ENDPOINT = ep; @@ -639,7 +650,8 @@ PUBLIC void do_exit(message *m_ptr) run_script(rp); else { start_service(rp, 0, &ep); /* direct restart */ - m_ptr->RS_ENDPOINT = ep; + if(m_ptr) + m_ptr->RS_ENDPOINT = ep; } } else if (rp->r_flags & RS_EXECFAILED) { @@ -679,7 +691,8 @@ rp->r_restarts= 0; else { printf("RS: restarting %s\n", rp->r_cmd); start_service(rp, 0, &ep); /* direct restart */ - m_ptr->RS_ENDPOINT = ep; + if(m_ptr) + m_ptr->RS_ENDPOINT = ep; /* Do this even if no I/O happens with the ioctl, in * order to disambiguate requests with DEV_IOCTL_S. */ @@ -783,7 +796,9 @@ endpoint_t *endpoint; char *file_only; int s, use_copy, slot_nr; struct priv *privp; + bitchunk_t *vm_mask; message m; + char * null_env = NULL; use_copy= (rp->r_exec != NULL); @@ -813,9 +828,9 @@ endpoint_t *endpoint; cpf_reload(); /* Tell kernel about grant table */ if (!use_copy) { - execve(rp->r_argv[0], rp->r_argv, NULL); /* POSIX execute */ + execve(rp->r_argv[0], rp->r_argv, &null_env); /* POSIX execute */ file_only = strrchr(rp->r_argv[0], '/') + 1; - execve(file_only, rp->r_argv, NULL); /* POSIX execute */ + execve(file_only, rp->r_argv, &null_env); /* POSIX execute */ } printf("RS: exec failed for %s: %d\n", rp->r_argv[0], errno); slot_nr= rp-rproc; @@ -843,6 +858,7 @@ endpoint_t *endpoint; } privp= NULL; + vm_mask = NULL; if (rp->r_set_resources) { init_privs(rp, &rp->r_priv); @@ -850,6 +866,8 @@ endpoint_t *endpoint; /* Inform the PCI server about the driver */ init_pci(rp, child_proc_nr_e); + + vm_mask = &rp->r_vm[0]; } /* Set the privilege structure for the child process to let is run. @@ -863,6 +881,14 @@ endpoint_t *endpoint; return(s); /* return error */ } + if ((s = vm_set_priv(child_proc_nr_e, vm_mask)) < 0) { + report("RS", "vm_set_priv call failed", s); + rp->r_flags |= RS_EXITING; + if (child_pid > 0) kill(child_pid, SIGKILL); + else report("RS", "didn't kill pid", child_pid); + return (s); + } + s= ds_publish_u32(rp->r_label, child_proc_nr_e); if (s != OK) printf("RS: start_service: ds_publish_u32 failed: %d\n", s); @@ -1034,6 +1060,7 @@ struct rproc *rp; pid_t pid; char *reason; char incarnation_str[20]; /* Enough for a counter? */ + char *envp[1] = { NULL }; if (rp->r_flags & RS_EXITING) reason= "exit"; @@ -1071,7 +1098,7 @@ struct rproc *rp; break; case 0: execle(rp->r_script, rp->r_script, rp->r_label, reason, - incarnation_str, NULL, NULL); + incarnation_str, NULL, envp); printf("RS: run_script: execl '%s' failed: %s\n", rp->r_script, strerror(errno)); exit(1); diff --git a/servers/rs/manager.h b/servers/rs/manager.h index 817f6d4e5..4a8f407ba 100644 --- a/servers/rs/manager.h +++ b/servers/rs/manager.h @@ -18,6 +18,7 @@ #define MAX_IPC_LIST 256 /* Max size of list for IPC target * process names */ +#define MAX_VM_LIST 256 /* Definition of the system process table. This table only has entries for * the servers and drivers, and thus is not directly indexed by slot number. @@ -61,6 +62,8 @@ extern struct rproc { u32_t r_call_mask[MAX_NR_SYSTEM]; char r_ipc_list[MAX_IPC_LIST]; +#define R_VM_CALL_SIZE BITMAP_CHUNKS(VM_NCALLS) + bitchunk_t r_vm[R_VM_CALL_SIZE]; } rproc[NR_SYS_PROCS]; /* Mapping for fast access to the system process table. */ diff --git a/servers/rs/service.c b/servers/rs/service.c index 3e0251d41..ee3729f77 100644 --- a/servers/rs/service.c +++ b/servers/rs/service.c @@ -13,6 +13,7 @@ #include #include #include +#include #include #include #include @@ -21,6 +22,7 @@ #include #include #include +#include #include #include #include @@ -332,6 +334,7 @@ PRIVATE void fatal(char *fmt, ...) #define KW_CLASS "class" #define KW_SYSTEM "system" #define KW_IPC "ipc" +#define KW_VM "vm" FORWARD void do_driver(config_t *cpe, config_t *config); @@ -700,6 +703,7 @@ struct { "VMCTL", SYS_VMCTL }, { "PROFBUF", SYS_PROFBUF }, { "SYSCTL", SYS_SYSCTL }, + { "INT86", SYS_INT86 }, { NULL, 0 } }; @@ -752,6 +756,48 @@ PRIVATE void do_ipc(config_t *cpe) req_ipc= list; } +struct +{ + char *label; + int call_nr; +} vm_table[] = +{ + { "REMAP", VM_REMAP }, + { "UNREMAP", VM_SHM_UNMAP }, + { "GETPHYS", VM_GETPHYS }, + { "GETREFCNT", VM_GETREF }, + { "QUERYEXIT", VM_QUERY_EXIT }, + { "CTL", VM_CTL }, + { NULL, 0 }, +}; + +PRIVATE void do_vm(config_t *cpe) +{ + int i; + + for (; cpe; cpe = cpe->next) + { + if (cpe->flags & CFG_SUBLIST) + { + fatal("do_vm: unexpected sublist at %s:%d", + cpe->file, cpe->line); + } + if (cpe->flags & CFG_STRING) + { + fatal("do_vm: unexpected string at %s:%d", + cpe->file, cpe->line); + } + + for (i = 0; vm_table[i].label != NULL; i++) + if (!strcmp(cpe->word, vm_table[i].label)) + break; + if (vm_table[i].label == NULL) + fatal("do_vm: unknown call '%s' at %s:%d", + cpe->word, cpe->file, cpe->line); + SET_BIT(rs_start.rss_vm, vm_table[i].call_nr - VM_RQ_BASE); + } +} + PRIVATE void do_system(config_t *cpe) { int i, call_nr, word, bits_per_word; @@ -883,6 +929,11 @@ PRIVATE void do_driver(config_t *cpe, config_t *config) do_ipc(cpe->next); continue; } + if (strcmp(cpe->word, KW_VM) == 0) + { + do_vm(cpe->next); + continue; + } } }