*/
#include "inc.h"
+#include <ctype.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/types.h>
rp->r_uid= rs_start.rss_uid;
rp->r_nice= rs_start.rss_nice;
+ if (rs_start.rss_flags & RF_IPC_VALID)
+ {
+ if (rs_start.rss_ipclen+1 > sizeof(rp->r_ipc_list))
+ {
+ printf("rs: ipc list too long for '%s'\n", rp->r_label);
+ return EINVAL;
+ }
+ s=sys_datacopy(m_ptr->m_source, (vir_bytes) rs_start.rss_ipc,
+ SELF, (vir_bytes) rp->r_ipc_list, rs_start.rss_ipclen);
+ if (s != OK) return(s);
+ rp->r_ipc_list[rs_start.rss_ipclen]= '\0';
+ }
+ else
+ rp->r_ipc_list[0]= '\0';
+
rp->r_exec= NULL;
if (rs_start.rss_flags & RF_COPY)
{
if (rp->r_dev_nr > 0) { /* set driver map */
if ((s=mapdriver5(rp->r_label, strlen(rp->r_label),
rp->r_dev_nr, rp->r_dev_style, !!use_copy /* force */)) < 0) {
- report("RS", "couldn't map driver", errno);
+ report("RS", "couldn't map driver (continuing)", errno);
+#if 0
rp->r_flags |= RS_EXITING; /* expect exit */
if(child_pid > 0) kill(child_pid, SIGKILL); /* kill driver */
else report("RS", "didn't kill pid", child_pid);
return(s); /* return error */
+#endif
}
}
sprintf(incarnation_str, "%d", rp->r_restarts);
if(rs_verbose) {
- printf("RS: should call script '%s'\n", rp->r_script);
+ printf("RS: calling script '%s'\n", rp->r_script);
printf("RS: sevice name: '%s'\n", rp->r_label);
printf("RS: reason: '%s'\n", reason);
printf("RS: incarnation: '%s'\n", incarnation_str);
{
int i, src_bits_per_word, dst_bits_per_word, src_word, dst_word,
src_bit, call_nr, chunk, bit, priv_id, slot_nr;
+ endpoint_t proc_nr_e;
+ size_t len;
unsigned long mask;
+ char *p, *q;
struct rproc *tmp_rp;
+ char label[MAX_LABEL_LEN+1];
/* Clear s_k_call_mask */
memset(privp->s_k_call_mask, '\0', sizeof(privp->s_k_call_mask));
memset(&privp->s_ipc_to, '\0', sizeof(privp->s_ipc_to));
memset(&privp->s_ipc_sendrec, '\0', sizeof(privp->s_ipc_sendrec));
- if (strcmp(rp->r_label, "dp8390") == 0)
+ if (strlen(rp->r_ipc_list) != 0)
{
- printf("init_privs: special code for dp8390\n");
-
- /* Try to find inet */
- for (slot_nr = 0; slot_nr < NR_SYS_PROCS; slot_nr++)
- {
- tmp_rp = &rproc[slot_nr];
- if (!(tmp_rp->r_flags & RS_IN_USE))
- continue;
- if (strcmp(tmp_rp->r_label, "inet") == 0)
- break;
- }
- if (slot_nr >= NR_SYS_PROCS)
- {
- printf("init_privs: unable to find inet\n");
- return;
- }
-
- priv_id= sys_getprivid(tmp_rp->r_proc_nr_e);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for inet: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_to.chunk[chunk] |= (1 << bit);
-
- priv_id= sys_getprivid(RS_PROC_NR);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for RS: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_to.chunk[chunk] |= (1 << bit);
-
- priv_id= sys_getprivid(SYSTEM);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for SYSTEM: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
-
- priv_id= sys_getprivid(PM_PROC_NR);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for PM: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
-
- priv_id= sys_getprivid(LOG_PROC_NR);
- if (priv_id < 0)
+ for (p= rp->r_ipc_list; p[0] != '\0'; p= q)
{
- printf(
- "init_privs: unable to get priv_id for LOG: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
-
- priv_id= sys_getprivid(TTY_PROC_NR);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for TTY: %d\n",
- priv_id);
- return;
- }
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
-
- /* Try to find PCI */
- for (slot_nr = 0; slot_nr < NR_SYS_PROCS; slot_nr++)
- {
- tmp_rp = &rproc[slot_nr];
- if (!(tmp_rp->r_flags & RS_IN_USE))
- continue;
- if (strcmp(tmp_rp->r_label, "pci") == 0)
- break;
- }
- if (slot_nr >= NR_SYS_PROCS)
- {
- printf("init_privs: unable to find PCI\n");
- return;
- }
+ /* Skip leading space */
+ while (p[0] != '\0' && isspace((unsigned char)p[0]))
+ p++;
+
+ /* Find start of next word */
+ q= p;
+ while (q[0] != '\0' && !isspace((unsigned char)q[0]))
+ q++;
+ if (q == p)
+ continue;
+ len= q-p;
+ if (len+1 > sizeof(label))
+ {
+ printf(
+ "rs:init_privs: bad ipc list entry '.*s' for %s: too long\n",
+ len, p, rp->r_label);
+ continue;
+ }
+ memcpy(label, p, len);
+ label[len]= '\0';
+
+ if (strcmp(label, "SYSTEM") == 0)
+ proc_nr_e= SYSTEM;
+ else if (strcmp(label, "PM") == 0)
+ proc_nr_e= PM_PROC_NR;
+ else if (strcmp(label, "VFS") == 0)
+ proc_nr_e= FS_PROC_NR;
+ else if (strcmp(label, "RS") == 0)
+ proc_nr_e= RS_PROC_NR;
+ else if (strcmp(label, "LOG") == 0)
+ proc_nr_e= LOG_PROC_NR;
+ else if (strcmp(label, "TTY") == 0)
+ proc_nr_e= TTY_PROC_NR;
+ else if (strcmp(label, "DS") == 0)
+ proc_nr_e= DS_PROC_NR;
+ else
+ {
+ /* Try to find process */
+ for (slot_nr = 0; slot_nr < NR_SYS_PROCS;
+ slot_nr++)
+ {
+ tmp_rp = &rproc[slot_nr];
+ if (!(tmp_rp->r_flags & RS_IN_USE))
+ continue;
+ if (strcmp(tmp_rp->r_label, label) == 0)
+ break;
+ }
+ if (slot_nr >= NR_SYS_PROCS)
+ {
+ printf(
+ "init_privs: unable to find '%s'\n",
+ label);
+ continue;
+ }
+ proc_nr_e= tmp_rp->r_proc_nr_e;
+ }
- priv_id= sys_getprivid(tmp_rp->r_proc_nr_e);
- if (priv_id < 0)
- {
- printf(
- "init_privs: unable to get priv_id for PCI: %d\n",
- priv_id);
- return;
+ priv_id= sys_getprivid(proc_nr_e);
+ if (priv_id < 0)
+ {
+ printf(
+ "init_privs: unable to get priv_id for '%s': %d\n",
+ label, priv_id);
+ continue;
+ }
+ chunk= (priv_id / (sizeof(bitchunk_t)*8));
+ bit= (priv_id % (sizeof(bitchunk_t)*8));
+ privp->s_ipc_to.chunk[chunk] |= (1 << bit);
+ privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
}
- chunk= (priv_id / (sizeof(bitchunk_t)*8));
- bit= (priv_id % (sizeof(bitchunk_t)*8));
- privp->s_ipc_sendrec.chunk[chunk] |= (1 << bit);
}
else
{
PRIVATE long req_period;
PRIVATE char *req_script;
PRIVATE char *req_label;
+PRIVATE char *req_ipc;
PRIVATE char *req_config = PATH_CONFIG;
PRIVATE int req_printep;
PRIVATE int class_recurs; /* Nesting level of class statements */
int req_nr;
int c, i;
int c_flag;
+ int i_flag=0;
c_flag= 0;
- while (c= getopt(argc, argv, "c?"), c != -1)
+ while (c= getopt(argc, argv, "ci?"), c != -1)
{
switch(c)
{
case 'c':
c_flag= 1;
break;
+ case 'i':
+ i_flag= 1;
+ break;
default:
fprintf(stderr, "%s: getopt failed: %c\n",
argv[ARG_NAME], c);
rs_start.rss_flags= 0;
if (c_flag)
rs_start.rss_flags |= RF_COPY;
+ if (i_flag)
+ rs_start.rss_flags |= RF_IPC_VALID;
if (do_run)
{
#define KW_DEVICE "device"
#define KW_CLASS "class"
#define KW_SYSTEM "system"
+#define KW_IPC "ipc"
FORWARD void do_driver(config_t *cpe, config_t *config);
{ "SETGRANT", SYS_SETGRANT },
{ "READBIOS", SYS_READBIOS },
{ "VM_MAP", SYS_VM_MAP },
+ { "MAPDMAx", SYS_MAPDMAx },
{ NULL, 0 }
};
+PRIVATE void do_ipc(config_t *cpe)
+{
+ char *list;
+ size_t listsize, wordlen;
+
+ list= NULL;
+ listsize= 1;
+ list= malloc(listsize);
+ if (list == NULL)
+ fatal("do_ipc: unable to malloc %d bytes", listsize);
+ list[0]= '\0';
+
+ /* Process a list of process names that are allowed to be
+ * contacted
+ */
+ for (; cpe; cpe= cpe->next)
+ {
+ if (cpe->flags & CFG_SUBLIST)
+ {
+ fatal("do_ipc: unexpected sublist at %s:%d",
+ cpe->file, cpe->line);
+ }
+ if (cpe->flags & CFG_STRING)
+ {
+ fatal("do_ipc: unexpected string at %s:%d",
+ cpe->file, cpe->line);
+ }
+
+ wordlen= strlen(cpe->word);
+
+ listsize += 1 + wordlen;
+ list= realloc(list, listsize);
+ if (list == NULL)
+ {
+ fatal("do_ipc: unable to realloc %d bytes",
+ listsize);
+ }
+ strcat(list, " ");
+ strcat(list, cpe->word);
+ }
+ printf("do_ipc: got list '%s'\n", list);
+
+ if (req_ipc)
+ fatal("do_ipc: req_ipc is set");
+ req_ipc= list;
+}
+
PRIVATE void do_system(config_t *cpe)
{
int i, call_nr, word, bits_per_word;
do_system(cpe->next);
continue;
}
+ if (strcmp(cpe->word, KW_IPC) == 0)
+ {
+ do_ipc(cpe->next);
+ continue;
+ }
}
}
do_config(progname, req_config);
}
+ if (req_ipc)
+ {
+ rs_start.rss_ipc= req_ipc+1; /* Skip initial space */
+ rs_start.rss_ipclen= strlen(rs_start.rss_ipc);
+ }
+ else
+ {
+ rs_start.rss_ipc= NULL;
+ rs_start.rss_ipclen= 0;
+ }
+
m.RS_CMD_ADDR = (char *) &rs_start;
/* Build request message and send the request. */