]> Zhao Yanbai Git Server - minix.git/commitdiff
Initialization protocol for system services.
authorCristiano Giuffrida <cristiano@minix3.org>
Fri, 8 Jan 2010 01:20:42 +0000 (01:20 +0000)
committerCristiano Giuffrida <cristiano@minix3.org>
Fri, 8 Jan 2010 01:20:42 +0000 (01:20 +0000)
SYSLIB CHANGES:
- SEF framework now supports a new SEF Init request type from RS. 3 different
callbacks are available (init_fresh, init_lu, init_restart) to specify
initialization code when a service starts fresh, starts after a live update,
or restarts.

SYSTEM SERVICE CHANGES:
- Initialization code for system services is now enclosed in a callback SEF will
automatically call at init time. The return code of the callback will
tell RS whether the initialization completed successfully.
- Each init callback can access information passed by RS to initialize. As of
now, each system service has access to the public entries of RS's system process
table to gather all the information required to initialize. This design
eliminates many existing or potential races at boot time and provides a uniform
initialization interface to system services. The same interface will be reused
for the upcoming publish/subscribe model to handle dynamic
registration / deregistration of system services.

VM CHANGES:
- Uniform privilege management for all system services. Every service uses the
same call mask format. For boot services, VM copies the call mask from init
data. For dynamic services, VM still receives the call mask via rs_set_priv
call that will be soon replaced by the upcoming publish/subscribe model.

RS CHANGES:
- The system process table has been reorganized and split into private entries
and public entries. Only the latter ones are exposed to system services.
- VM call masks are now entirely configured in rs/table.c
- RS has now its own slot in the system process table. Only kernel tasks and
user processes not included in the boot image are now left out from the system
process table.
- RS implements the initialization protocol for system services.
- For services in the boot image, RS blocks till initialization is complete and
panics when failure is reported back. Services are initialized in their order of
appearance in the boot image priv table and RS blocks to implements synchronous
initialization for every system service having the flag SF_SYNCH_BOOT set.
- For services started dynamically, the initialization protocol is implemented
as though it were the first ping for the service. In this case, if the
system service fails to report back (or reports failure), RS brings the service
down rather than trying to restart it.

70 files changed:
drivers/amddev/amddev.c
drivers/at_wini/at_wini.c
drivers/atl2/atl2.c
drivers/audio/framework/audio_fw.c
drivers/bios_wini/bios_wini.c
drivers/dp8390/dp8390.c
drivers/dpeth/dp.c
drivers/e1000/e1000.c
drivers/filter/main.c
drivers/floppy/floppy.c
drivers/floppy/floppy.h
drivers/fxp/fxp.c
drivers/lance/lance.c
drivers/log/log.c
drivers/memory/memory.c
drivers/orinoco/orinoco.c
drivers/pci/main.c
drivers/pci/pci.c
drivers/pci/pci.h
drivers/printer/printer.c
drivers/random/main.c
drivers/readclock/readclock.c
drivers/rtl8139/rtl8139.c
drivers/rtl8169/rtl8169.c
drivers/sb16/sb16_dsp.c
drivers/sb16/sb16_mixer.c
drivers/ti1225/ti1225.c
drivers/tty/tty.c
include/minix/com.h
include/minix/config.h
include/minix/rs.h
include/minix/sef.h
include/unistd.h
kernel/const.h
kernel/main.c
kernel/priv.h
kernel/system/do_privctl.c
kernel/system/do_safecopy.c
lib/syslib/Makefile.in
lib/syslib/safecopies.c
lib/syslib/sef.c
lib/syslib/sef_init.c [new file with mode: 0644]
lib/sysutil/env_get_prm.c
servers/ds/inc.h
servers/ds/main.c
servers/ds/proto.h
servers/ds/store.c
servers/inet/inet.c
servers/ipc/main.c
servers/is/dmp_rs.c
servers/is/main.c
servers/iso9660fs/main.c
servers/mfs/main.c
servers/mfs/mount.c
servers/pfs/main.c
servers/pm/main.c
servers/rs/const.h
servers/rs/glo.h
servers/rs/main.c
servers/rs/manager.c
servers/rs/proto.h
servers/rs/service.c
servers/rs/table.c
servers/rs/type.h
servers/rs/utility.c
servers/vfs/main.c
servers/vm/fork.c
servers/vm/main.c
servers/vm/rs.c
servers/vm/vmproc.h

index 86267550e7a161f7cecec351f3bc0e3697878dbe..342c969b6a694f275ee952a99f0a12b4804f8323 100644 (file)
@@ -49,7 +49,6 @@ static int dev_devind;
 static u8_t dev_capptr;
 static u8_t *table;
 
-static int init(void);
 static int find_dev(int *devindp, u8_t *capaddrp);
 static u32_t read_reg(int function, int index);
 static void write_reg(int function, int index, u32_t value);
@@ -65,6 +64,7 @@ static void report_exceptions(void);
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 int main(void)
 {
@@ -74,10 +74,6 @@ int main(void)
        /* SEF local startup. */
        sef_local_startup();
 
-       printf("amddev: starting\n");
-
-       init();
-
        for(;;)
        {
                report_exceptions();
@@ -106,6 +102,11 @@ int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -114,12 +115,18 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
-static int init()
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
+/* Initialize the amddev driver. */
        int r, n_maps, n_domains, revision;
        u16_t flags;
        u32_t bits;
 
+       printf("amddev: starting\n");
+
        r= find_dev(&dev_devind, &dev_capptr);
        if (!r)
                return r;
@@ -147,6 +154,8 @@ static int init()
        write_reg(DEVF_CR, 0, 0x10 | 0x8 | 0x4 | 1);
 
        printf("after write: DEVF_CR: 0x%x\n", read_reg(DEVF_CR, 0));
+
+       return(OK);
 }
 
 static int find_dev(devindp, capaddrp)
index 23c69b6fc5db0a564e08d9049159711f03f53e90..ee6a518f1f5f0947d2d43849f55e9909d7698c67 100644 (file)
@@ -217,6 +217,7 @@ PRIVATE struct driver w_dtab = {
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -226,29 +227,13 @@ EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
  *===========================================================================*/
 PUBLIC int main(int argc, char *argv[])
 {
-  struct sigaction sa;
-
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
-  /* Install signal handlers. Ask PM to transform signal into message. */
-  system_hz = sys_hz();
-
-  init_buffer();
-
-  w_identify_wakeup_ticks = WAKEUP_TICKS;
-  wakeup_ticks = WAKEUP_TICKS;
-
-  sa.sa_handler = SIG_MESS;
-  sigemptyset(&sa.sa_mask);
-  sa.sa_flags = 0;
-  if (sigaction(SIGTERM,&sa,NULL)<0) panic("AT","sigaction failed", errno);
-
-  /* Set special disk parameters then call the generic main loop. */
-  env_setargs(argc, argv);
-  init_params();
-  signal(SIGTERM, SIG_IGN);
+  /* Call the generic receive loop. */
   driver_task(&w_dtab, DRIVER_STD);
+
   return(OK);
 }
 
@@ -257,6 +242,11 @@ PUBLIC int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -266,6 +256,34 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the at_wini driver. */
+  struct sigaction sa;
+  
+  /* Install signal handlers. Ask PM to transform signal into message. */
+  system_hz = sys_hz();
+
+  init_buffer();
+
+  w_identify_wakeup_ticks = WAKEUP_TICKS;
+  wakeup_ticks = WAKEUP_TICKS;
+
+  sa.sa_handler = SIG_MESS;
+  sigemptyset(&sa.sa_mask);
+  sa.sa_flags = 0;
+  if (sigaction(SIGTERM,&sa,NULL)<0) panic("AT","sigaction failed", errno);
+
+  /* Set special disk parameters. */
+  init_params();
+  signal(SIGTERM, SIG_IGN);
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                             init_params                                  *
  *===========================================================================*/
index e57a8983feb03fb3e5f2ad9a7e0b67550ff7d105..eefd3ea3a09879a89792a10e68e327cf112b53e5 100644 (file)
@@ -91,6 +91,8 @@ PRIVATE struct {
        { 0x0000, 0x0000 }
 };
 
+long instance;
+
 /*===========================================================================*
  *                             atl2_read_vpd                                *
  *===========================================================================*/
@@ -1237,39 +1239,19 @@ PRIVATE void atl2_dump(void)
 }
 
 /*===========================================================================*
- *                             sef_local_startup                            *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void sef_local_startup(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-       /* Initialize the System Event Framework.
-        */
-
-       /* No support for live update yet. */
-       sef_startup();
-}
-
-/*===========================================================================*
- *                             main                                         *
- *===========================================================================*/
-int main(int argc, char **argv)
-{
-       /* Driver task.
-        */
+/* Initialize the atl2 driver. */
        u32_t inet_endpt;
-       message m;
-       sigset_t set;
        int r, devind;
-       long instance;
 #if ATL2_FKEY
        int fkeys, sfkeys;
 #endif
 
-       /* Initialize SEF. */
-       sef_local_startup();
-
        /* How many matching devices should we skip? */
        instance = 0;
-       env_setargs(argc, argv);
        env_parse("atl2_instance", "d", 0, &instance, 0, 32);
 
        /* Try to find a recognized device. */
@@ -1296,6 +1278,39 @@ int main(int argc, char **argv)
                printf("ATL2: warning, could not map Shift+F11 key (%d)\n", r);
 #endif
 
+       return(OK);
+}
+
+/*===========================================================================*
+ *                             sef_local_startup                            *
+ *===========================================================================*/
+PRIVATE void sef_local_startup(void)
+{
+       /* Register init callbacks. */
+       sef_setcb_init_fresh(sef_cb_init_fresh);
+       sef_setcb_init_restart(sef_cb_init_fresh);
+
+       /* No support for live update yet. */
+
+       /* Let SEF perform startup. */
+       sef_startup();
+}
+
+/*===========================================================================*
+ *                             main                                         *
+ *===========================================================================*/
+int main(int argc, char **argv)
+{
+       /* Driver task.
+        */
+       message m;
+       sigset_t set;
+       int r;
+
+       /* Initialize SEF. */
+       env_setargs(argc, argv);
+       sef_local_startup();
+
        while (TRUE) {
                if ((r = sef_receive(ANY, &m)) != OK)
                        panic("atl2", "sef_receive failed", r);
index 84951eb7ce84bcf03e92ca2e762002fe7756df7f..be719cef1532cad1651cda11c7491b0c3490dbe9 100644 (file)
@@ -79,6 +79,7 @@ PRIVATE device_available = 0;/*todo*/
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -92,8 +93,6 @@ PUBLIC void main(void)
        /* SEF local startup. */
        sef_local_startup();
 
-       drv_init();
-
        /* Here is the main loop of the dma driver.  It waits for a message, 
           carries it out, and sends a reply. */
 
@@ -185,6 +184,11 @@ PUBLIC void main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -194,6 +198,15 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the audio driver framework. */
+  return init_driver();
+}
+
 PRIVATE int init_driver(void) {
        u32_t i; char irq;
        static int executed = 0;
index c14ce12dacf82d5bb0a1706083a9385d8865c105..a62650e867fa4c3714b086f3888bb9dedb5c1257 100644 (file)
@@ -96,23 +96,19 @@ PRIVATE struct driver w_dtab = {
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             bios_winchester_task                         *
  *===========================================================================*/
 PUBLIC int main()
 {
-  long v;
-
   /* SEF local startup. */
   sef_local_startup();
 
-  v= 0;
-  env_parse("bios_remap_first", "d", 0, &v, 0, 1);
-  remap_first= v;
-
-/* Set special disk parameters then call the generic main loop. */
+  /* Call the generic receive loop. */
   driver_task(&w_dtab, DRIVER_STD);
+
   return(OK);
 }
 
@@ -121,6 +117,11 @@ PUBLIC int main()
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -129,6 +130,21 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the bios_wini driver. */
+  long v;
+
+  v = 0;
+  env_parse("bios_remap_first", "d", 0, &v, 0, 1);
+  remap_first = v;
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                             w_prepare                                    *
  *===========================================================================*/
index 9dfac7d633db3d98b79452b4a0712087cb3f13f5..bedede9c9bf45d093e2faf7207bd9354f747168a 100644 (file)
@@ -234,6 +234,9 @@ PRIVATE int handle_hw_intr(void)
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
  *                             dpeth_task                                   *
@@ -241,38 +244,11 @@ FORWARD _PROTOTYPE( void sef_local_startup, (void) );
 int main(int argc, char *argv[])
 {
        message m;
-       int i, r, tasknr;
-       dpeth_t *dep;
-       long v;
+       int r;
 
        /* SEF local startup. */
-       sef_local_startup();
-
-       system_hz = sys_hz();
-
-       if (argc < 1)
-       {
-               panic("DP8390",
-                       "A head which at this time has no name", NO_NUM);
-       }
-       (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
        env_setargs(argc, argv);
-
-       for (i= 0, dep= de_table; i<DE_PORT_NR; i++, dep++)
-       {
-               strcpy(dep->de_name, "dp8390#0");
-               dep->de_name[7] += i;
-       }
-
-       v= 0;
-       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
-       eth_ign_proto= htons((u16_t) v);
-
-       /* Try to notify inet that we are present (again) */
-       r = _pm_findproc("inet", &tasknr);
-       if (r == OK)
-               notify(tasknr);
+       sef_local_startup();
 
        while (TRUE)
        {
@@ -331,12 +307,54 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the dp8390 driver. */
+       int i, r, tasknr;
+       dpeth_t *dep;
+       long v;
+
+       system_hz = sys_hz();
+
+       if (env_argc < 1)
+       {
+               panic("DP8390",
+                       "A head which at this time has no name", NO_NUM);
+       }
+       (progname=strrchr(env_argv[0],'/')) ? progname++
+               : (progname=env_argv[0]);
+
+       for (i= 0, dep= de_table; i<DE_PORT_NR; i++, dep++)
+       {
+               strcpy(dep->de_name, "dp8390#0");
+               dep->de_name[7] += i;
+       }
+
+       v= 0;
+       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
+       eth_ign_proto= htons((u16_t) v);
+
+       /* Try to notify inet that we are present (again) */
+       r = _pm_findproc("inet", &tasknr);
+       if (r == OK)
+               notify(tasknr);
+
+       return(OK);
+}
+
 #if 0
 /*===========================================================================*
  *                             dp8390_dump                                  *
index 7de00b47403a65cc709180b731f51cced85424f2..c8ca4ea2c5a931d7ccc0a74baf6a7f5e823b9ab5 100644 (file)
@@ -579,6 +579,9 @@ PRIVATE void handle_hw_intr(void)
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*
 **  Name:      int dpeth_task(void)
@@ -588,34 +591,11 @@ PUBLIC int main(int argc, char **argv)
 {
   message m;
   dpeth_t *dep;
-  int rc, fkeys, sfkeys, tasknr;
+  int rc;
 
   /* SEF local startup. */
-  sef_local_startup();
-
-  (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
   env_setargs(argc, argv);
-
-  /* Request function key for debug dumps */
-  fkeys = sfkeys = 0; bit_set(sfkeys, 8);
-  if ((fkey_map(&fkeys, &sfkeys)) != OK) 
-       printf("%s: couldn't program Shift+F8 key (%d)\n", DevName, errno);
-
-#ifdef ETH_IGN_PROTO
-  {
-       static u16_t eth_ign_proto = 0;
-       long val;
-       val = 0xFFFF;
-       env_parse("ETH_IGN_PROTO", "x", 0, &val, 0x0000L, 0xFFFFL);
-       eth_ign_proto = htons((u16_t) val);
-  }
-#endif
-
-  /* Try to notify inet that we are present (again) */
-  rc = _pm_findproc("inet", &tasknr);
-  if (rc == OK)
-       notify(tasknr);
+  sef_local_startup();
 
   while (TRUE) {
        if ((rc = sef_receive(ANY, &m)) != OK) panic(dep->de_name, RecvErrMsg, rc);
@@ -680,10 +660,48 @@ PUBLIC int main(int argc, char **argv)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the dpeth driver. */
+  dpeth_t *dep;
+  int rc, fkeys, sfkeys, tasknr;
+
+  (progname=strrchr(env_argv[0],'/')) ? progname++ : (progname=env_argv[0]);
+
+  /* Request function key for debug dumps */
+  fkeys = sfkeys = 0; bit_set(sfkeys, 8);
+  if ((fkey_map(&fkeys, &sfkeys)) != OK) 
+       printf("%s: couldn't program Shift+F8 key (%d)\n", DevName, errno);
+
+#ifdef ETH_IGN_PROTO
+  {
+       static u16_t eth_ign_proto = 0;
+       long val;
+       val = 0xFFFF;
+       env_parse("ETH_IGN_PROTO", "x", 0, &val, 0x0000L, 0xFFFFL);
+       eth_ign_proto = htons((u16_t) val);
+  }
+#endif
+
+  /* Try to notify inet that we are present (again) */
+  rc = _pm_findproc("inet", &tasknr);
+  if (rc == OK)
+       notify(tasknr);
+
+  return(OK);
+}
+
 /** dp.c **/
index 22c5a4ebb35330a4a00a59039e66e84b38766bcd..28ed13d30b2fddb0bc8bc035118ddccfa306be23 100644 (file)
@@ -64,6 +64,9 @@ _PROTOTYPE( PRIVATE void mess_reply, (message *req, message *reply)   );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
  *                             main                                         *
@@ -71,40 +74,12 @@ FORWARD _PROTOTYPE( void sef_local_startup, (void) );
 int main(int argc, char *argv[])
 {
     message m;
-    int i, r;
-    u32_t tasknr;
-    e1000_t *e;
-    long v;
+    int r;
 
     /* SEF local startup. */
+    env_setargs(argc, argv);
     sef_local_startup();
 
-    /* Verify command-line arguments. */
-    if (argc < 1)
-    {
-       panic("e1000", "no program name given in argc/argv", NO_NUM);
-    }
-    else
-       (progname = strrchr(argv[0],'/')) ? progname++ : (progname = argv[0]);
-
-    /* Clear state. */
-    memset(e1000_table, 0, sizeof(e1000_table));
-
-    /* Perform calibration. */
-    if((r = micro_delay_calibrate()) != OK)
-    {
-        panic("e1000", "rmicro_delay_calibrate failed", r);
-    }
-    /* Try to notify inet that we are present (again) */
-    if ((r = ds_retrieve_u32("inet", &tasknr)) == OK)
-    {
-        notify(tasknr);
-    }
-    else if (r != ESRCH)
-    {
-        printf("e1000: ds_retrieve_u32 failed for 'inet': %d\n", r);
-    }
-
     /*
      * Enter the main driver loop.
      */
@@ -150,12 +125,55 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the e1000 driver. */
+    int r;
+    u32_t tasknr;
+
+    /* Verify command-line arguments. */
+    if (env_argc < 1)
+    {
+       panic("e1000", "no program name given in argc/argv", NO_NUM);
+    }
+    else
+       (progname = strrchr(env_argv[0],'/')) ? progname++
+               : (progname = env_argv[0]);
+
+    /* Clear state. */
+    memset(e1000_table, 0, sizeof(e1000_table));
+
+    /* Perform calibration. */
+    if((r = micro_delay_calibrate()) != OK)
+    {
+        panic("e1000", "rmicro_delay_calibrate failed", r);
+    }
+    /* Try to notify inet that we are present (again) */
+    if ((r = ds_retrieve_u32("inet", &tasknr)) == OK)
+    {
+        notify(tasknr);
+    }
+    else if (r != ESRCH)
+    {
+        printf("e1000: ds_retrieve_u32 failed for 'inet': %d\n", r);
+    }
+
+    return(OK);
+}
+
 /*===========================================================================*
  *                             e1000_init                                   *
  *===========================================================================*/
index 834f4e2123aa3357464ed20737941f1f36c9c94a..1d7fd5a640be306d4da2a7817535ae3cbba644d7 100644 (file)
@@ -73,6 +73,12 @@ static cp_grant_id_t grant_id;                       /* IO_GRANT */
 /* Data buffers. */
 static char *buf_array, *buffer;               /* contiguous buffer */
 
+/* SEF functions and variables. */
+FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
+
 /*===========================================================================*
  *                             carry                                        *
  *===========================================================================*/
@@ -384,17 +390,6 @@ static void got_signal(void)
        exit(0);
 }
 
-/*===========================================================================*
- *                            sef_local_startup                             *
- *===========================================================================*/
-static void sef_local_startup(void)
-{
-       /* No live update support for now. */
-
-       /* Let SEF perform startup. */
-       sef_startup();
-}
-
 /*===========================================================================*
  *                             main                                         *
  *===========================================================================*/
@@ -404,21 +399,9 @@ int main(int argc, char *argv[])
        int r;
 
        /* SEF local startup. */
+       env_setargs(argc, argv);
        sef_local_startup();
 
-       r = parse_arguments(argc, argv);
-       if(r != OK) {
-               printf("Filter: wrong argument!\n");
-               return 1;
-       }
-
-       if ((buf_array = flt_malloc(BUF_SIZE, NULL, 0)) == NULL)
-               panic(__FILE__, "no memory available", NO_NUM);
-
-       sum_init();
-
-       driver_init();
-
        for (;;) {
                /* Wait for request. */
                if(sef_receive(ANY, &m_in) != OK) {
@@ -466,3 +449,43 @@ int main(int argc, char *argv[])
 
        return 0;
 }
+
+/*===========================================================================*
+ *                            sef_local_startup                             *
+ *===========================================================================*/
+PRIVATE void sef_local_startup(void)
+{
+       /* Register init callbacks. */
+       sef_setcb_init_fresh(sef_cb_init_fresh);
+       sef_setcb_init_restart(sef_cb_init_fresh);
+
+       /* No live update support for now. */
+
+       /* Let SEF perform startup. */
+       sef_startup();
+}
+
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the filter driver. */
+       int r;
+
+       r = parse_arguments(env_argc, env_argv);
+       if(r != OK) {
+               printf("Filter: wrong argument!\n");
+               return 1;
+       }
+
+       if ((buf_array = flt_malloc(BUF_SIZE, NULL, 0)) == NULL)
+               panic(__FILE__, "no memory available", NO_NUM);
+
+       sum_init();
+
+       driver_init();
+
+       return(OK);
+}
+
index 3788d8a3dd7d84ac8841a1b0268cac96576e301e..00700d31089a806ae4222479316309d7d5f8d8a7 100644 (file)
@@ -292,6 +292,7 @@ static phys_bytes floppy_buf_phys;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -300,14 +301,45 @@ PUBLIC int last_transfer_opcode;
 /*===========================================================================*
  *                             floppy_task                                  *
  *===========================================================================*/
-PUBLIC void main()
+PUBLIC int main()
 {
-  struct floppy *fp;
-  int s;
-
   /* SEF local startup. */
   sef_local_startup();
 
+  /* Call the generic receive loop. */
+  driver_task(&f_dtab, DRIVER_STD);
+
+  return(OK);
+}
+
+/*===========================================================================*
+ *                            sef_local_startup                             *
+ *===========================================================================*/
+PRIVATE void sef_local_startup()
+{
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
+  /* Register live update callbacks. */
+  sef_setcb_lu_prepare(sef_cb_lu_prepare);
+  sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
+  sef_setcb_lu_state_dump(sef_cb_lu_state_dump);
+
+  /* Let SEF perform startup. */
+  sef_startup();
+}
+
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the floppy driver. */
+  struct floppy *fp;
+  int s;
+
   /* Initialize the floppy structure and the timers. */
   system_hz = sys_hz();
 
@@ -337,21 +369,7 @@ PUBLIC void main()
   /* Ignore signals */
   signal(SIGHUP, SIG_IGN);
 
-  driver_task(&f_dtab, DRIVER_STD);
-}
-
-/*===========================================================================*
- *                            sef_local_startup                             *
- *===========================================================================*/
-PRIVATE void sef_local_startup()
-{
-  /* Register live update callbacks. */
-  sef_setcb_lu_prepare(sef_cb_lu_prepare);
-  sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
-  sef_setcb_lu_state_dump(sef_cb_lu_state_dump);
-
-  /* Let SEF perform startup. */
-  sef_startup();
+  return(OK);
 }
 
 /*===========================================================================*
index 6d737ab7e8bbcb50296c0ec0c57a536415a4fd89..49e16225e2323c3c170cf349623e5b34a800de80 100644 (file)
@@ -2,6 +2,6 @@
 #include "../libdriver/driver.h"
 #include "../libdriver/drvlib.h"
 
-_PROTOTYPE(void main, (void));
+_PROTOTYPE(int main, (void));
 
 
index 576f2f27be97461b19bba220b0f6e622496200c7..1d3dbba6e69c6c78411be547f1d1559620d99c39 100644 (file)
@@ -303,6 +303,9 @@ PRIVATE void handle_hw_intr(void)
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
  *                             main                                         *
@@ -310,42 +313,12 @@ FORWARD _PROTOTYPE( void sef_local_startup, (void) );
 int main(int argc, char *argv[])
 {
        message m;
-       int i, r;
-       u32_t tasknr;
-       long v;
-       vir_bytes ft = sizeof(*fxp_table)*FXP_PORT_NR;
+       int r;
 
        /* SEF local startup. */
+       env_setargs(argc, argv);
        sef_local_startup();
 
-       system_hz = sys_hz();
-
-       if (argc < 1)
-               panic("FXP", "A head which at this time has no name", NO_NUM);
-       (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
-       v= 0;
-#if 0
-       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
-#endif
-       eth_ign_proto= htons((u16_t) v);
-
-       if(!(fxp_table = alloc_contig(ft, 0, &fxp_table_phys)))
-               panic("FXP","couldn't allocate table", r);
-
-       memset(fxp_table, 0, ft);
-
-       if((r=micro_delay_calibrate()) != OK)
-               panic("FXP","rmicro_delay_calibrate failed", r);
-
-       /* Try to notify inet that we are present (again) */
-       r= ds_retrieve_u32("inet", &tasknr);
-       if (r == OK)
-               notify(tasknr);
-       else if (r != ESRCH)
-               printf("fxp: ds_retrieve_u32 failed for 'inet': %d\n", r);
-
-
        while (TRUE)
        {
                if ((r= sef_receive(ANY, &m)) != OK)
@@ -401,12 +374,59 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the fxp driver. */
+       int r;
+       u32_t tasknr;
+       long v;
+       vir_bytes ft;
+
+       ft = sizeof(*fxp_table)*FXP_PORT_NR;
+       system_hz = sys_hz();
+
+       if (env_argc < 1)
+               panic("FXP", "A head which at this time has no name", NO_NUM);
+       (progname=strrchr(env_argv[0],'/')) ? progname++
+               : (progname=env_argv[0]);
+
+       v= 0;
+#if 0
+       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
+#endif
+       eth_ign_proto= htons((u16_t) v);
+
+       if(!(fxp_table = alloc_contig(ft, 0, &fxp_table_phys)))
+               panic("FXP","couldn't allocate table", r);
+
+       memset(fxp_table, 0, ft);
+
+       if((r=micro_delay_calibrate()) != OK)
+               panic("FXP","rmicro_delay_calibrate failed", r);
+
+       /* Try to notify inet that we are present (again) */
+       r= ds_retrieve_u32("inet", &tasknr);
+       if (r == OK)
+               notify(tasknr);
+       else if (r != ESRCH)
+               printf("fxp: ds_retrieve_u32 failed for 'inet': %d\n", r);
+
+       return(OK);
+}
+
 /*===========================================================================*
  *                             fxp_init                                     *
  *===========================================================================*/
index 5975f9a3d12f731c514bdc5ca16635f546f3c8fe..c6a49e19c3c2f9c33eb28f2964ef82d9139b4f4d 100644 (file)
@@ -267,6 +267,9 @@ phys_bytes lance_buf_phys;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
  *                              main                                         *
@@ -275,38 +278,12 @@ void main( int argc, char **argv )
 {
    message m;
    int i,irq,r;
-   u32_t tasknr;
    ether_card_t *ec;
-   long v;
-#if LANCE_FKEY
-   int fkeys, sfkeys;
-#endif
 
    /* SEF local startup. */
+   env_setargs(argc, argv);
    sef_local_startup();
 
-   (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
-   env_setargs( argc, argv );
-
-#if LANCE_FKEY
-   fkeys = sfkeys = 0;
-   bit_set( sfkeys, 7 );
-   if ( (r = fkey_map(&fkeys, &sfkeys)) != OK )
-      printf("Warning: lance couldn't observe Shift+F7 key: %d\n",r);
-#endif
-
-   v= 0;
-   (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
-   eth_ign_proto= htons((u16_t) v);
-
-   /* Try to notify inet that we are present (again) */
-   r= ds_retrieve_u32("inet", &tasknr);
-   if (r == OK)
-      notify(tasknr);
-   else if (r != ESRCH)
-      printf("lance: ds_retrieve_u32 failed for 'inet': %d\n", r);
-
    while (TRUE)
    {
       for (i=0;i<EC_PORT_NR_MAX;++i)
@@ -396,12 +373,52 @@ void main( int argc, char **argv )
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the lance driver. */
+   int r;
+   u32_t tasknr;
+   long v;
+#if LANCE_FKEY
+   int fkeys, sfkeys;
+#endif
+
+   (progname=strrchr(env_argv[0],'/')) ? progname++ : (progname=env_argv[0]);
+
+#if LANCE_FKEY
+   fkeys = sfkeys = 0;
+   bit_set( sfkeys, 7 );
+   if ( (r = fkey_map(&fkeys, &sfkeys)) != OK )
+      printf("Warning: lance couldn't observe Shift+F7 key: %d\n",r);
+#endif
+
+   v= 0;
+   (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
+   eth_ign_proto= htons((u16_t) v);
+
+   /* Try to notify inet that we are present (again) */
+   r= ds_retrieve_u32("inet", &tasknr);
+   if (r == OK)
+      notify(tasknr);
+   else if (r != ESRCH)
+      printf("lance: ds_retrieve_u32 failed for 'inet': %d\n", r);
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                              lance_dump                                   *
  *===========================================================================*/
index 7009526d5efb28036073c2425ce3a2d238988c6f..e662f9aa21f69b2c3495db5a6b313be09600aecc 100644 (file)
@@ -56,6 +56,7 @@ extern int device_caller;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -65,24 +66,12 @@ EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
  *===========================================================================*/
 PUBLIC int main(void)
 {
-  int i;
-
   /* SEF local startup. */
   sef_local_startup();
 
-  /* Initialize log devices. */
-  for(i = 0; i < NR_DEVS; i++) {
-       log_geom[i].dv_size = cvul64(LOG_SIZE);
-       log_geom[i].dv_base = cvul64((long)logdevices[i].log_buffer);
-       logdevices[i].log_size = logdevices[i].log_read =
-               logdevices[i].log_write =
-               logdevices[i].log_select_alerted =
-               logdevices[i].log_selected =
-               logdevices[i].log_select_ready_ops = 0;
-       logdevices[i].log_proc_nr = 0;
-       logdevices[i].log_revive_alerted = 0;
-  }
+  /* Call the generic receive loop. */
   driver_task(&log_dtab, DRIVER_ASYN);
+
   return(OK);
 }
 
@@ -91,6 +80,11 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -100,6 +94,30 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the log driver. */
+  int i;
+
+  /* Initialize log devices. */
+  for(i = 0; i < NR_DEVS; i++) {
+       log_geom[i].dv_size = cvul64(LOG_SIZE);
+       log_geom[i].dv_base = cvul64((long)logdevices[i].log_buffer);
+       logdevices[i].log_size = logdevices[i].log_read =
+               logdevices[i].log_write =
+               logdevices[i].log_select_alerted =
+               logdevices[i].log_selected =
+               logdevices[i].log_select_ready_ops = 0;
+       logdevices[i].log_proc_nr = 0;
+       logdevices[i].log_revive_alerted = 0;
+  }
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                              log_name                                    *
  *===========================================================================*/
index 0402f00c3a49c3f701ecbeb3dcbfa9446fe261a6..231a74161c11e46b4b35a70c095777d993c808c8 100644 (file)
@@ -55,7 +55,6 @@ FORWARD _PROTOTYPE( int m_transfer, (int proc_nr, int opcode,
                        u64_t position, iovec_t *iov, unsigned nr_req)  );
 FORWARD _PROTOTYPE( int m_do_open, (struct driver *dp, message *m_ptr)         );
 FORWARD _PROTOTYPE( int m_do_close, (struct driver *dp, message *m_ptr)        );
-FORWARD _PROTOTYPE( void m_init, (void) );
 FORWARD _PROTOTYPE( int m_ioctl, (struct driver *dp, message *m_ptr)   );
 FORWARD _PROTOTYPE( void m_geometry, (struct partition *entry)                 );
 
@@ -86,25 +85,19 @@ PRIVATE char dev_zero[ZERO_BUF_SIZE];
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                                main                                      *
  *===========================================================================*/
 PUBLIC int main(void)
 {
-/* Main program. Initialize the memory driver and start the main loop. */
-  struct sigaction sa;
-
   /* SEF local startup. */
   sef_local_startup();
 
-  sa.sa_handler = SIG_MESS;
-  sigemptyset(&sa.sa_mask);
-  sa.sa_flags = 0;
-  if (sigaction(SIGTERM,&sa,NULL)<0) panic("MEM","sigaction failed", errno);
-
-  m_init();
+  /* Call the generic receive loop. */
   driver_task(&m_dtab, DRIVER_STD);
+
   return(OK);
 }
 
@@ -113,6 +106,11 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -121,6 +119,58 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the memory driver. */
+  struct sigaction sa;
+  u32_t ramdev_size;
+  int i, s;
+
+  sa.sa_handler = SIG_MESS;
+  sigemptyset(&sa.sa_mask);
+  sa.sa_flags = 0;
+  if (sigaction(SIGTERM,&sa,NULL)<0) panic("MEM","sigaction failed", errno);
+
+  /* Initialize all minor devices one by one. */
+  if (OK != (s=sys_getkinfo(&kinfo))) {
+      panic("MEM","Couldn't get kernel information.",s);
+  }
+
+#if 0
+  /* Map in kernel memory for /dev/kmem. */
+  m_geom[KMEM_DEV].dv_base = cvul64(kinfo.kmem_base);
+  m_geom[KMEM_DEV].dv_size = cvul64(kinfo.kmem_size);
+  if((m_vaddrs[KMEM_DEV] = vm_map_phys(SELF, (void *) kinfo.kmem_base,
+       kinfo.kmem_size)) == MAP_FAILED) {
+       printf("MEM: Couldn't map in /dev/kmem.");
+  }
+#endif
+
+  /* Ramdisk image built into the memory driver */
+  m_geom[IMGRD_DEV].dv_base= cvul64(0);
+  m_geom[IMGRD_DEV].dv_size= cvul64(imgrd_size);
+  m_vaddrs[IMGRD_DEV] = (vir_bytes) imgrd;
+
+  /* Initialize /dev/zero. Simply write zeros into the buffer. */
+  for (i=0; i<ZERO_BUF_SIZE; i++) {
+       dev_zero[i] = '\0';
+  }
+
+  for(i = 0; i < NR_DEVS; i++)
+       openct[i] = 0;
+
+  /* Set up memory range for /dev/mem. */
+  m_geom[MEM_DEV].dv_base = cvul64(0);
+  m_geom[MEM_DEV].dv_size = cvul64(0xffffffff);
+
+  m_vaddrs[MEM_DEV] = (vir_bytes) MAP_FAILED; /* we are not mapping this in. */
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                              m_name                                      *
  *===========================================================================*/
@@ -357,50 +407,6 @@ message *m_ptr;
   return(OK);
 }
 
-
-/*===========================================================================*
- *                             m_init                                       *
- *===========================================================================*/
-PRIVATE void m_init()
-{
-  /* Initialize this task. All minor devices are initialized one by one. */
-  u32_t ramdev_size;
-  int i, s;
-
-  if (OK != (s=sys_getkinfo(&kinfo))) {
-      panic("MEM","Couldn't get kernel information.",s);
-  }
-
-#if 0
-  /* Map in kernel memory for /dev/kmem. */
-  m_geom[KMEM_DEV].dv_base = cvul64(kinfo.kmem_base);
-  m_geom[KMEM_DEV].dv_size = cvul64(kinfo.kmem_size);
-  if((m_vaddrs[KMEM_DEV] = vm_map_phys(SELF, (void *) kinfo.kmem_base,
-       kinfo.kmem_size)) == MAP_FAILED) {
-       printf("MEM: Couldn't map in /dev/kmem.");
-  }
-#endif
-
-  /* Ramdisk image built into the memory driver */
-  m_geom[IMGRD_DEV].dv_base= cvul64(0);
-  m_geom[IMGRD_DEV].dv_size= cvul64(imgrd_size);
-  m_vaddrs[IMGRD_DEV] = (vir_bytes) imgrd;
-
-  /* Initialize /dev/zero. Simply write zeros into the buffer. */
-  for (i=0; i<ZERO_BUF_SIZE; i++) {
-       dev_zero[i] = '\0';
-  }
-
-  for(i = 0; i < NR_DEVS; i++)
-       openct[i] = 0;
-
-  /* Set up memory range for /dev/mem. */
-  m_geom[MEM_DEV].dv_base = cvul64(0);
-  m_geom[MEM_DEV].dv_size = cvul64(0xffffffff);
-
-  m_vaddrs[MEM_DEV] = (vir_bytes) MAP_FAILED; /* we are not mapping this in. */
-}
-
 /*===========================================================================*
  *                             m_ioctl                                      *
  *===========================================================================*/
index 4b3105ce511a18701851a8e292187e3e5325fa61..515246ad2fe4bca08313e4fb5844b5711f36eaab 100644 (file)
@@ -238,6 +238,9 @@ extern int errno;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*****************************************************************************
  *            main                                                           *
@@ -246,33 +249,11 @@ FORWARD _PROTOTYPE( void sef_local_startup, (void) );
  * The main function of the driver, receiving and processing messages        *
  *****************************************************************************/
 int main(int argc, char *argv[]) {
-       int fkeys, sfkeys, r, i, ret;
-       u32_t inet_proc_nr;
-       long v = 0;
-       t_or *orp;
+       int r;
 
        /* SEF local startup. */
-       sef_local_startup();
-
-       system_hz = sys_hz();
-
-       (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
        env_setargs(argc, argv);
-
-       /* Observe some function key for debug dumps. */
-       fkeys = sfkeys = 0; bit_set(sfkeys, 11);
-       if ((r=fkey_map(&fkeys, &sfkeys)) != OK) 
-           printf("Warning: orinoco couldn't observe F-key(s): %d\n",r);
-
-       /* Try to notify INET that we are present (again). If INET cannot
-        * be found, assume this is the first time we started and INET is
-        * not yet alive. */
-       r = ds_retrieve_u32("inet", &inet_proc_nr);
-       if (r == OK) 
-               notify(inet_proc_nr);
-       else if (r != ESRCH)
-               printf("orinoco: ds_retrieve_u32 failed for 'inet': %d\n", r);
+       sef_local_startup();
 
        while (TRUE) {
                if ((r = sef_receive (ANY, &m)) != OK)
@@ -354,12 +335,47 @@ int main(int argc, char *argv[]) {
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the orinoco driver. */
+       int fkeys, sfkeys, r;
+       u32_t inet_proc_nr;
+
+       system_hz = sys_hz();
+
+       (progname=strrchr(env_argv[0],'/')) ? progname++
+               : (progname=env_argv[0]);
+
+       /* Observe some function key for debug dumps. */
+       fkeys = sfkeys = 0; bit_set(sfkeys, 11);
+       if ((r=fkey_map(&fkeys, &sfkeys)) != OK) 
+           printf("Warning: orinoco couldn't observe F-key(s): %d\n",r);
+
+       /* Try to notify INET that we are present (again). If INET cannot
+        * be found, assume this is the first time we started and INET is
+        * not yet alive. */
+       r = ds_retrieve_u32("inet", &inet_proc_nr);
+       if (r == OK) 
+               notify(inet_proc_nr);
+       else if (r != ESRCH)
+               printf("orinoco: ds_retrieve_u32 failed for 'inet': %d\n", r);
+
+       return(OK);
+}
+
 /*****************************************************************************
  *                    check_int_events                                       *
  *                                                                           *
index fecbef64499e4108e8825b9d89f9d059eaa233ba..67c7c94fdb6a8d969ec9c06f561ff43c9ee64556 100644 (file)
@@ -10,13 +10,7 @@ main.c
 
 #include "pci.h"
 
-#define NR_DRIVERS     NR_SYS_PROCS
-
-PRIVATE struct acl
-{
-       int inuse;
-       struct rs_pci acl;
-} acl[NR_DRIVERS];
+PUBLIC struct pci_acl pci_acl[NR_DRIVERS];
 
 FORWARD _PROTOTYPE( void do_init, (message *mp)                                );
 FORWARD _PROTOTYPE( void do_first_dev, (message *mp)                   );
@@ -52,8 +46,6 @@ int main(void)
        /* SEF local startup. */
        sef_local_startup();
 
-       pci_init();
-
        for(;;)
        {
                r= sef_receive(ANY, &m);
@@ -112,6 +104,11 @@ int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -126,7 +123,7 @@ message *mp;
        int r;
 
 #if DEBUG
-       printf("PCI: pci_init: called by '%d'\n", mp->m_source);
+       printf("PCI: do_init: called by '%d'\n", mp->m_source);
 #endif
 
        mp->m_type= 0;
@@ -363,7 +360,7 @@ message *mp;
 
        for (i= 0; i<NR_DRIVERS; i++)
        {
-               if (!acl[i].inuse)
+               if (!pci_acl[i].inuse)
                        break;
        }
        if (i >= NR_DRIVERS)
@@ -375,18 +372,18 @@ message *mp;
 
        gid= mp->m1_i1;
 
-       r= sys_safecopyfrom(mp->m_source, gid, 0, (vir_bytes)&acl[i].acl,
-               sizeof(acl[i].acl), D);
+       r= sys_safecopyfrom(mp->m_source, gid, 0, (vir_bytes)&pci_acl[i].acl,
+               sizeof(pci_acl[i].acl), D);
        if (r != OK)
        {
                printf("PCI: do_set_acl: safecopyfrom failed\n");
                reply(mp, r);
                return;
        }
-       acl[i].inuse= 1;
+       pci_acl[i].inuse= 1;
        if(debug)
          printf("PCI: do_acl: setting ACL for %d ('%s') at entry %d\n",
-               acl[i].acl.rsp_endpoint, acl[i].acl.rsp_label,
+               pci_acl[i].acl.rsp_endpoint, pci_acl[i].acl.rsp_label,
                i);
 
        reply(mp, OK);
@@ -408,9 +405,9 @@ message *mp;
 
        for (i= 0; i<NR_DRIVERS; i++)
        {
-               if (!acl[i].inuse)
+               if (!pci_acl[i].inuse)
                        continue;
-               if (acl[i].acl.rsp_endpoint == proc_nr)
+               if (pci_acl[i].acl.rsp_endpoint == proc_nr)
                        break;
        }
 
@@ -421,10 +418,10 @@ message *mp;
                return;
        }
 
-       acl[i].inuse= 0;
+       pci_acl[i].inuse= 0;
 #if 0
        printf("do_acl: deleting ACL for %d ('%s') at entry %d\n",
-               acl[i].acl.rsp_endpoint, acl[i].acl.rsp_label, i);
+               pci_acl[i].acl.rsp_endpoint, pci_acl[i].acl.rsp_label, i);
 #endif
 
        /* Also release all devices held by this process */
@@ -621,10 +618,10 @@ int endpoint;
        /* Find ACL entry for caller */
        for (i= 0; i<NR_DRIVERS; i++)
        {
-               if (!acl[i].inuse)
+               if (!pci_acl[i].inuse)
                        continue;
-               if (acl[i].acl.rsp_endpoint == endpoint)
-                       return &acl[i].acl;
+               if (pci_acl[i].acl.rsp_endpoint == endpoint)
+                       return &pci_acl[i].acl;
        }
        return NULL;
 }
index 9aa1cf60fb2595ffce131e6221b1f5740a61ddbd..9ebf3d6d75ea675b1f9197d30c89b02bc0d6287f 100644 (file)
@@ -12,7 +12,6 @@ Created:      Jan 2000 by Philip Homburg <philip@cs.vu.nl>
 #include <ibm/pci.h>
 #include <sys/vm_i386.h>
 #include <minix/com.h>
-#include <minix/rs.h>
 #include <minix/syslib.h>
 
 #include "pci.h"
@@ -86,6 +85,8 @@ PRIVATE struct pcidev
        int pd_bar_nr;
 } pcidev[NR_PCIDEV];
 
+EXTERN struct pci_acl *pci_acl;
+
 /* pb_flags */
 #define PBF_IO         1       /* I/O else memory */
 #define PBF_INCOMPLETE 2       /* not allocated */
@@ -149,6 +150,75 @@ FORWARD _PROTOTYPE( void print_capabilities, (int devind)          );
 FORWARD _PROTOTYPE( int visible, (struct rs_pci *aclp, int devind)     );
 FORWARD _PROTOTYPE( void print_hyper_cap, (int devind, U8_t capptr)    );
 
+/*===========================================================================*
+ *                             sef_cb_init_fresh                            *
+ *===========================================================================*/
+PUBLIC int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the pci driver. */
+       long v;
+       int i, r;
+       struct rprocpub rprocpub[NR_BOOT_PROCS];
+
+       v= 0;
+       env_parse("pci_debug", "d", 0, &v, 0, 1);
+       debug= v;
+
+       /* Only Intel (compatible) PCI controllers are supported at the
+        * moment.
+        */
+       pci_intel_init();
+
+       /* Map all the services in the boot image. */
+       if((r = sys_safecopyfrom(RS_PROC_NR, info->rproctab_gid, 0,
+               (vir_bytes) rprocpub, sizeof(rprocpub), S)) != OK) {
+               panic("pci", "sys_safecopyfrom failed", r);
+       }
+       for(i=0;i < NR_BOOT_PROCS;i++) {
+               if(rprocpub[i].in_use) {
+                       if((r = map_service(&rprocpub[i])) != OK) {
+                               panic("pci", "unable to map service", r);
+                       }
+               }
+       }
+
+       return(OK);
+}
+
+/*===========================================================================*
+ *                            map_service                                   *
+ *===========================================================================*/
+PUBLIC int map_service(rpub)
+struct rprocpub *rpub;
+{
+/* Map a new service by registering a new acl entry if required. */
+       int i;
+
+       /* Stop right now if no pci device or class is found. */
+       if(rpub->pci_acl.rsp_nr_device == 0
+               && rpub->pci_acl.rsp_nr_class == 0) {
+               return(OK);
+       }
+
+       /* Find a free acl slot. */
+       for (i= 0; i<NR_DRIVERS; i++)
+       {
+               if (!pci_acl[i].inuse)
+                       break;
+       }
+       if (i >= NR_DRIVERS)
+       {
+               printf("PCI: map_service: table is full\n");
+               return ENOMEM;
+       }
+
+       /* Initialize acl slot. */
+       pci_acl[i].inuse = 1;
+       pci_acl[i].acl = rpub->pci_acl;
+
+       return(OK);
+}
+
 /*===========================================================================*
  *                     helper functions for I/O                             *
  *===========================================================================*/
@@ -189,34 +259,6 @@ PUBLIC void pci_outl(U16_t port, U32_t value) {
                printf("PCI: warning, sys_outl failed: %d\n", s);
 }
 
-/*===========================================================================*
- *                             pci_init                                     *
- *===========================================================================*/
-PUBLIC void pci_init()
-{
-       static int first_time= 1;
-
-       long v;
-
-       if (!first_time)
-               return;
-
-       v= 0;
-       env_parse("pci_debug", "d", 0, &v, 0, 1);
-       debug= v;
-
-       /* We don't expect to interrupted */
-       assert(first_time == 1);
-       first_time= -1;
-
-       /* Only Intel (compatible) PCI controllers are supported at the
-        * moment.
-        */
-       pci_intel_init();
-
-       first_time= 0;
-}
-
 /*===========================================================================*
  *                             pci_find_dev                                 *
  *===========================================================================*/
index 387aca7d7834f79cfdcff937475d268aaa66b9cd..0f53d0ccfbd342338804c1d5d0e3da79a8f4fd93 100644 (file)
@@ -4,6 +4,8 @@ pci.h
 Created:       Jan 2000 by Philip Homburg <philip@cs.vu.nl>
 */
 
+#include <minix/rs.h>
+
 /* tempory functions: to be replaced later (see pci_intel.h) */
 _PROTOTYPE( unsigned pci_inb, (U16_t port) );
 _PROTOTYPE( unsigned pci_inw, (U16_t port) );
@@ -61,6 +63,14 @@ struct pci_pcibridge
        int type;
 };
 
+struct pci_acl
+{
+       int inuse;
+       struct rs_pci acl;
+};
+
+#define NR_DRIVERS     NR_SYS_PROCS
+
 #define PCI_IB_PIIX    1       /* Intel PIIX compatible ISA bridge */
 #define PCI_IB_VIA     2       /* VIA compatible ISA bridge */
 #define PCI_IB_AMD     3       /* AMD compatible ISA bridge */
@@ -81,7 +91,9 @@ extern struct pci_intel_ctrl pci_intel_ctrl[];
 extern struct pci_isabridge pci_isabridge[];
 extern struct pci_pcibridge pci_pcibridge[];
 
-/* Utility functions */
+/* Function prototypes. */
+_PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info)   );
+_PROTOTYPE( int map_service, (struct rprocpub *rpub)                   );
 _PROTOTYPE( int pci_reserve2, (int devind, endpoint_t proc)            );
 _PROTOTYPE( void pci_release, (endpoint_t proc)                                );
 _PROTOTYPE( int pci_first_dev_a, (struct rs_pci *aclp, int *devindp,
index e61153d5f2bb3adc71e62f52d8aebe28511c1af8..021921f917416f21a9a6ce9aa1c262ed96ac4449 100644 (file)
@@ -117,6 +117,7 @@ FORWARD _PROTOTYPE( void do_signal, (void) );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -129,18 +130,10 @@ PUBLIC void main(void)
 {
 /* Main routine of the printer task. */
   message pr_mess;             /* buffer for all incoming messages */
-  struct sigaction sa;
-  int s;
 
   /* SEF local startup. */
   sef_local_startup();
 
-  /* Install signal handlers. Ask PM to transform signal into message. */
-  sa.sa_handler = SIG_MESS;
-  sigemptyset(&sa.sa_mask);
-  sa.sa_flags = 0;
-  if (sigaction(SIGTERM,&sa,NULL)<0) panic("PRN","sigaction failed", errno);
-  
   while (TRUE) {
        sef_receive(ANY, &pr_mess);
 
@@ -180,6 +173,11 @@ PUBLIC void main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -189,6 +187,23 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the printer driver. */
+  struct sigaction sa;
+
+  /* Install signal handlers. Ask PM to transform signal into message. */
+  sa.sa_handler = SIG_MESS;
+  sigemptyset(&sa.sa_mask);
+  sa.sa_flags = 0;
+  if (sigaction(SIGTERM,&sa,NULL)<0) panic("PRN","sigaction failed", errno);
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                              do_signal                                   *
  *===========================================================================*/
index 97024a80628163336463dbb0362875bd8878350c..bb1d332e39a7e10ab96bd33c4254277b1ce2d6ce 100644 (file)
@@ -26,7 +26,6 @@ FORWARD _PROTOTYPE( struct device *r_prepare, (int device) );
 FORWARD _PROTOTYPE( int r_transfer, (int proc_nr, int opcode, u64_t position,
                                iovec_t *iov, unsigned nr_req) );
 FORWARD _PROTOTYPE( int r_do_open, (struct driver *dp, message *m_ptr) );
-FORWARD _PROTOTYPE( void r_init, (void) );
 FORWARD _PROTOTYPE( int r_ioctl, (struct driver *dp, message *m_ptr) );
 FORWARD _PROTOTYPE( void r_geometry, (struct partition *entry) );
 FORWARD _PROTOTYPE( void r_random, (struct driver *dp, message *m_ptr) );
@@ -56,6 +55,7 @@ PRIVATE char random_buf[RANDOM_BUF_SIZE];
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                                main                                      *
@@ -65,8 +65,9 @@ PUBLIC int main(void)
   /* SEF local startup. */
   sef_local_startup();
 
-  r_init();                            /* initialize the memory driver */
-  driver_task(&r_dtab, DRIVER_ASYN);   /* start driver's main loop */
+  /* Call the generic receive loop. */
+  driver_task(&r_dtab, DRIVER_ASYN);
+
   return(OK);
 }
 
@@ -75,6 +76,11 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -83,6 +89,40 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the random driver. */
+  static struct k_randomness krandom;
+  int i, s;
+
+  random_init();
+  r_random(NULL, NULL);                                /* also set periodic timer */
+
+  /* Retrieve first randomness buffer with parameters. */
+  if (OK != (s=sys_getrandomness(&krandom))) {
+       report("RANDOM", "sys_getrandomness failed", s);
+       exit(1);
+  }
+
+  /* Do sanity check on parameters. */
+  if(krandom.random_sources != RANDOM_SOURCES ||
+     krandom.random_elements != RANDOM_ELEMENTS) {
+     printf("random: parameters (%d, %d) don't match kernel's (%d, %d)\n",
+       RANDOM_SOURCES, RANDOM_ELEMENTS,
+       krandom.random_sources, krandom.random_elements);
+     exit(1);
+  }
+
+  /* Feed initial batch. */
+  for(i = 0; i < RANDOM_SOURCES; i++)
+       r_updatebin(i, &krandom.bin[i]);
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                              r_name                                      *
  *===========================================================================*/
@@ -199,37 +239,6 @@ message *m_ptr;
   return(OK);
 }
 
-/*===========================================================================*
- *                             r_init                                       *
- *===========================================================================*/
-PRIVATE void r_init()
-{
-  static struct k_randomness krandom;
-  int i, s;
-
-  random_init();
-  r_random(NULL, NULL);                                /* also set periodic timer */
-
-  /* Retrieve first randomness buffer with parameters. */
-  if (OK != (s=sys_getrandomness(&krandom))) {
-       report("RANDOM", "sys_getrandomness failed", s);
-       exit(1);
-  }
-
-  /* Do sanity check on parameters. */
-  if(krandom.random_sources != RANDOM_SOURCES ||
-     krandom.random_elements != RANDOM_ELEMENTS) {
-     printf("random: parameters (%d, %d) don't match kernel's (%d, %d)\n",
-       RANDOM_SOURCES, RANDOM_ELEMENTS,
-       krandom.random_sources, krandom.random_elements);
-     exit(1);
-  }
-
-  /* Feed initial batch. */
-  for(i = 0; i < RANDOM_SOURCES; i++)
-       r_updatebin(i, &krandom.bin[i]);
-}
-
 /*===========================================================================*
  *                             r_ioctl                                      *
  *===========================================================================*/
index df5dcbd05c2987bc937d6fcea0da6a9479afaca6..3ae06b63374cdc61bcedc46ea5aa8692e6619842 100644 (file)
@@ -52,6 +52,7 @@
 #include <minix/type.h>
 #include <minix/const.h>
 #include <minix/syslib.h>
+#include <minix/sysutil.h>
 #include <minix/com.h>
 #include <minix/portio.h>
 #include <ibm/cmos.h>
@@ -103,6 +104,7 @@ int main(int argc, char **argv)
   struct sysgetenv sysgetenv;
 
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
   if((s=sys_readbios(MACH_ID_ADDR, &mach_id, sizeof(mach_id))) != OK) {
index d4b91d771a2f13fe5cc411c7a648e73281aee495..e709ea43f81e80016ffe04d44f2596fb1b84e7e7 100644 (file)
@@ -193,52 +193,23 @@ u32_t system_hz;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
- *                             main                                 *
+ *                             main                                         *
  *===========================================================================*/
 int main(int argc, char *argv[])
 {
-       int fkeys, sfkeys;
-       u32_t inet_proc_nr;
-       int i, r;
-       re_t *rep;
-       long v;
+       int r;
 
        /* SEF local startup. */
-       sef_local_startup();
-
-       system_hz = sys_hz();
-
-       (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
        env_setargs(argc, argv);
-
-       v= 0;
-       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
-       eth_ign_proto= htons((u16_t) v);
-
-       /* Observe some function key for debug dumps. */
-       fkeys = sfkeys = 0; bit_set(sfkeys, 9);
-       if ((r=fkey_map(&fkeys, &sfkeys)) != OK) 
-           printf("Warning: RTL8139 couldn't observe Shift+F9 key: %d\n",r);
-
-       /* Claim buffer memory now under Minix, before MM takes it all. */
-       for (rep= &re_table[0]; rep < re_table+RE_PORT_NR; rep++)
-               rl_init_buf(rep);
-
-       /* Try to notify INET that we are present (again). If INET cannot
-        * be found, assume this is the first time we started and INET is
-        * not yet alive.
-        */
-       r= ds_retrieve_u32("inet", &inet_proc_nr);
-       if (r == OK)
-               notify(inet_proc_nr);
-       else if (r != ESRCH)
-               printf("rtl8139: ds_retrieve_u32 failed for 'inet': %d\n", r);
+       sef_local_startup();
 
        while (TRUE)
        {
@@ -317,6 +288,11 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -326,6 +302,49 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the rtl8139 driver. */
+       int fkeys, sfkeys;
+       u32_t inet_proc_nr;
+       int r;
+       re_t *rep;
+       long v;
+
+       system_hz = sys_hz();
+
+       (progname=strrchr(env_argv[0],'/')) ? progname++
+               : (progname=env_argv[0]);
+
+       v= 0;
+       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
+       eth_ign_proto= htons((u16_t) v);
+
+       /* Observe some function key for debug dumps. */
+       fkeys = sfkeys = 0; bit_set(sfkeys, 9);
+       if ((r=fkey_map(&fkeys, &sfkeys)) != OK) 
+           printf("Warning: RTL8139 couldn't observe Shift+F9 key: %d\n",r);
+
+       /* Claim buffer memory now under Minix, before MM takes it all. */
+       for (rep= &re_table[0]; rep < re_table+RE_PORT_NR; rep++)
+               rl_init_buf(rep);
+
+       /* Try to notify INET that we are present (again). If INET cannot
+        * be found, assume this is the first time we started and INET is
+        * not yet alive.
+        */
+       r= ds_retrieve_u32("inet", &inet_proc_nr);
+       if (r == OK)
+               notify(inet_proc_nr);
+       else if (r != ESRCH)
+               printf("rtl8139: ds_retrieve_u32 failed for 'inet': %d\n", r);
+
+       return(OK);
+}
+
 /*===========================================================================*
  *                             check_int_events                             *
  *===========================================================================*/
index e5b46b3a37d21a5177d43b4aecb10b070c7f0bbb..86770128970531a6101b862296ea0e8fd2c7e91c 100644 (file)
@@ -286,46 +286,21 @@ u32_t system_hz;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
 /*===========================================================================*
  *                             main                                         *
  *===========================================================================*/
 int main(int argc, char *argv[])
 {
-       u32_t inet_proc_nr;
        int r;
-       re_t *rep;
-       long v;
 
        /* SEF local startup. */
-       sef_local_startup();
-
-       system_hz = sys_hz();
-
-       (progname = strrchr(argv[0], '/')) ? progname++ : (progname = argv[0]);
-
        env_setargs(argc, argv);
+       sef_local_startup();
 
-       v = 0;
-       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
-       eth_ign_proto = htons((u16_t) v);
-
-       /* Claim buffer memory now under Minix, before MM takes it all. */
-       for (rep = &re_table[0]; rep < re_table + RE_PORT_NR; rep++)
-               rl_init_buf(rep);
-
-       /*
-        * Try to notify INET that we are present (again). If INET cannot
-        * be found, assume this is the first time we started and INET is
-        * not yet alive.
-        */
-#if 0
-       r = ds_retrieve_u32("inet", &inet_proc_nr);
-       if (r == OK)
-               notify(inet_proc_nr);
-       else if (r != ESRCH)
-               printf("rtl8169: ds_retrieve_u32 failed for 'inet': %d\n", r);
-#endif
        while (TRUE) {
                if ((r = sef_receive(ANY, &m)) != OK)
                        panic("rtl8169", "sef_receive failed", r);
@@ -391,12 +366,56 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the rtl8169 driver. */
+       u32_t inet_proc_nr;
+       int r;
+       re_t *rep;
+       long v;
+
+       system_hz = sys_hz();
+
+       (progname = strrchr(env_argv[0], '/')) ? progname++
+               : (progname = env_argv[0]);
+
+       v = 0;
+       (void) env_parse("ETH_IGN_PROTO", "x", 0, &v, 0x0000L, 0xFFFFL);
+       eth_ign_proto = htons((u16_t) v);
+
+       /* Claim buffer memory now under Minix, before MM takes it all. */
+       for (rep = &re_table[0]; rep < re_table + RE_PORT_NR; rep++)
+               rl_init_buf(rep);
+
+       /*
+        * Try to notify INET that we are present (again). If INET cannot
+        * be found, assume this is the first time we started and INET is
+        * not yet alive.
+        */
+#if 0
+       r = ds_retrieve_u32("inet", &inet_proc_nr);
+       if (r == OK)
+               notify(inet_proc_nr);
+       else if (r != ESRCH)
+               printf("rtl8169: ds_retrieve_u32 failed for 'inet': %d\n", r);
+#endif
+
+       return(OK);
+}
+
 static void mdio_write(U16_t port, int regaddr, int value)
 {
        int i;
index 954e056891503f6415365017502399dbd5d2d806..d4ade9fb072948b095e15f0c8a73e429d38c8d66 100644 (file)
@@ -37,7 +37,6 @@ FORWARD _PROTOTYPE( void dsp_hardware_msg, (void) );
 FORWARD _PROTOTYPE( void dsp_status, (message *m_ptr) );
 
 FORWARD _PROTOTYPE( void reply, (int code, int replyee, int process, int status) );
-FORWARD _PROTOTYPE( void init_buffer, (void) );
 FORWARD _PROTOTYPE( int dsp_init, (void) );
 FORWARD _PROTOTYPE( int dsp_reset, (void) );
 FORWARD _PROTOTYPE( int dsp_command, (int value) );
@@ -79,6 +78,7 @@ PRIVATE int reviveProcNr;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 EXTERN _PROTOTYPE( void sef_cb_lu_prepare, (int state) );
 EXTERN _PROTOTYPE( int sef_cb_lu_state_isvalid, (int state) );
 EXTERN _PROTOTYPE( void sef_cb_lu_state_dump, (int state) );
@@ -90,17 +90,12 @@ PUBLIC int is_status_msg_expected = FALSE;
  *===========================================================================*/
 PUBLIC void main() 
 {      
-       int r, caller, proc_nr, s;
+       int r, caller, proc_nr;
        message mess;
 
        /* SEF local startup. */
        sef_local_startup();
 
-       dprint("sb16_dsp.c: main()\n");
-
-       /* Get a DMA buffer. */
-       init_buffer();
-
        while(TRUE) {
                /* Wait for an incoming message */
                sef_receive(ANY, &mess);
@@ -152,6 +147,11 @@ send_reply:
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid);
@@ -161,6 +161,33 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the rtl8169 driver. */
+       unsigned left;
+
+       /* Select a buffer that can safely be used for dma transfers.  
+        * Its absolute address is 'DmaPhys', the normal address is 'DmaPtr'.
+        */
+#if (CHIP == INTEL)
+       DmaPtr = DmaBuffer;
+       sys_umap(SELF, D, (vir_bytes)DmaBuffer, (phys_bytes)sizeof(DmaBuffer), &DmaPhys);
+
+       if((left = dma_bytes_left(DmaPhys)) < DMA_SIZE) {
+               /* First half of buffer crosses a 64K boundary, can't DMA into that */
+               DmaPtr += left;
+               DmaPhys += left;
+       }
+#else /* CHIP != INTEL */
+       panic("SB16DSP","initialization failed, CHIP != INTEL", 0);
+#endif /* CHIP == INTEL */
+
+       return(OK);
+}
+
 /*===========================================================================*
  *                             dsp_open
  *===========================================================================*/
@@ -392,33 +419,6 @@ int status;
        send(replyee, &m);
 }
 
-
-/*===========================================================================*
- *                             init_buffer
- *===========================================================================*/
-PRIVATE void init_buffer()
-{
-/* Select a buffer that can safely be used for dma transfers.  
- * Its absolute address is 'DmaPhys', the normal address is 'DmaPtr'.
- */
-
-#if (CHIP == INTEL)
-       unsigned left;
-
-       DmaPtr = DmaBuffer;
-       sys_umap(SELF, D, (vir_bytes)DmaBuffer, (phys_bytes)sizeof(DmaBuffer), &DmaPhys);
-
-       if((left = dma_bytes_left(DmaPhys)) < DMA_SIZE) {
-               /* First half of buffer crosses a 64K boundary, can't DMA into that */
-               DmaPtr += left;
-               DmaPhys += left;
-       }
-#else /* CHIP != INTEL */
-       panic("SB16DSP","init_buffer() failed, CHIP != INTEL", 0);
-#endif /* CHIP == INTEL */
-}
-
-
 /*===========================================================================*
  *                             dsp_init
  *===========================================================================*/
index 03b698022e595afa787a5551e3c66eec9d91654e..87fbf37e151f696543f2907abac5c63039afa844 100644 (file)
@@ -47,7 +47,7 @@ FORWARD _PROTOTYPE( void sef_local_startup, (void) );
  *                             main
  *===========================================================================*/
 PUBLIC void main() {
-message mess;
+       message mess;
        int err, caller, proc_nr;
 
        /* SEF local startup. */
index dcb29779dd4a886f94cc05752b01a14e2368697a..83e5a8fe818e64675d00bbb3bd4528579a7f70ca 100644 (file)
@@ -51,7 +51,6 @@ PRIVATE struct pcitab pcitab_ti[]=
 PRIVATE char *progname;
 PRIVATE int debug;
 
-FORWARD _PROTOTYPE( void init, (void)                                  );
 FORWARD _PROTOTYPE( void hw_init, (struct port *pp)                    );
 FORWARD _PROTOTYPE( void map_regs, (struct port *pp, u32_t base)       );
 FORWARD _PROTOTYPE( void do_int, (struct port *pp)                     );
@@ -61,33 +60,22 @@ FORWARD _PROTOTYPE( u8_t do_inb, (port_t port)                              );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
+EXTERN int env_argc;
+EXTERN char **env_argv;
 
+/*===========================================================================*
+ *                             main                                         *
+ *===========================================================================*/
 int main(int argc, char *argv[])
 {
-       int c, r;
+       int r;
        message m;
 
        /* SEF local startup. */
+       env_setargs(argc, argv);
        sef_local_startup();
 
-       (progname=strrchr(argv[0],'/')) ? progname++ : (progname=argv[0]);
-
-       if((r=micro_delay_calibrate()) != OK)
-               panic("ti1225", "micro_delay_calibrate failed", r);
-
-       debug= 0;
-       while (c= getopt(argc, argv, "d?"), c != -1)
-       {
-               switch(c)
-               {
-               case '?': panic("ti1225", "Usage: ti1225 [-d]", NO_NUM);
-               case 'd': debug++; break;
-               default: panic("ti1225", "getopt failed", NO_NUM);
-               }
-       }
-
-       init();
-
        for (;;)
        {
                r= sef_receive(ANY, &m);
@@ -104,6 +92,11 @@ int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -112,11 +105,32 @@ PRIVATE void sef_local_startup()
   sef_startup();
 }
 
-PRIVATE void init()
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-       int i, r, first, devind, port;
+/* Initialize the ti1225 driver. */
+       int c, i, r, first, devind, port;
        u16_t vid, did;
 
+       (progname=strrchr(env_argv[0],'/')) ? progname++
+               : (progname=env_argv[0]);
+
+       if((r=micro_delay_calibrate()) != OK)
+               panic("ti1225", "micro_delay_calibrate failed", r);
+
+       debug= 0;
+       while (c= getopt(env_argc, env_argv, "d?"), c != -1)
+       {
+               switch(c)
+               {
+               case '?': panic("ti1225", "Usage: ti1225 [-d]", NO_NUM);
+               case 'd': debug++; break;
+               default: panic("ti1225", "getopt failed", NO_NUM);
+               }
+       }
+
        pci_init1(progname);
 
        first= 1;
@@ -167,6 +181,8 @@ PRIVATE void init()
                        continue;
                hw_init(&ports[i]);
        }
+
+       return(OK);
 }
 
 PRIVATE void hw_init(pp)
index e2445b9771fc3fcbcd42935978be562f47107d42..51f7d378199660765fdea780ae702706bb284dfd 100644 (file)
@@ -149,6 +149,7 @@ extern PUBLIC phys_bytes vid_base;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             tty_task                                     *
@@ -159,23 +160,12 @@ PUBLIC int main(void)
 
   message tty_mess;            /* buffer for all incoming messages */
   unsigned line;
-  int r, s;
+  int r;
   register tty_t *tp;
 
   /* SEF local startup. */
   sef_local_startup();
 
-  /* Get kernel environment (protected_mode, pc_at and ega are needed). */ 
-  if (OK != (s=sys_getmachine(&machine))) {
-    panic("TTY","Couldn't obtain kernel environment.", s);
-  }
-
-  /* Initialize the TTY driver. */
-  tty_init();
-
-  /* Final one-time keyboard initialization. */
-  kb_init_once();
-
   while (TRUE) {
        int adflag = 0;
 
@@ -338,12 +328,38 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the tty driver. */
+  int r;
+
+  /* Get kernel environment (protected_mode, pc_at and ega are needed). */ 
+  if (OK != (r=sys_getmachine(&machine))) {
+    panic("TTY","Couldn't obtain kernel environment.", r);
+  }
+
+  /* Initialize the TTY driver. */
+  tty_init();
+
+  /* Final one-time keyboard initialization. */
+  kb_init_once();
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                             got_signal                                   *
  *===========================================================================*/
index 4cc3bd1994f8e5bff0c96b4091828c7f20932449..318ee380d21595f0a8fe5379eb57ef65aae5fa34 100644 (file)
 #  define SYS_RUNCTL     (KERNEL_CALL + 46)    /* sys_runctl() */
 
 #define NR_SYS_CALLS   47      /* number of system calls */ 
+#define SYS_CALL_MASK_SIZE BITMAP_CHUNKS(NR_SYS_CALLS)
 
 /* Field names for SYS_MEMSET. */
 #define MEM_PTR                m2_p1   /* base */
 
 #define RS_LOOKUP      (RS_RQ_BASE + 8)        /* lookup server name */
 
+#define RS_INIT        (RS_RQ_BASE + 20)       /* service init message */
 #define RS_LU_PREPARE  (RS_RQ_BASE + 21)       /* prepare to update message */
 
 #  define RS_CMD_ADDR          m1_p1           /* command string */
 #  define RS_NAME              m1_p1           /* name */
 #  define RS_NAME_LEN          m1_i1           /* namelen */
 
+#  define RS_INIT_RESULT        m1_i1           /* init result */
+#  define RS_INIT_TYPE          m1_i2           /* init type */
+#  define RS_INIT_RPROCTAB_GID  m1_i3           /* init rproc table gid */
+
 #  define RS_LU_RESULT          m1_i1           /* live update result */
 #  define RS_LU_STATE           m1_i2           /* state required to update */
 #  define RS_LU_PREPARE_MAXTIME m1_i3           /* the max time to prepare */
 #define VCTLP_STATS_EP                 2
 
 /* Total. */
-#define VM_NCALLS                              41
+#define NR_VM_CALLS                            41
+#define VM_CALL_MASK_SIZE                      BITMAP_CHUNKS(NR_VM_CALLS)
+
+/* Basic vm calls allowed to every process. */
+#define VM_BASIC_CALLS \
+    VM_MMAP, VM_MUNMAP, VM_MUNMAP_TEXT, VM_MAP_PHYS, VM_UNMAP_PHYS
 
 /*===========================================================================*
  *                Messages for IPC server                                   *
index 3eed5950db076ebee70fff0814d65f36b96aa6c8..ddea7339e990b07cbedccf977449ab8da76b717d 100644 (file)
@@ -38,6 +38,7 @@
  */
 #define NR_PROCS         _NR_PROCS 
 #define NR_SYS_PROCS      _NR_SYS_PROCS
+#define NR_SYS_CHUNKS    BITMAP_CHUNKS(NR_SYS_PROCS)
 
 /* Number of controller tasks (/dev/cN device classes). */
 #define NR_CTRLRS          2
index c07807dbbe3e9748ec926f1400f8d882416d83b8..ae784485af15604c6b18bd047d4c70f19c9da331 100644 (file)
@@ -8,13 +8,25 @@ Interface to the reincarnation server
 */
 
 #include <minix/bitmap.h>
+#include <minix/com.h>
 
+/* RSS definitions. */
 #define RSS_NR_IRQ             16
 #define RSS_NR_IO              16
-#define RSS_NR_PCI_ID          32
-#define RSS_NR_PCI_CLASS        4
-#define RSS_NR_SYSTEM           2
-#define RSS_NR_CONTROL          8
+
+/* RSS flags. */
+#define RSS_COPY       0x01    /* Copy the brinary into RS to make it possible
+                                * to restart the driver without accessing FS
+                                */
+#define RSS_IPC_VALID  0x02    /* rss_ipc and rss_ipclen are valid */
+#define RSS_REUSE      0x04    /* Try to reuse previously copied binary */
+
+/* Common definitions. */
+#define RS_SYS_CALL_MASK_SIZE   2
+#define RS_NR_CONTROL           8
+#define RS_NR_PCI_DEVICE       32
+#define RS_NR_PCI_CLASS                 4
+#define RS_MAX_LABEL_LEN       16
 
 /* Labels are copied over separately. */
 struct rss_label
@@ -40,38 +52,45 @@ struct rs_start
        int rss_nr_io;
        struct { unsigned base; unsigned len; } rss_io[RSS_NR_IO];
        int rss_nr_pci_id;
-       struct { u16_t vid; u16_t did; } rss_pci_id[RSS_NR_PCI_ID];
+       struct { u16_t vid; u16_t did; } rss_pci_id[RS_NR_PCI_DEVICE];
        int rss_nr_pci_class;
-       struct { u32_t class; u32_t mask; } rss_pci_class[RSS_NR_PCI_CLASS];
-       u32_t rss_system[RSS_NR_SYSTEM];
+       struct { u32_t class; u32_t mask; } rss_pci_class[RS_NR_PCI_CLASS];
+       u32_t rss_system[RS_SYS_CALL_MASK_SIZE];
        struct rss_label rss_label;
        char *rss_ipc;
        size_t rss_ipclen;
-#define RSS_VM_CALL_SIZE BITMAP_CHUNKS(VM_NCALLS)
-       bitchunk_t rss_vm[RSS_VM_CALL_SIZE];
+       bitchunk_t rss_vm[VM_CALL_MASK_SIZE];
        int rss_nr_control;
-       struct rss_label rss_control[RSS_NR_CONTROL];
+       struct rss_label rss_control[RS_NR_CONTROL];
 };
 
-#define RF_COPY                0x01    /* Copy the brinary into RS to make it possible
-                                * to restart the driver without accessing FS
-                                */
-#define RF_IPC_VALID   0x02    /* rss_ipc and rss_ipclen are valid */
-#define RF_REUSE       0x04    /* Try to reuse previously copied binary */
-
-#define RSP_LABEL_SIZE 16
-#define RSP_NR_DEVICE  32
-#define RSP_NR_CLASS    4
-
 /* ACL information for access to PCI devices */
 struct rs_pci
 {
-       char rsp_label[RSP_LABEL_SIZE];         /* Name of the driver */
+       char rsp_label[RS_MAX_LABEL_LEN];
        int rsp_endpoint;
        int rsp_nr_device;
-       struct { u16_t vid; u16_t did; } rsp_device[RSP_NR_DEVICE];
+       struct { u16_t vid; u16_t did; } rsp_device[RS_NR_PCI_DEVICE];
        int rsp_nr_class;
-       struct { u32_t class; u32_t mask; } rsp_class[RSP_NR_CLASS];
+       struct { u32_t class; u32_t mask; } rsp_class[RS_NR_PCI_CLASS];
+};
+
+/* Definition of a public entry of the system process table. */
+struct rprocpub {
+  short in_use;                  /* set when the entry is in use */
+  unsigned sys_flags;            /* sys flags */
+  endpoint_t endpoint;           /* process endpoint number */
+
+  dev_t dev_nr;                          /* major device number */
+  int dev_style;                 /* device style */
+  long period;                   /* heartbeat period (or zero) */
+
+  char label[RS_MAX_LABEL_LEN];          /* label of this service */
+  char proc_name[RS_MAX_LABEL_LEN]; /* process name of this service */
+
+  bitchunk_t vm_call_mask[VM_CALL_MASK_SIZE]; /* vm call mask */
+
+  struct rs_pci pci_acl;         /* pci acl */
 };
 
 _PROTOTYPE( int minix_rs_lookup, (const char *name, endpoint_t *value));
index 26a5734754cdb98312ee49a1f631adb74f2a1162..e2fe145f3955903e171eeee7c562dddf358f7f53 100644 (file)
@@ -13,6 +13,61 @@ _PROTOTYPE( int sef_receive, (endpoint_t src, message *m_ptr) );
 #define sef_debug_begin()               (void)(NULL)
 #define sef_debug_end()                 fflush(stdout)
 
+/*===========================================================================*
+ *                               SEF Init                                   *
+ *===========================================================================*/
+/* What to intercept. */
+#define INTERCEPT_SEF_INIT_REQUESTS 1
+#define IS_SEF_INIT_REQUEST(mp) ((mp)->m_type == RS_INIT \
+    && (mp)->m_source == RS_PROC_NR)
+
+/* Type definitions. */
+typedef struct {
+    int rproctab_gid;
+} sef_init_info_t;
+
+/* Callback type definitions. */
+typedef int(*sef_cb_init_fresh_t)(int type, sef_init_info_t *info);
+typedef int(*sef_cb_init_lu_t)(int type, sef_init_info_t *info);
+typedef int(*sef_cb_init_restart_t)(int type, sef_init_info_t *info);
+
+/* Callback registration helpers. */
+_PROTOTYPE( void sef_setcb_init_fresh, (sef_cb_init_fresh_t cb));
+_PROTOTYPE( void sef_setcb_init_lu, (sef_cb_init_lu_t cb));
+_PROTOTYPE( void sef_setcb_init_restart, (sef_cb_init_restart_t cb));
+
+/* Predefined callback implementations. */
+_PROTOTYPE( int sef_cb_init_fresh_null, (int type, sef_init_info_t *info) );
+_PROTOTYPE( int sef_cb_init_lu_null, (int type, sef_init_info_t *info) );
+_PROTOTYPE( int sef_cb_init_restart_null, (int type, sef_init_info_t *info) );
+
+_PROTOTYPE( int sef_cb_init_restart_fail, (int type, sef_init_info_t *info) );
+
+/* Macros for predefined callback implementations. */
+#define SEF_CB_INIT_FRESH_NULL          sef_cb_init_fresh_null
+#define SEF_CB_INIT_LU_NULL             sef_cb_init_lu_null
+#define SEF_CB_INIT_RESTART_NULL        sef_cb_init_restart_null
+
+#define SEF_CB_INIT_FRESH_DEFAULT       sef_cb_init_fresh_null
+#define SEF_CB_INIT_LU_DEFAULT          sef_cb_init_lu_null
+#define SEF_CB_INIT_RESTART_DEFAULT     sef_cb_init_restart_null
+
+/* Init types. */
+#define SEF_INIT_FRESH                  0    /* init fresh */
+#define SEF_INIT_LU                     1    /* init after live update */
+#define SEF_INIT_RESTART                2    /* init after restart */
+
+/* Debug. */
+#define SEF_INIT_DEBUG_DEFAULT 0
+
+#ifndef SEF_INIT_DEBUG
+#define SEF_INIT_DEBUG                  SEF_INIT_DEBUG_DEFAULT
+#endif
+
+#define sef_init_dprint                 sef_dprint
+#define sef_init_debug_begin            sef_debug_begin
+#define sef_init_debug_end              sef_debug_end
+
 /*===========================================================================*
  *                               SEF Ping                                   *
  *===========================================================================*/
index 18814b544c2a6123b4faa4d69de274b5b5931819..5c25f64fc916fe2d0e1b17adf7ca8c7fde8ef993 100644 (file)
@@ -49,6 +49,7 @@
 #define SI_KPROC_TAB      7    /* copy of kernel process table */
 #define SI_CALL_STATS     8    /* system call statistics */
 #define SI_PCI_INFO       9    /* get kernel info via PM */
+#define SI_PROCPUB_TAB   10    /* copy of public entries of process table */
 
 /* NULL must be defined in <unistd.h> according to POSIX Sec. 2.7.1. */
 #define NULL    ((void *)0)
index 771291241f9d9d5ce4c390abbb6261c24de8ae8a..ef05149af9556131994e7f2311040de37e25e818 100644 (file)
@@ -30,7 +30,6 @@
        ( MAP_CHUNK(map.chunk,bit) |= (1 << CHUNK_OFFSET(bit) )
 #define unset_sys_bit(map,bit) \
        ( MAP_CHUNK(map.chunk,bit) &= ~(1 << CHUNK_OFFSET(bit) )
-#define NR_SYS_CHUNKS  BITMAP_CHUNKS(NR_SYS_PROCS)
 
 #define reallock  do { int d; d = intr_disabled(); intr_disable(); locklevel++; if(d && locklevel == 1) { minix_panic("reallock while interrupts disabled first time", __LINE__); } } while(0)
 
index 94df0738061a69d3afad1041ba95cf682f2a7dbb..8a76110f73617c826243f94a83666f4f6445b725 100644 (file)
@@ -126,7 +126,7 @@ PUBLIC void main()
            }
 
             /* Fill in kernel call mask. */
-            for(j = 0; j < CALL_MASK_SIZE; j++) {
+            for(j = 0; j < SYS_CALL_MASK_SIZE; j++) {
                 priv(rp)->s_k_call_mask[j] = (kcalls == NO_C ? 0 : (~0));
             }
        }
index 12d2d8cffe0c302400d727c458ea61ac222ae10d..d05a22683ed86b32dc7ba5eea9d8f9198642e9da 100644 (file)
@@ -40,8 +40,7 @@ struct priv {
   sys_map_t s_ipc_to;          /* allowed destination processes */
 
   /* allowed kernel calls */
-#define CALL_MASK_SIZE BITMAP_CHUNKS(NR_SYS_CALLS)
-  bitchunk_t s_k_call_mask[CALL_MASK_SIZE];  
+  bitchunk_t s_k_call_mask[SYS_CALL_MASK_SIZE];  
 
   sys_map_t s_notify_pending;          /* bit map with pending notifications */
   irq_id_t s_int_pending;      /* pending hardware interrupts */
index d32ade0dcbbf83602ca150368241d86bb3b2ec64..7081d31906339a54df91f099ac07565afe3a01d4 100644 (file)
@@ -97,7 +97,7 @@ message *m_ptr;                       /* pointer to request message */
        priv(rp)->s_id = priv_id;               /* restore privilege id */
        priv(rp)->s_proc_nr = proc_nr;          /* reassociate process nr */
 
-       for (i=0; i< BITMAP_CHUNKS(NR_SYS_PROCS); i++)  /* remove pending: */
+       for (i=0; i< NR_SYS_CHUNKS; i++)                /* remove pending: */
              priv(rp)->s_notify_pending.chunk[i] = 0;  /* - notifications */
        priv(rp)->s_int_pending = 0;                    /* - interrupts */
        sigemptyset(&priv(rp)->s_sig_pending);          /* - signals */
@@ -107,7 +107,7 @@ message *m_ptr;                     /* pointer to request message */
        priv(rp)->s_trap_mask= DEF_SYS_T;       /* allowed traps */
        ipc_to_m = DEF_SYS_M;                   /* allowed targets */
        kcalls = DEF_SYS_KC;                    /* allowed kernel calls */
-       for(i = 0; i < CALL_MASK_SIZE; i++) {
+       for(i = 0; i < SYS_CALL_MASK_SIZE; i++) {
                priv(rp)->s_k_call_mask[i] = (kcalls == NO_C ? 0 : (~0));
        }
 
index 22eaa0637b174be86779f4f387d738c43baecff0..aa171551fe2f019baf1667d2834f37cf955feeeb 100644 (file)
@@ -113,7 +113,8 @@ endpoint_t *e_granter;              /* new granter (magic grants) */
 
                        /* Verify actual grantee. */
                        if(g.cp_u.cp_indirect.cp_who_to != grantee &&
-                               grantee != ANY) {
+                               grantee != ANY &&
+                               g.cp_u.cp_indirect.cp_who_to != ANY) {
                                kprintf(
                                        "verify_grant: indirect grant verify "
                                        "failed: bad grantee\n");
@@ -147,7 +148,8 @@ endpoint_t *e_granter;              /* new granter (magic grants) */
                }
 
                /* Verify actual grantee. */
-               if(g.cp_u.cp_direct.cp_who_to != grantee && grantee != ANY) {
+               if(g.cp_u.cp_direct.cp_who_to != grantee && grantee != ANY
+                       && g.cp_u.cp_direct.cp_who_to != ANY) {
                        kprintf(
                "verify_grant: direct grant verify failed: bad grantee\n");
                        return EPERM;
@@ -180,7 +182,8 @@ endpoint_t *e_granter;              /* new granter (magic grants) */
                }
 
                /* Verify actual grantee. */
-               if(g.cp_u.cp_magic.cp_who_to != grantee && grantee != ANY) {
+               if(g.cp_u.cp_magic.cp_who_to != grantee && grantee != ANY
+                       && g.cp_u.cp_direct.cp_who_to != ANY) {
                        kprintf(
                "verify_grant: magic grant verify failed: bad grantee\n");
                        return EPERM;
index e09f9513e2206e360276ebe97f6436b12852862e..da20eba465ffdd3942d63867033c0f92cf4caaf0 100644 (file)
@@ -30,6 +30,7 @@ libsys_FILES=" \
        sef.c \
        sef_liveupdate.c \
        sef_ping.c \
+       sef_init.c \
        sys_abort.c \
        sys_cprof.c \
        sys_endsig.c \
index d09a789e5db750425a4f4dd928c7baae373c6ac5..3159f6f09e8a684b0c789c2a620dc4ec018c886d 100644 (file)
@@ -37,6 +37,8 @@
        }                                                       \
    }
 
+#define NR_STATIC_GRANTS 2
+PRIVATE cp_grant_t static_grants[NR_STATIC_GRANTS];
 PRIVATE cp_grant_t *grants = NULL;
 PRIVATE int ngrants = 0;
 
@@ -48,12 +50,19 @@ cpf_grow(void)
        cp_grant_id_t g;
        int new_size;
 
-       new_size = (1+ngrants)*2;
-       assert(new_size > ngrants);
+       if(!ngrants) {
+               /* Use statically allocated grants the first time. */
+               new_size = NR_STATIC_GRANTS;
+               new_grants = static_grants;
+       }
+       else {
+               new_size = (1+ngrants)*2;
+               assert(new_size > ngrants);
 
-       /* Allocate a block of new size. */
-       if(!(new_grants=malloc(new_size * sizeof(grants[0])))) {
-               return;
+               /* Allocate a block of new size. */
+               if(!(new_grants=malloc(new_size * sizeof(grants[0])))) {
+                       return;
+               }
        }
 
        /* Copy old block to new block. */
@@ -66,12 +75,12 @@ cpf_grow(void)
 
        /* Inform kernel about new size (and possibly new location). */
        if((sys_setgrant(new_grants, new_size))) {
-               free(new_grants);
+                if(new_grants != static_grants) free(new_grants);
                return; /* Failed - don't grow then. */
        }
 
        /* Update internal data. */
-       if(grants && ngrants > 0) free(grants);
+       if(grants && ngrants > 0 && grants != static_grants) free(grants);
        grants = new_grants;
        ngrants = new_size;
 }
index 3f1d145d3b9238da7acc95a4adc56053925a23f4..a2536d8d740f434b7de7a7b43eaab6eda4e13b0d 100644 (file)
@@ -18,6 +18,10 @@ PRIVATE char sef_debug_header_buff[SEF_DEBUG_HEADER_MAXLEN];
 FORWARD _PROTOTYPE( void sef_debug_refresh_params, (void) );
 PUBLIC _PROTOTYPE( char* sef_debug_header, (void) );
 
+/* SEF Init prototypes. */
+EXTERN _PROTOTYPE( int do_sef_rs_init, (void) );
+EXTERN _PROTOTYPE( int do_sef_init_request, (message *m_ptr) );
+
 /* SEF Live update prototypes. */
 EXTERN _PROTOTYPE( void do_sef_lu_before_receive, (void) );
 EXTERN _PROTOTYPE( int do_sef_lu_request, (message *m_ptr) );
@@ -39,6 +43,30 @@ PUBLIC void sef_startup()
       sef_self_endpoint = SELF;
       sprintf(sef_self_name, "%s", "Unknown");
   }
+
+#if INTERCEPT_SEF_INIT_REQUESTS
+  /* Intercept SEF Init requests. */
+  if(sef_self_endpoint == RS_PROC_NR) {
+      if((r = do_sef_rs_init()) != OK) {
+          panic("SEF", "unable to complete init", r);
+      }
+  }
+  else {
+      message m;
+
+      if((r = receive(RS_PROC_NR, &m)) != OK) {
+          panic("SEF", "unable to receive from RS", r);
+      }
+      if(IS_SEF_INIT_REQUEST(&m)) {
+          if((r = do_sef_init_request(&m)) != OK) {
+              panic("SEF", "unable to process init request", r);
+          }
+      }
+      else {
+          panic("SEF", "unable to receive init request", NO_NUM);
+      }
+  }
+#endif
 }
 
 /*===========================================================================*
diff --git a/lib/syslib/sef_init.c b/lib/syslib/sef_init.c
new file mode 100644 (file)
index 0000000..a6d8e8d
--- /dev/null
@@ -0,0 +1,137 @@
+#include "syslib.h"
+#include <assert.h>
+#include <minix/sysutil.h>
+
+/* SEF Init callbacks. */
+PRIVATE struct sef_cbs {
+    sef_cb_init_fresh_t                 sef_cb_init_fresh;
+    sef_cb_init_lu_t                    sef_cb_init_lu;
+    sef_cb_init_restart_t               sef_cb_init_restart;
+} sef_cbs = {
+    SEF_CB_INIT_FRESH_DEFAULT,
+    SEF_CB_INIT_LU_DEFAULT,
+    SEF_CB_INIT_RESTART_DEFAULT
+};
+
+/* SEF Init prototypes for sef_startup(). */
+PUBLIC _PROTOTYPE( int do_sef_rs_init, (void) );
+PUBLIC _PROTOTYPE( int do_sef_init_request, (message *m_ptr) );
+
+/* Debug. */
+EXTERN _PROTOTYPE( char* sef_debug_header, (void) );
+
+/*===========================================================================*
+ *                              do_sef_rs_init                              *
+ *===========================================================================*/
+PUBLIC int do_sef_rs_init()
+{
+/* Special SEF Init for RS. */
+  return sef_cbs.sef_cb_init_fresh(SEF_INIT_FRESH, NULL);
+}
+
+/*===========================================================================*
+ *                            do_sef_init_request                           *
+ *===========================================================================*/
+PUBLIC int do_sef_init_request(message *m_ptr)
+{
+/* Handle a SEF Init request. */
+  int r;
+  int type;
+  sef_init_info_t info;
+
+  /* Debug. */
+#if SEF_INIT_DEBUG
+  sef_init_debug_begin();
+  sef_init_dprint("%s. Got a SEF Init request of type: %d. About to init.\n",
+      sef_debug_header(), m_ptr->RS_INIT_TYPE);
+  sef_init_debug_end();
+#endif
+
+  /* Let the callback code handle the request. */
+  type = m_ptr->RS_INIT_TYPE;
+  info.rproctab_gid = m_ptr->RS_INIT_RPROCTAB_GID;
+  switch(type) {
+      case SEF_INIT_FRESH:
+          r = sef_cbs.sef_cb_init_fresh(type, &info);
+      break;
+      case SEF_INIT_LU:
+          r = sef_cbs.sef_cb_init_lu(type, &info);
+      break;
+      case SEF_INIT_RESTART:
+          r = sef_cbs.sef_cb_init_restart(type, &info);
+      break;
+
+      default:
+          /* Not a valid SEF init type. */
+          r = EINVAL;
+      break;
+  }
+
+  /* Report back to RS. XXX FIXME: we should use send, but this would cause
+   * a deadlock due to the current blocking nature of mapdriver().
+   */
+  m_ptr->RS_INIT_RESULT = r;
+  r = asynsend(RS_PROC_NR, m_ptr);
+
+  return r;
+}
+
+/*===========================================================================*
+ *                         sef_setcb_init_fresh                              *
+ *===========================================================================*/
+PUBLIC void sef_setcb_init_fresh(sef_cb_init_fresh_t cb)
+{
+  assert(cb != NULL);
+  sef_cbs.sef_cb_init_fresh = cb;
+}
+
+/*===========================================================================*
+ *                            sef_setcb_init_lu                              *
+ *===========================================================================*/
+PUBLIC void sef_setcb_init_lu(sef_cb_init_lu_t cb)
+{
+  assert(cb != NULL);
+  sef_cbs.sef_cb_init_lu = cb;
+}
+
+/*===========================================================================*
+ *                         sef_setcb_init_restart                            *
+ *===========================================================================*/
+PUBLIC void sef_setcb_init_restart(sef_cb_init_restart_t cb)
+{
+  assert(cb != NULL);
+  sef_cbs.sef_cb_init_restart = cb;
+}
+
+/*===========================================================================*
+ *                         sef_cb_init_fresh_null                           *
+ *===========================================================================*/
+PUBLIC int sef_cb_init_fresh_null(int type, sef_init_info_t *info)
+{
+  return(OK);
+}
+
+/*===========================================================================*
+ *                           sef_cb_init_lu_null                            *
+ *===========================================================================*/
+PUBLIC int sef_cb_init_lu_null(int type, sef_init_info_t *info)
+{
+  return(OK);
+}
+
+/*===========================================================================*
+ *                         sef_cb_init_restart_null                         *
+ *===========================================================================*/
+PUBLIC int sef_cb_init_restart_null(int type, sef_init_info_t *info)
+{
+  return(OK);
+}
+
+/*===========================================================================*
+ *                         sef_cb_init_restart_fail                         *
+ *===========================================================================*/
+PUBLIC int sef_cb_init_restart_fail(int type, sef_init_info_t *info)
+{
+  return(ENOSYS);
+}
+
index c69cdf52c35eda863f67e58ac523d6718098b7b3..a67694956a8c133691a5abc6cef13cee43450363 100644 (file)
@@ -2,8 +2,8 @@
 #include <minix/config.h>
 #include <string.h>
 
-PRIVATE int argc = 0;
-PRIVATE char **argv = NULL;
+PUBLIC int env_argc = 0;
+PUBLIC char **env_argv = NULL;
 
 FORWARD _PROTOTYPE( char *find_key, (const char *params, const char *key));
 
@@ -14,8 +14,8 @@ PUBLIC void env_setargs(arg_c, arg_v)
 int arg_c;
 char *arg_v[];
 {
-       argc= arg_c;
-       argv= arg_v;
+       env_argc= arg_c;
+       env_argv= arg_v;
 }
 
 /*===========================================================================*
@@ -35,15 +35,15 @@ int max_len;                                /* maximum length of value */
        return EINVAL;
 
   keylen= strlen(key);
-  for (i= 1; i<argc; i++)
+  for (i= 1; i<env_argc; i++)
   {
-       if (strncmp(argv[i], key, keylen) != 0)
+       if (strncmp(env_argv[i], key, keylen) != 0)
                continue;
-       if (strlen(argv[i]) <= keylen)
+       if (strlen(env_argv[i]) <= keylen)
                continue;
-       if (argv[i][keylen] != '=')
+       if (env_argv[i][keylen] != '=')
                continue;
-       key_value= argv[i]+keylen+1;
+       key_value= env_argv[i]+keylen+1;
        if (strlen(key_value)+1 > max_len)
              return(E2BIG);
        strcpy(value, key_value);
index 76c97455e0bbaf17601b02f1538bd7bfa93058f4..9aef23a354dfdfdbdae451417332045da4eca925 100644 (file)
@@ -17,6 +17,7 @@
 #include <minix/sysutil.h>
 #include <minix/keymap.h>
 #include <minix/bitmap.h>
+#include <minix/rs.h>
 
 #include <stdlib.h>
 #include <stdio.h>
index 978da669b53d9a6e13f33ba66e4629b53d0a60f5..6dcacd1d891f5f8b814d1566d32b96acc8ed9cc8 100644 (file)
@@ -19,7 +19,6 @@ int sys_panic;                /* flag to indicate system-wide panic */
 extern int errno;      /* error number set by system library */
 
 /* Declare some local functions. */
-FORWARD _PROTOTYPE(void init_server, (int argc, char **argv)           );
 FORWARD _PROTOTYPE(void exit_server, (void)                            );
 FORWARD _PROTOTYPE(void sig_handler, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (message *m_ptr)                     );
@@ -42,11 +41,9 @@ PUBLIC int main(int argc, char **argv)
   sigset_t sigset;
 
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server(argc, argv);
-
   /* Main loop - get work and do it, forever. */         
   while (TRUE) {              
 
@@ -104,25 +101,16 @@ send_reply:
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
-/*===========================================================================*
- *                              init_server                                 *
- *===========================================================================*/
-PRIVATE void init_server(int argc, char **argv)
-{
-/* Initialize the data store server. */
-  int i, s;
-  struct sigaction sigact;
-
-  /* Initialize DS. */
-  ds_init();
-}
-
 /*===========================================================================*
  *                              sig_handler                                 *
  *===========================================================================*/
index e5d1435de9cbbdb7369dba22fb2cf91b266b4411..6844e976f1a076080e910754b9f8d3d5bd25feb8 100644 (file)
@@ -9,4 +9,6 @@ _PROTOTYPE(int do_retrieve, (message *m_ptr));
 _PROTOTYPE(int do_subscribe, (message *m_ptr));
 _PROTOTYPE(int do_check, (message *m_ptr));
 _PROTOTYPE(int do_getsysinfo, (message *m_ptr));
-_PROTOTYPE(void ds_init, (void));
+_PROTOTYPE(int sef_cb_init_fresh, (int type, sef_init_info_t *info));
+_PROTOTYPE(int map_service, (struct rprocpub *rpub));
+
index 86018ee264e9f766f58b2227e8f55188d555d86d..6fc06f3aeb26c3363698b59e2e7b2f4bf7b5e046 100644 (file)
@@ -14,14 +14,15 @@ PRIVATE _PROTOTYPE(void check_subscribers, (struct data_store *dsp));
 
 
 /*===========================================================================*
- *                             ds_init                                      *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PUBLIC void ds_init(void)
+PUBLIC int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-       int i;
+/* Initialize the data store server. */
+       int i, r;
+       struct rprocpub rprocpub[NR_BOOT_PROCS];
 
        /* Reset data store: data and subscriptions. */
-
        for(i = 0; i < NR_DS_KEYS; i++) {
                int b;
                ds_store[i].ds_flags = 0;
@@ -32,7 +33,42 @@ PUBLIC void ds_init(void)
        for(i = 0; i < NR_DS_SUBS; i++)
                ds_subs[i].sub_flags = 0;
 
-       return;
+       /* Map all the services in the boot image. */
+       if((r = sys_safecopyfrom(RS_PROC_NR, info->rproctab_gid, 0,
+               (vir_bytes) rprocpub, sizeof(rprocpub), S)) != OK) {
+               panic("DS", "sys_safecopyfrom failed", r);
+       }
+       for(i=0;i < NR_BOOT_PROCS;i++) {
+               if(rprocpub[i].in_use) {
+                       if((r = map_service(&rprocpub[i])) != OK) {
+                               panic("DS", "unable to map service", r);
+                       }
+               }
+       }
+
+       return(OK);
+}
+
+/*===========================================================================*
+ *                            map_service                                   *
+ *===========================================================================*/
+PUBLIC int map_service(rpub)
+struct rprocpub *rpub;
+{
+/* Map a new service by registering its label. */
+  struct data_store *dsp;
+
+  dsp = &ds_store[nr_in_use];                  /* new slot found */
+  strcpy(dsp->ds_key, rpub->label);
+  dsp->ds_flags = DS_IN_USE | DS_TYPE_U32;     /* initialize slot */
+  nr_in_use++;
+
+  dsp->ds_val.ds_val_u32 = (u32_t) rpub->endpoint;     /* store data */
+
+  /* If anyone has a matching subscription, update them. */
+  check_subscribers(dsp);
+
+  return(OK);
 }
 
 PRIVATE int set_owner(dsp, auth)
index c82050f67a1bcade687e6495f0cd9b11ae04ea89..d833f695939be15027ffd89c57db701aba602e2a 100644 (file)
@@ -95,98 +95,17 @@ FORWARD _PROTOTYPE( void nw_init, (void) );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 PUBLIC void main()
 {
        mq_t *mq;
        int r;
-       int source, m_type, timerand, fd;
-       u32_t tasknr;
-       struct fssignon device;
-       u8_t randbits[32];
-       struct timeval tv;
+       int source, m_type;
 
        /* SEF local startup. */
        sef_local_startup();
 
-#if DEBUG
-       printf("Starting inet...\n");
-       printf("%s\n", version);
-#endif
-
-#if HZ_DYNAMIC
-       system_hz = sys_hz();
-#endif
-
-       /* Read configuration. */
-       nw_conf();
-
-       /* Get a random number */
-       timerand= 1;
-       fd= open(RANDOM_DEV_NAME, O_RDONLY | O_NONBLOCK);
-       if (fd != -1)
-       {
-               r= read(fd, randbits, sizeof(randbits));
-               if (r == sizeof(randbits))
-                       timerand= 0;
-               else
-               {
-                       printf("inet: unable to read random data from %s: %s\n",
-                               RANDOM_DEV_NAME, r == -1 ? strerror(errno) :
-                               r == 0 ? "EOF" : "not enough data");
-               }
-               close(fd);
-       }
-       else
-       {
-               printf("inet: unable to open random device %s: %s\n",
-                       RANDOM_DEV_NAME, strerror(errno));
-       }
-       if (timerand)
-       {
-               printf("inet: using current time for random-number seed\n");
-               r= gettimeofday(&tv, NULL);
-               if (r == -1)
-               {
-                       printf("sysutime failed: %s\n", strerror(errno));
-                       exit(1);
-               }
-               memcpy(randbits, &tv, sizeof(tv));
-       }
-       init_rand256(randbits);
-
-       /* Our new identity as a server. */
-       r= ds_retrieve_u32("inet", &tasknr);
-       if (r != OK)
-               ip_panic(("inet: ds_retrieve_u32 failed for 'inet': %d", r));
-       this_proc= tasknr;
-
-       /* Register the device group. */
-       device.dev= ip_dev;
-       device.style= STYLE_CLONE;
-       if (svrctl(FSSIGNON, (void *) &device) == -1) {
-               printf("inet: error %d on registering ethernet devices\n",
-                       errno);
-               pause();
-       }
-
-#ifdef BUF_CONSISTENCY_CHECK
-       inet_buf_debug= (getenv("inetbufdebug") && 
-               (strcmp(getenv("inetbufdebug"), "on") == 0));
-       inet_buf_debug= 100;
-       if (inet_buf_debug)
-       {
-               ip_warning(( "buffer consistency check enabled" ));
-       }
-#endif
-
-       if (getenv("killerinet"))
-       {
-               ip_warning(( "killer inet active" ));
-               killer_inet= 1;
-       }
-
-       nw_init();
        while (TRUE)
        {
 #ifdef BUF_CONSISTENCY_CHECK
@@ -269,12 +188,111 @@ PUBLIC void main()
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the inet server. */
+       int r;
+       int timerand, fd;
+       u32_t tasknr;
+       struct fssignon device;
+       u8_t randbits[32];
+       struct timeval tv;
+
+#if DEBUG
+       printf("Starting inet...\n");
+       printf("%s\n", version);
+#endif
+
+#if HZ_DYNAMIC
+       system_hz = sys_hz();
+#endif
+
+       /* Read configuration. */
+       nw_conf();
+
+       /* Get a random number */
+       timerand= 1;
+       fd= open(RANDOM_DEV_NAME, O_RDONLY | O_NONBLOCK);
+       if (fd != -1)
+       {
+               r= read(fd, randbits, sizeof(randbits));
+               if (r == sizeof(randbits))
+                       timerand= 0;
+               else
+               {
+                       printf("inet: unable to read random data from %s: %s\n",
+                               RANDOM_DEV_NAME, r == -1 ? strerror(errno) :
+                               r == 0 ? "EOF" : "not enough data");
+               }
+               close(fd);
+       }
+       else
+       {
+               printf("inet: unable to open random device %s: %s\n",
+                       RANDOM_DEV_NAME, strerror(errno));
+       }
+       if (timerand)
+       {
+               printf("inet: using current time for random-number seed\n");
+               r= gettimeofday(&tv, NULL);
+               if (r == -1)
+               {
+                       printf("sysutime failed: %s\n", strerror(errno));
+                       exit(1);
+               }
+               memcpy(randbits, &tv, sizeof(tv));
+       }
+       init_rand256(randbits);
+
+       /* Our new identity as a server. */
+       r= ds_retrieve_u32("inet", &tasknr);
+       if (r != OK)
+               ip_panic(("inet: ds_retrieve_u32 failed for 'inet': %d", r));
+       this_proc= tasknr;
+
+       /* Register the device group. */
+       device.dev= ip_dev;
+       device.style= STYLE_CLONE;
+       if (svrctl(FSSIGNON, (void *) &device) == -1) {
+               printf("inet: error %d on registering ethernet devices\n",
+                       errno);
+               pause();
+       }
+
+#ifdef BUF_CONSISTENCY_CHECK
+       inet_buf_debug= (getenv("inetbufdebug") && 
+               (strcmp(getenv("inetbufdebug"), "on") == 0));
+       inet_buf_debug= 100;
+       if (inet_buf_debug)
+       {
+               ip_warning(( "buffer consistency check enabled" ));
+       }
+#endif
+
+       if (getenv("killerinet"))
+       {
+               ip_warning(( "killer inet active" ));
+               killer_inet= 1;
+       }
+
+       nw_init();
+
+       return(OK);
+}
+
 PRIVATE void nw_conf()
 {
        read_conf();
index 2310a245c79080557b2cc3ea550a8c86e1a5d50c..d5f4c02a53853d4afb9c4221072b94f46395bafd 100644 (file)
@@ -25,19 +25,16 @@ int verbose = 0;
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 PUBLIC int main(int argc, char *argv[])
 {
        message m;
 
        /* SEF local startup. */
+       env_setargs(argc, argv);
        sef_local_startup();
 
-       SELF_E = getprocnr();
-
-       if(verbose)
-               printf("IPC: self: %d\n", SELF_E);
-
        while (TRUE) {
                int r;
                int i;
@@ -111,9 +108,28 @@ PUBLIC int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                         sef_cb_init_fresh                                *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the ipc server. */
+
+  SELF_E = getprocnr();
+
+  if(verbose)
+      printf("IPC: self: %d\n", SELF_E);
+
+  return(OK);
+}
+
index 709ffbd462790a11312df200e6eb03133fdb9638..eb1d1925fc3e943c05db4c6f68a58b2f740e2310 100644 (file)
@@ -14,6 +14,7 @@
 #include "../rs/const.h"
 #include "../rs/type.h"
 
+PUBLIC struct rprocpub rprocpub[NR_SYS_PROCS];
 PUBLIC struct rproc rproc[NR_SYS_PROCS];
 
 FORWARD _PROTOTYPE( char *s_flags_str, (int flags)             );
@@ -24,21 +25,24 @@ FORWARD _PROTOTYPE( char *s_flags_str, (int flags)          );
 PUBLIC void rproc_dmp()
 {
   struct rproc *rp;
+  struct rprocpub *rpub;
   int i,j, n=0;
   static int prev_i=0;
 
+  getsysinfo(RS_PROC_NR, SI_PROCPUB_TAB, rprocpub);
   getsysinfo(RS_PROC_NR, SI_PROC_TAB, rproc);
 
   printf("Reincarnation Server (RS) system process table dump\n");
   printf("----label---- endpoint- -pid- flags -dev- -T- alive_tm starts command\n");
   for (i=prev_i; i<NR_SYS_PROCS; i++) {
        rp = &rproc[i];
+       rpub = &rprocpub[i];
        if (! rp->r_flags & RS_IN_USE) continue;
        if (++n > 22) break;
        printf("%13s %9d %5d %5s %3d/%1d %3u %8u %5dx %s",
-               rp->r_label, rp->r_proc_nr_e, rp->r_pid,
-               s_flags_str(rp->r_flags), rp->r_dev_nr, rp->r_dev_style,
-               rp->r_period, rp->r_alive_tm, rp->r_restarts,
+               rpub->label, rpub->endpoint, rp->r_pid,
+               s_flags_str(rp->r_flags), rpub->dev_nr, rpub->dev_style,
+               rpub->period, rp->r_alive_tm, rp->r_restarts,
                rp->r_cmd
        );
        printf("\n");
@@ -53,10 +57,10 @@ PRIVATE char *s_flags_str(int flags)
 {
        static char str[10];
        str[0] = (flags & RS_IN_USE)        ? 'U' : '-';
-       str[1] = (flags & RS_EXITING)       ? 'E' : '-';
-       str[2] = (flags & RS_REFRESHING)    ? 'R' : '-';
-       str[3] = (flags & RS_NOPINGREPLY)   ? 'N' : '-';
-       str[4] = (flags & RS_UPDATING)      ? 'u' : '-';
+       str[1] = (flags & RS_INITIALIZING)  ? 'I' : '-';
+       str[2] = (flags & RS_UPDATING)      ? 'u' : '-';
+       str[3] = (flags & RS_EXITING)       ? 'E' : '-';
+       str[4] = (flags & RS_NOPINGREPLY)   ? 'N' : '-';
        str[5] = '\0';
 
        return(str);
index c2e88ab00fb30b2a991bde8c869d16370a65458d..b1117381cfc093add64a8efaefd6243df2686151 100644 (file)
@@ -19,13 +19,13 @@ int callnr;         /* system call number */
 extern int errno;      /* error number set by system library */
 
 /* Declare some local functions. */
-FORWARD _PROTOTYPE(void init_server, (int argc, char **argv)           );
 FORWARD _PROTOTYPE(void sig_handler, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (void)                               );
 FORWARD _PROTOTYPE(void reply, (int whom, int result)                  );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -40,11 +40,9 @@ PUBLIC int main(int argc, char **argv)
   sigset_t sigset;
 
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server(argc, argv);
-
   /* Main loop - get work and do it, forever. */         
   while (TRUE) {              
       /* Wait for incoming message, sets 'callnr' and 'who'. */
@@ -87,6 +85,11 @@ PUBLIC int main(int argc, char **argv)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_lu(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_fresh);
+
   /* Register live update callbacks. */
   sef_setcb_lu_prepare(sef_cb_lu_prepare_always_ready);
   sef_setcb_lu_state_isvalid(sef_cb_lu_state_isvalid_standard);
@@ -96,11 +99,11 @@ PRIVATE void sef_local_startup()
 }
 
 /*===========================================================================*
- *                              init_server                                 *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void init_server(int argc, char **argv)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-/* Initialize the information service. */
+/* Initialize the information server. */
   struct sigaction sigact;
 
   /* Install signal handler. Ask PM to transform signal into message. */
@@ -112,6 +115,8 @@ PRIVATE void init_server(int argc, char **argv)
 
   /* Set key mappings. */
   map_unmap_fkeys(TRUE /*map*/);
+
+  return(OK);
 }
 
 /*===========================================================================*
index 6bff616d764732941057fcfd9c8a8ddca7721ae3..a2e84f8b51dbb5ffa691bc273b7ecce1d31df937 100644 (file)
@@ -9,11 +9,11 @@
 #include "glo.h"
 
 /* Declare some local functions. */
-FORWARD _PROTOTYPE(void init_server, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (message *m_in)                      );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -25,16 +25,6 @@ PUBLIC int main(void) {
   /* SEF local startup. */
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server();
-
-  fs_m_in.m_type = FS_READY;
-  
-  if (send(FS_PROC_NR, &fs_m_in) != OK) {
-      printf("ISOFS (%d): Error sending login to VFS\n", SELF_E);
-      return -1;
-  }
-
   for (;;) {
 
        /* Wait for request message. */
@@ -76,6 +66,10 @@ PUBLIC int main(void) {
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
@@ -83,11 +77,12 @@ PRIVATE void sef_local_startup()
 }
 
 /*===========================================================================*
- *                             init_server                                  *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void init_server(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-   int i;
+/* Initialize the iso9660fs server. */
+   int i, r;
 
    /* Init driver mapping */
    for (i = 0; i < NR_DEVICES; ++i) 
@@ -96,6 +91,14 @@ PRIVATE void init_server(void)
    SELF_E = getprocnr();
 /*    hash_init(); */                  /* Init the table with the ids */
    setenv("TZ","",1);          /* Used to calculate the time */
+
+   fs_m_in.m_type = FS_READY;
+
+   if ((r = send(FS_PROC_NR, &fs_m_in)) != OK) {
+       panic("ISOFS", "Error sending login to VFS", r);
+   }
+
+   return(OK);
 }
 
 /*===========================================================================*
index d946b4d03d0683ef6f6d5ae3dfb37aba6e310928..a4bee343a0db838e7a4eafc98649e2fc3a2e4c85 100644 (file)
 
 
 /* Declare some local functions. */
-FORWARD _PROTOTYPE(void init_server, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (message *m_in)                      );
 FORWARD _PROTOTYPE(void cch_check, (void)                              );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -30,18 +30,9 @@ PUBLIC int main(int argc, char *argv[])
   message m;
 
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server();       
-
-  fs_m_in.m_type = FS_READY;
-
-  if (send(FS_PROC_NR, &fs_m_in) != OK) {
-       printf("MFS(%d): Error sending login to VFS\n", SELF_E);
-       return(-1);
-  }
-
   while(!unmountdone || !exitsignaled) {
        endpoint_t src;
 
@@ -94,6 +85,10 @@ PUBLIC int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
@@ -101,11 +96,12 @@ PRIVATE void sef_local_startup()
 }
 
 /*===========================================================================*
- *                             init_server                                  *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void init_server(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
-  int i;
+/* Initialize the Minix file server. */
+  int i, r;
 
   /* Init inode table */
   for (i = 0; i < NR_INODES; ++i) {
@@ -122,6 +118,14 @@ PRIVATE void init_server(void)
   SELF_E = getprocnr();
   buf_pool();
   fs_block_size = _MIN_BLOCK_SIZE;
+
+  fs_m_in.m_type = FS_READY;
+
+  if ((r = send(FS_PROC_NR, &fs_m_in)) != OK) {
+       panic("MFS", "Error sending login to VFS", r);
+  }
+
+  return(OK);
 }
 
 
index f030a3f13e9e85d1439db117d13ca75d2aebbe5a..4a9a58dc87bcbae7e620bed5c1a8f3b395090bc7 100644 (file)
@@ -52,7 +52,7 @@ PUBLIC int fs_readsuper()
   r = ds_retrieve_u32(fs_dev_label, &tasknr);
   if (r != OK) {
        printf("%s:%d fs_readsuper: ds_retrieve_u32 failed for '%s': %d\n",
-              fs_dev_label, __FILE__, __LINE__, r);
+              __FILE__, __LINE__, fs_dev_label, r);
        return(EINVAL);
   }
 
index f386b07979ff8bbf55a55874ff16959842027c5b..d52a506fad29ff0ce5a1453125004b0467698e2b 100644 (file)
@@ -7,11 +7,11 @@
 #include "inode.h"
 #include "drivers.h"
 
-FORWARD _PROTOTYPE(void init_server, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (message *m_in)                      );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -26,11 +26,9 @@ PUBLIC int main(int argc, char *argv[])
   message m;
 
   /* SEF local startup. */
+  env_setargs(argc, argv);
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server();       
-
   while(!exitsignaled || busy) {
        endpoint_t src;
 
@@ -71,6 +69,10 @@ PUBLIC int main(int argc, char *argv[])
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
@@ -78,10 +80,11 @@ PRIVATE void sef_local_startup()
 }
 
 /*===========================================================================*
- *                             init_server                                  *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void init_server(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
+/* Initialize the pipe file server. */
   int i;
 
   /* Initialize main loop parameters. */
@@ -102,6 +105,8 @@ PRIVATE void init_server(void)
        
   SELF_E = getprocnr();
   buf_pool();
+
+  return(OK);
 }
 
 
index 6967536ea36df00b13d805fe59c81b2d92d8ef33..ede2edcb23566f15eba5ee09601ec0c67499e040 100644 (file)
@@ -41,15 +41,17 @@ EXTERN unsigned long calls_stats[NCALLS];
 #endif
 
 FORWARD _PROTOTYPE( void get_work, (void)                              );
-FORWARD _PROTOTYPE( void pm_init, (void)                               );
 FORWARD _PROTOTYPE( int get_nice_value, (int queue)                    );
 FORWARD _PROTOTYPE( void handle_fs_reply, (void)                       );
 
 #define click_to_round_k(n) \
        ((unsigned) ((((unsigned long) (n) << CLICK_SHIFT) + 512) / 1024))
 
+extern int unmap_ok;
+
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -64,8 +66,6 @@ PUBLIC int main()
   /* SEF local startup. */
   sef_local_startup();
 
-  pm_init();                   /* initialize process manager tables */
-
   /* This is PM's main loop-  get work and do it, forever and forever. */
   while (TRUE) {
        get_work();             /* wait for an PM system call */
@@ -166,6 +166,10 @@ send_reply:
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
@@ -173,55 +177,9 @@ PRIVATE void sef_local_startup()
 }
 
 /*===========================================================================*
- *                             get_work                                     *
- *===========================================================================*/
-PRIVATE void get_work()
-{
-/* Wait for the next message and extract useful information from it. */
-  if (sef_receive(ANY, &m_in) != OK)
-       panic(__FILE__,"PM sef_receive error", NO_NUM);
-  who_e = m_in.m_source;       /* who sent the message */
-  if(pm_isokendpt(who_e, &who_p) != OK)
-       panic(__FILE__, "PM got message from invalid endpoint", who_e);
-  call_nr = m_in.m_type;       /* system call number */
-
-  /* Process slot of caller. Misuse PM's own process slot if the kernel is
-   * calling. This can happen in case of synchronous alarms (CLOCK) or or 
-   * event like pending kernel signals (SYSTEM).
-   */
-  mp = &mproc[who_p < 0 ? PM_PROC_NR : who_p];
-  if(who_p >= 0 && mp->mp_endpoint != who_e) {
-       panic(__FILE__, "PM endpoint number out of sync with source",
-               mp->mp_endpoint);
-  }
-}
-
-/*===========================================================================*
- *                             setreply                                     *
- *===========================================================================*/
-PUBLIC void setreply(proc_nr, result)
-int proc_nr;                   /* process to reply to */
-int result;                    /* result of call (usually OK or error #) */
-{
-/* Fill in a reply message to be sent later to a user process.  System calls
- * may occasionally fill in other fields, this is only for the main return
- * value, and for setting the "must send reply" flag.
- */
-  register struct mproc *rmp = &mproc[proc_nr];
-
-  if(proc_nr < 0 || proc_nr >= NR_PROCS)
-      panic(__FILE__,"setreply arg out of range", proc_nr);
-
-  rmp->mp_reply.reply_res = result;
-  rmp->mp_flags |= REPLY;      /* reply pending */
-}
-
-extern int unmap_ok;
-
-/*===========================================================================*
- *                             pm_init                                      *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void pm_init()
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
 /* Initialize the process manager. 
  * Memory use info is collected from the boot monitor, the kernel, and
@@ -351,6 +309,52 @@ PRIVATE void pm_init()
   */
   unmap_ok = 1;
   _minix_unmapzero();
+
+  return(OK);
+}
+
+/*===========================================================================*
+ *                             get_work                                     *
+ *===========================================================================*/
+PRIVATE void get_work()
+{
+/* Wait for the next message and extract useful information from it. */
+  if (sef_receive(ANY, &m_in) != OK)
+       panic(__FILE__,"PM sef_receive error", NO_NUM);
+  who_e = m_in.m_source;       /* who sent the message */
+  if(pm_isokendpt(who_e, &who_p) != OK)
+       panic(__FILE__, "PM got message from invalid endpoint", who_e);
+  call_nr = m_in.m_type;       /* system call number */
+
+  /* Process slot of caller. Misuse PM's own process slot if the kernel is
+   * calling. This can happen in case of synchronous alarms (CLOCK) or or 
+   * event like pending kernel signals (SYSTEM).
+   */
+  mp = &mproc[who_p < 0 ? PM_PROC_NR : who_p];
+  if(who_p >= 0 && mp->mp_endpoint != who_e) {
+       panic(__FILE__, "PM endpoint number out of sync with source",
+               mp->mp_endpoint);
+  }
+}
+
+/*===========================================================================*
+ *                             setreply                                     *
+ *===========================================================================*/
+PUBLIC void setreply(proc_nr, result)
+int proc_nr;                   /* process to reply to */
+int result;                    /* result of call (usually OK or error #) */
+{
+/* Fill in a reply message to be sent later to a user process.  System calls
+ * may occasionally fill in other fields, this is only for the main return
+ * value, and for setting the "must send reply" flag.
+ */
+  register struct mproc *rmp = &mproc[proc_nr];
+
+  if(proc_nr < 0 || proc_nr >= NR_PROCS)
+      panic(__FILE__,"setreply arg out of range", proc_nr);
+
+  rmp->mp_reply.reply_res = result;
+  rmp->mp_flags |= REPLY;      /* reply pending */
 }
 
 /*===========================================================================*
index a9ce99c66f175487b6ff78e0b7ee687d1f1e1cd6..c060553b4a51620c37a42a17b13deccde36222e7 100644 (file)
@@ -5,16 +5,12 @@
 
 /* Space reserved for program and arguments. */
 #define MAX_COMMAND_LEN     512         /* maximum argument string length */
-#define MAX_LABEL_LEN        16         /* Unique name of (this instance of)
-                                         * the service
-                                         */
 #define MAX_SCRIPT_LEN      256         /* maximum restart script name length */
 #define MAX_NR_ARGS           4         /* maximum number of arguments */
 
 #define MAX_IPC_LIST        256         /* Max size of list for IPC target
                                          * process names
                                          */
-#define MAX_VM_LIST         256
 
 /* Flag values. */
 #define RS_IN_USE       0x001    /* set when process slot is in use */
 #define RS_CRASHED      0x040    /* service crashed */
 #define RS_LATEREPLY    0x080    /* no reply sent to RS_DOWN caller yet */
 #define RS_SIGNALED     0x100    /* service crashed */
-#define RS_UPDATING     0x200    /* set when update must be done */
+#define RS_INITIALIZING 0x200    /* set when init is in progress */
+#define RS_UPDATING     0x400    /* set when update is in progress */
 
 /* Sys flag values. */
-#define SF_CORE_PROC    0x001    /* set for core system processes
+#define SF_CORE_SRV     0x001    /* set for core system services
                                   * XXX FIXME: This should trigger a system
-                                  * panic when a CORE_PROC service cannot
+                                  * panic when a CORE_SRV service cannot
                                   * be restarted. We need better error-handling
                                   * in RS to change this.
                                   */
+#define SF_SYNCH_BOOT   0X002    /* set when process needs synch boot init */
 #define SF_NEED_COPY    0x004    /* set when process needs copy to restart */
 #define SF_USE_COPY     0x008    /* set when process has a copy in memory */
 
 /* Constants determining RS period and binary exponential backoff. */
+#define RS_INIT_T       600                     /* allow T ticks for init */
 #define RS_DELTA_T       60                     /* check every T ticks */
 #define BACKOFF_BITS    (sizeof(long)*8)        /* bits in backoff field */
 #define MAX_BACKOFF      30                     /* max backoff in RS_DELTA_T */
@@ -55,8 +54,8 @@
 /* Definitions for boot info tables. */
 #define NULL_BOOT_NR    NR_BOOT_PROCS        /* marks a null boot entry */
 #define DEFAULT_BOOT_NR NR_BOOT_PROCS        /* marks the default boot entry */
-#define SYS_ALL_C       (NR_SYS_CALLS+0)     /* specifies all calls */
-#define SYS_NULL_C      (NR_SYS_CALLS+1)     /* marks a null call entry */
+#define SYS_ALL_C       (-1)                 /* specifies all calls */
+#define SYS_NULL_C      (-2)                 /* marks a null call entry */
 
 /* Define privilege flags for the various process types. */
 #define SRV_F  (SYS_PROC | PREEMPTIBLE)            /* system services */
     | spi_to(VM_PROC_NR) )                         /* root user proc */
 
 /* Define sys flags for the various process types. */
-#define SRV_SF   (SF_CORE_PROC | SF_NEED_COPY) /* system services */
+#define SRV_SF   (SF_CORE_SRV | SF_NEED_COPY)  /* system services */
 #define SRVC_SF  (SRV_SF | SF_USE_COPY)        /* system services with a copy */
 #define DSRV_SF  (0)                           /* dynamic system services */
+#define VM_SF    (SRV_SF | SF_SYNCH_BOOT)      /* vm */
 
 #endif /* RS_CONST_H */
 
index 9d9f4dd8aa6a896fdbeeb7c086a4828efcbdfafe..c2eb506f1e9e47b32a58b8ebdcc7c0f484f386ff 100644 (file)
@@ -27,6 +27,7 @@ extern struct boot_image_dev boot_image_dev_table[];
  * services (servers and drivers), and thus is not directly indexed by
  * slot number.
  */
+EXTERN struct rprocpub rprocpub[NR_SYS_PROCS];  /* public entries */
 EXTERN struct rproc rproc[NR_SYS_PROCS];
 EXTERN struct rproc *rproc_ptr[NR_PROCS];       /* mapping for fast access */
 
@@ -37,6 +38,11 @@ EXTERN struct rproc *rproc_ptr[NR_PROCS];       /* mapping for fast access */
  */
 EXTERN int exec_pipe[2];
 
+/* Global init descriptor. This descriptor holds data to initialize system
+ * services.
+ */
+EXTERN sef_init_info_t rinit;
+
 /* Global update descriptor. This descriptor holds data when a live update
  * is in progress.
  */
index 2986dc16946d835cddcf5fd865daea883429abc6..b61a03f20d53c5f387475d5ed6bc5aab76956fb2 100644 (file)
@@ -25,9 +25,7 @@ FORWARD _PROTOTYPE(void boot_image_info_lookup, ( endpoint_t endpoint,
     struct boot_image *image,
     struct boot_image **ip, struct boot_image_priv **pp,
     struct boot_image_sys **sp, struct boot_image_dev **dp)             );
-FORWARD _PROTOTYPE(void fill_call_mask, ( int *calls, int tot_nr_calls,
-    bitchunk_t *call_mask, int call_base)                               );
-FORWARD _PROTOTYPE(void init_server, (void)                            );
+FORWARD _PROTOTYPE(void catch_boot_init_ready, (endpoint_t endpoint)   );
 FORWARD _PROTOTYPE(void sig_handler, (void)                            );
 FORWARD _PROTOTYPE(void get_work, (message *m)                         );
 FORWARD _PROTOTYPE(void reply, (int whom, message *m_out)              );
@@ -36,16 +34,12 @@ FORWARD _PROTOTYPE(void reply, (int whom, message *m_out)           );
 PRIVATE int boot_image_buffer_size;
 PRIVATE char *boot_image_buffer;
 
-/* Macro to identify a system service in the boot image. This rules out
- * kernel tasks and the root system process (RS).
- */
-#define isbootsrvprocn(n) (!iskerneln((n)) && !isrootsysn((n)))
-
 /* Flag set when memory unmapping can be done. */
 EXTERN int unmap_ok;
 
 /* SEF functions and variables. */
-FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( void sef_local_startup, (void)                      );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -59,15 +53,10 @@ PUBLIC int main(void)
   message m;                                   /* request message */
   int call_nr, who_e,who_p;                    /* call number and caller */
   int result;                                  /* result to return */
-  sigset_t sigset;                             /* system signal set */
-  int s;
 
   /* SEF local startup. */
   sef_local_startup();
 
-  /* Initialize the server, then go to work. */
-  init_server();       
-
   /* Main loop - get work and do it, forever. */         
   while (TRUE) {              
 
@@ -83,8 +72,8 @@ PUBLIC int main(void)
       /* Now determine what to do.  Four types of requests are expected:
        * - Heartbeat messages (notifications from registered system services)
        * - System notifications (POSIX signals or synchronous alarm)
-       * - Ready to update messages (reply messages from registered services)
        * - User requests (control messages to manage system services)
+       * - Ready messages (reply messages from registered services)
        */
 
       /* Notification messages are control messages and do not need a reply.
@@ -107,21 +96,7 @@ PUBLIC int main(void)
          }
       }
 
-      /* See if this is a ready to update message.
-       * If the message was expected, update the originating process
-       */
-      else if(call_nr == RS_LU_PREPARE) {
-         result = do_upd_ready(&m);
-         
-         /* Send reply only if something went wrong. */
-          if (result != OK) {
-             m.m_type = result;
-              reply(who_e, &m);
-          }
-      }
-      
-      /* If this is neither a ready to update message nor a notification
-       * message, it is a normal request.
+      /* If we get this far, this is a normal request.
        * Handle the request and send a reply to the caller. 
        */
       else {
@@ -136,6 +111,7 @@ PUBLIC int main(void)
 
           /* Handler functions are responsible for permission checking. */
           switch(call_nr) {
+          /* User requests. */
          case RS_UP:           result = do_up(&m);             break;
           case RS_DOWN:        result = do_down(&m);           break;
           case RS_REFRESH:     result = do_refresh(&m);        break;
@@ -144,6 +120,9 @@ PUBLIC int main(void)
           case RS_UPDATE:      result = do_update(&m);         break;
           case GETSYSINFO:     result = do_getsysinfo(&m);     break;
          case RS_LOOKUP:       result = do_lookup(&m);         break;
+         /* Ready messages. */
+         case RS_INIT:         result = do_init_ready(&m);     break;
+         case RS_LU_PREPARE:   result = do_upd_ready(&m);      break;
           default: 
               printf("Warning, RS got unexpected request %d from %d\n",
                   m.m_type, m.m_source);
@@ -164,186 +143,25 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
-  /* No live update support for now. */
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);     /* RS can only start fresh. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
 /*===========================================================================*
- *                         exec_image_copy                                  *
- *===========================================================================*/
-PRIVATE void exec_image_copy(boot_proc_idx, ip, rp)
-int boot_proc_idx;
-struct boot_image *ip;
-struct rproc *rp;
-{
-/* Copy the executable image of the given boot process. */
-  int s;
-  struct exec header;
-  static char *boot_image_ptr = NULL;
-
-  if(boot_image_ptr == NULL) {
-      boot_image_ptr = boot_image_buffer;
-  }
-  s = NO_NUM;
-
-  /* Get a.out header. */
-  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < sizeof(header)
-      || (s = sys_getaoutheader(&header, boot_proc_idx)) != OK) {
-      panic("RS", "unable to get copy of a.out header", s);
-  }
-  memcpy(boot_image_ptr, &header, header.a_hdrlen);
-  boot_image_ptr += header.a_hdrlen;
-
-  /* Get text segment. */
-  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < header.a_text
-      || (s = rs_startup_segcopy(ip->endpoint, T, D, (vir_bytes) boot_image_ptr,
-      header.a_text)) != OK) {
-      panic("RS", "unable to get copy of text segment", s);
-  }
-  boot_image_ptr += header.a_text;
-
-  /* Get data segment. */
-  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < header.a_data
-      || (s = rs_startup_segcopy(ip->endpoint, D, D, (vir_bytes) boot_image_ptr,
-      header.a_data)) != OK) {
-      panic("RS", "unable to get copy of data segment", s);
-  }
-  boot_image_ptr += header.a_data;
-
-  /* Set the executable image for the given boot process. */
-  rp->r_exec_len = header.a_hdrlen + header.a_text + header.a_data;
-  rp->r_exec = boot_image_ptr - rp->r_exec_len;
-}
-
-/*===========================================================================*
- *                         boot_image_info_lookup                            *
- *===========================================================================*/
-PRIVATE void boot_image_info_lookup(endpoint, image, ip, pp, sp, dp)
-endpoint_t endpoint;
-struct boot_image *image;
-struct boot_image **ip;
-struct boot_image_priv **pp;
-struct boot_image_sys **sp;
-struct boot_image_dev **dp;
-{
-/* Lookup entries in boot image tables. */
-  int i;
-
-  /* When requested, locate the corresponding entry in the boot image table
-   * or panic if not found.
-   */
-  if(ip) {
-      for (i=0; i < NR_BOOT_PROCS; i++) {
-          if(image[i].endpoint == endpoint) {
-              *ip = &image[i];
-              break;
-          }
-      }
-      if(i == NR_BOOT_PROCS) {
-          panic("RS", "boot image table lookup failed", NO_NUM);
-      }
-  }
-
-  /* When requested, locate the corresponding entry in the boot image priv table
-   * or panic if not found.
-   */
-  if(pp) {
-      for (i=0; boot_image_priv_table[i].endpoint != NULL_BOOT_NR; i++) {
-          if(boot_image_priv_table[i].endpoint == endpoint) {
-              *pp = &boot_image_priv_table[i];
-              break;
-          }
-      }
-      if(i == NULL_BOOT_NR) {
-          panic("RS", "boot image priv table lookup failed", NO_NUM);
-      }
-  }
-
-  /* When requested, locate the corresponding entry in the boot image sys table
-   * or resort to the default entry if not found.
-   */
-  if(sp) {
-      for (i=0; boot_image_sys_table[i].endpoint != DEFAULT_BOOT_NR; i++) {
-          if(boot_image_sys_table[i].endpoint == endpoint) {
-              *sp = &boot_image_sys_table[i];
-              break;
-          }
-      }
-      if(boot_image_sys_table[i].endpoint == DEFAULT_BOOT_NR) {
-          *sp = &boot_image_sys_table[i];         /* accept the default entry */
-      }
-  }
-
-  /* When requested, locate the corresponding entry in the boot image dev table
-   * or resort to the default entry if not found.
-   */
-  if(dp) {
-      for (i=0; boot_image_dev_table[i].endpoint != DEFAULT_BOOT_NR; i++) {
-          if(boot_image_dev_table[i].endpoint == endpoint) {
-              *dp = &boot_image_dev_table[i];
-              break;
-          }
-      }
-      if(boot_image_dev_table[i].endpoint == DEFAULT_BOOT_NR) {
-          *dp = &boot_image_dev_table[i];         /* accept the default entry */
-      }
-  }
-}
-
-/*===========================================================================*
- *                           fill_call_mask                                 *
+ *                         sef_cb_init_fresh                                *
  *===========================================================================*/
-PRIVATE void fill_call_mask(calls, tot_nr_calls, call_mask, call_base)
-int *calls;                     /* the unordered set of calls */
-int tot_nr_calls;               /* the total number of calls */
-bitchunk_t *call_mask;          /* the call mask to fill in */
-int call_base;                  /* the base offset for the calls */
-{
-/* Fill a call mask from an unordered set of calls. */
-  int i;
-  bitchunk_t fv;
-  int call_mask_size, nr_calls;
-
-  call_mask_size = BITMAP_CHUNKS(tot_nr_calls);
-
-  /* Count the number of calls to fill in. */
-  nr_calls = 0;
-  for(i=0; calls[i] != SYS_NULL_C; i++) {
-      nr_calls++;
-  }
-
-  /* See if all calls are allowed and call mask must be completely filled. */
-  fv = 0;
-  if(nr_calls == 1 && calls[0] == SYS_ALL_C) {
-      fv = (~0);
-  }
-
-  /* Fill or clear call mask. */
-  for(i=0; i < call_mask_size; i++) {
-      call_mask[i] = fv;
-  }
-
-  /* Not all calls allowed? Enter calls bit by bit. */
-  if(!fv) {
-      for(i=0; i < nr_calls; i++) {
-          SET_BIT(call_mask, calls[i] - call_base);
-      }
-  }
-}
-
-/*===========================================================================*
- *                             init_server                                  *
- *===========================================================================*/
-PRIVATE void init_server(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
 /* Initialize the reincarnation server. */
   struct sigaction sa;
   struct boot_image *ip;
   int s,i,j;
-  int nr_image_srvs, nr_image_priv_srvs;
+  int nr_image_srvs, nr_image_priv_srvs, nr_uncaught_init_srvs;
   struct rproc *rp;
+  struct rprocpub *rpub;
   struct boot_image image[NR_BOOT_PROCS];
   struct mproc mproc[NR_PROCS];
   struct exec header;
@@ -354,6 +172,13 @@ PRIVATE void init_server(void)
   /* See if we run in verbose mode. */
   env_parse("rs_verbose", "d", 0, &rs_verbose, 0, 1);
 
+  /* Initialize the global init descriptor. */
+  rinit.rproctab_gid = cpf_grant_direct(ANY, (vir_bytes) rprocpub,
+      sizeof(rprocpub), CPF_READ);
+  if(!GRANT_VALID(rinit.rproctab_gid)) {
+      panic("RS", "unable to create rprocpub table grant", rinit.rproctab_gid);
+  }
+
   /* Initialize the global update descriptor. */
   rupdate.flags = 0;
 
@@ -371,7 +196,7 @@ PRIVATE void init_server(void)
       ip = &image[i];
 
       /* System services only. */
-      if(!isbootsrvprocn(_ENDPOINT_P(ip->endpoint))) {
+      if(iskerneln(_ENDPOINT_P(ip->endpoint))) {
           continue;
       }
       nr_image_srvs++;
@@ -400,7 +225,7 @@ PRIVATE void init_server(void)
       boot_image_priv = &boot_image_priv_table[i];
 
       /* System services only. */
-      if(!isbootsrvprocn(_ENDPOINT_P(boot_image_priv->endpoint))) {
+      if(iskerneln(_ENDPOINT_P(boot_image_priv->endpoint))) {
           continue;
       }
       nr_image_priv_srvs++;
@@ -418,7 +243,14 @@ PRIVATE void init_server(void)
       }
   }
 
-  /* Initialize the system process table in 3 steps, each of them following
+  /* Reset the system process table. */
+  for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
+      rp->r_flags = 0;
+      rp->r_pub = &rprocpub[rp - rproc];
+      rp->r_pub->in_use = FALSE;
+  }
+
+  /* Initialize the system process table in 4 steps, each of them following
    * the appearance of system services in the boot image priv table.
    * - Step 1: get a copy of the executable image of every system service that
    * requires it while it is not yet running.
@@ -429,7 +261,7 @@ PRIVATE void init_server(void)
       boot_image_priv = &boot_image_priv_table[i];
 
       /* System services only. */
-      if(!isbootsrvprocn(_ENDPOINT_P(boot_image_priv->endpoint))) {
+      if(iskerneln(_ENDPOINT_P(boot_image_priv->endpoint))) {
           continue;
       }
 
@@ -437,6 +269,7 @@ PRIVATE void init_server(void)
       boot_image_info_lookup(boot_image_priv->endpoint, image,
           &ip, NULL, &boot_image_sys, &boot_image_dev);
       rp = &rproc[boot_image_priv - boot_image_priv_table];
+      rpub = rp->r_pub;
 
       /*
        * Get a copy of the executable image if required.
@@ -449,30 +282,30 @@ PRIVATE void init_server(void)
 
       /*
        * Set privileges.
-       * XXX FIXME: We should also let RS set vm calls allowed for each sys
-       * service by using vm_set_priv(). We need a more uniform privilege
-       * management scheme in VM for this change.
        */
       /* Get label. */
-      strcpy(rp->r_label, boot_image_priv->label);
-
-      /* Force a static privilege id for system services in the boot image. */
-      rp->r_priv.s_id = static_priv_id(_ENDPOINT_P(boot_image_priv->endpoint));
-
-      /* Initialize privilege bitmaps. */
-      rp->r_priv.s_flags = boot_image_priv->flags;         /* privilege flags */
-      rp->r_priv.s_trap_mask = boot_image_priv->trap_mask; /* allowed traps */
-      memcpy(&rp->r_priv.s_ipc_to, &boot_image_priv->ipc_to,
-                       sizeof(rp->r_priv.s_ipc_to));      /* allowed targets */
-
-      /* Initialize call mask bitmap from unordered set. */
-      fill_call_mask(boot_image_priv->k_calls, NR_SYS_CALLS,
-          rp->r_priv.s_k_call_mask, KERNEL_CALL);
-
-      /* Set the privilege structure. */
-      if ((s = sys_privctl(ip->endpoint, SYS_PRIV_SET_SYS, &(rp->r_priv)))
-          != OK) {
-          panic("RS", "unable to set privilege structure", s);
+      strcpy(rpub->label, boot_image_priv->label);
+
+      if(boot_image_priv->endpoint != RS_PROC_NR) {
+          /* Force a static priv id for system services in the boot image. */
+          rp->r_priv.s_id = static_priv_id(
+              _ENDPOINT_P(boot_image_priv->endpoint));
+
+          /* Initialize privilege bitmaps. */
+          rp->r_priv.s_flags = boot_image_priv->flags;         /* priv flags */
+          rp->r_priv.s_trap_mask = boot_image_priv->trap_mask; /* traps */
+          memcpy(&rp->r_priv.s_ipc_to, &boot_image_priv->ipc_to,
+                            sizeof(rp->r_priv.s_ipc_to));      /* targets */
+
+          /* Initialize kernel call mask bitmap from unordered set. */
+          fill_call_mask(boot_image_priv->k_calls, NR_SYS_CALLS,
+              rp->r_priv.s_k_call_mask, KERNEL_CALL, TRUE);
+
+          /* Set the privilege structure. */
+          if ((s = sys_privctl(ip->endpoint, SYS_PRIV_SET_SYS, &(rp->r_priv)))
+              != OK) {
+              panic("RS", "unable to set privilege structure", s);
+          }
       }
 
       /* Synch the privilege structure with the kernel. */
@@ -483,17 +316,17 @@ PRIVATE void init_server(void)
       /*
        * Set sys properties.
        */
-      rp->r_sys_flags = boot_image_sys->flags;        /* sys flags */
+      rpub->sys_flags = boot_image_sys->flags;        /* sys flags */
 
       /*
        * Set dev properties.
        */
-      rp->r_dev_nr = boot_image_dev->dev_nr;          /* major device number */
-      rp->r_dev_style = boot_image_dev->dev_style;    /* device style */
-      rp->r_period = boot_image_dev->period;          /* heartbeat period */
+      rpub->dev_nr = boot_image_dev->dev_nr;          /* major device number */
+      rpub->dev_style = boot_image_dev->dev_style;    /* device style */
+      rpub->period = boot_image_dev->period;          /* heartbeat period */
 
       /* Get process name. */
-      strcpy(rp->r_proc_name, ip->proc_name);
+      strcpy(rpub->proc_name, ip->proc_name);
 
       /* Get command settings. */
       rp->r_cmd[0]= '\0';
@@ -502,9 +335,13 @@ PRIVATE void init_server(void)
       rp->r_argc = 1;
       rp->r_script[0]= '\0';
 
+      /* Initialize vm call mask bitmap from unordered set. */
+      fill_call_mask(boot_image_priv->vm_calls, NR_VM_CALLS,
+          rpub->vm_call_mask, VM_RQ_BASE, TRUE);
+
       /* Get some settings from the boot image table. */
       rp->r_nice = ip->priority;
-      rp->r_proc_nr_e = ip->endpoint;
+      rpub->endpoint = ip->endpoint;
 
       /* Set some defaults. */
       rp->r_uid = 0;                           /* root */
@@ -516,30 +353,62 @@ PRIVATE void init_server(void)
 
       /* Mark as in use. */
       rp->r_flags = RS_IN_USE;
-      rproc_ptr[_ENDPOINT_P(rp->r_proc_nr_e)]= rp;
+      rproc_ptr[_ENDPOINT_P(rpub->endpoint)]= rp;
+      rpub->in_use = TRUE;
   }
 
   /* - Step 2: allow every system service in the boot image to run.
    */
+  nr_uncaught_init_srvs = 0;
   for (i=0; boot_image_priv_table[i].endpoint != NULL_BOOT_NR; i++) {
       boot_image_priv = &boot_image_priv_table[i];
 
       /* System services only. */
-      if(!isbootsrvprocn(_ENDPOINT_P(boot_image_priv->endpoint))) {
+      if(iskerneln(_ENDPOINT_P(boot_image_priv->endpoint))) {
           continue;
       }
 
-      /* Lookup the corresponding entry in the boot image table. */
-      boot_image_info_lookup(boot_image_priv->endpoint, image,
-          &ip, NULL, NULL, NULL);
+      /* Ignore RS. */
+      if(boot_image_priv->endpoint == RS_PROC_NR) {
+          continue;
+      }
+
+      /* Lookup the corresponding slot in the system process table. */
+      rp = &rproc[boot_image_priv - boot_image_priv_table];
+      rpub = rp->r_pub;
 
       /* Allow the service to run. */
-      if ((s = sys_privctl(ip->endpoint, SYS_PRIV_ALLOW, NULL)) != OK) {
+      if ((s = sys_privctl(rpub->endpoint, SYS_PRIV_ALLOW, NULL)) != OK) {
           panic("RS", "unable to initialize privileges", s);
       }
+
+      /* Initialize service. We assume every service will always get
+       * back to us here at boot time.
+       */
+      if(boot_image_priv->flags & SYS_PROC) {
+          if ((s = init_service(rp, SEF_INIT_FRESH)) != OK) {
+              panic("RS", "unable to initialize service", s);
+          }
+          if(rpub->sys_flags & SF_SYNCH_BOOT) {
+              /* Catch init ready message now to synchronize. */
+              catch_boot_init_ready(rpub->endpoint);
+          }
+          else {
+              /* Catch init ready message later. */
+              nr_uncaught_init_srvs++;
+          }
+      }
+  }
+
+  /* - Step 3: let every system service complete initialization by
+   * catching all the init ready messages left.
+   */
+  while(nr_uncaught_init_srvs) {
+      catch_boot_init_ready(ANY);
+      nr_uncaught_init_srvs--;
   }
 
-  /* - Step 3: all the system services in the boot image are now running.
+  /* - Step 4: all the system services in the boot image are now running.
    * Complete the initialization of the system process table in collaboration
    * with other system processes.
    */
@@ -550,17 +419,18 @@ PRIVATE void init_server(void)
       boot_image_priv = &boot_image_priv_table[i];
 
       /* System services only. */
-      if(!isbootsrvprocn(_ENDPOINT_P(boot_image_priv->endpoint))) {
+      if(iskerneln(_ENDPOINT_P(boot_image_priv->endpoint))) {
           continue;
       }
 
       /* Lookup the corresponding slot in the system process table. */
       rp = &rproc[boot_image_priv - boot_image_priv_table];
+      rpub = rp->r_pub;
 
       /* Get pid from PM process table. */
       rp->r_pid = NO_PID;
       for (j = 0; j < NR_PROCS; j++) {
-          if (mproc[j].mp_endpoint == rp->r_proc_nr_e) {
+          if (mproc[j].mp_endpoint == rpub->endpoint) {
               rp->r_pid = mproc[j].mp_pid;
               break;
           }
@@ -568,15 +438,6 @@ PRIVATE void init_server(void)
       if(j == NR_PROCS) {
           panic("RS", "unable to get pid", NO_NUM);
       }
-
-      /* Publish the new system service.
-       * XXX FIXME. Possible race condition. We should publish labels before
-       * allowing other processes to run.
-       */
-      s = publish_service(rp);
-      if (s != OK) {
-          panic("RS", "unable to publish boot system service", s);
-      }
   }
 
   /*
@@ -631,6 +492,163 @@ PRIVATE void init_server(void)
   */
   unmap_ok = 1;
   _minix_unmapzero();
+
+  return(OK);
+}
+
+/*===========================================================================*
+ *                         exec_image_copy                                  *
+ *===========================================================================*/
+PRIVATE void exec_image_copy(boot_proc_idx, ip, rp)
+int boot_proc_idx;
+struct boot_image *ip;
+struct rproc *rp;
+{
+/* Copy the executable image of the given boot process. */
+  int s;
+  struct exec header;
+  static char *boot_image_ptr = NULL;
+
+  if(boot_image_ptr == NULL) {
+      boot_image_ptr = boot_image_buffer;
+  }
+  s = NO_NUM;
+
+  /* Get a.out header. */
+  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < sizeof(header)
+      || (s = sys_getaoutheader(&header, boot_proc_idx)) != OK) {
+      panic("RS", "unable to get copy of a.out header", s);
+  }
+  memcpy(boot_image_ptr, &header, header.a_hdrlen);
+  boot_image_ptr += header.a_hdrlen;
+
+  /* Get text segment. */
+  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < header.a_text
+      || (s = rs_startup_segcopy(ip->endpoint, T, D, (vir_bytes) boot_image_ptr,
+      header.a_text)) != OK) {
+      panic("RS", "unable to get copy of text segment", s);
+  }
+  boot_image_ptr += header.a_text;
+
+  /* Get data segment. */
+  if(boot_image_buffer+boot_image_buffer_size - boot_image_ptr < header.a_data
+      || (s = rs_startup_segcopy(ip->endpoint, D, D, (vir_bytes) boot_image_ptr,
+      header.a_data)) != OK) {
+      panic("RS", "unable to get copy of data segment", s);
+  }
+  boot_image_ptr += header.a_data;
+
+  /* Set the executable image for the given boot process. */
+  rp->r_exec_len = header.a_hdrlen + header.a_text + header.a_data;
+  rp->r_exec = boot_image_ptr - rp->r_exec_len;
+}
+
+/*===========================================================================*
+ *                         boot_image_info_lookup                            *
+ *===========================================================================*/
+PRIVATE void boot_image_info_lookup(endpoint, image, ip, pp, sp, dp)
+endpoint_t endpoint;
+struct boot_image *image;
+struct boot_image **ip;
+struct boot_image_priv **pp;
+struct boot_image_sys **sp;
+struct boot_image_dev **dp;
+{
+/* Lookup entries in boot image tables. */
+  int i;
+
+  /* When requested, locate the corresponding entry in the boot image table
+   * or panic if not found.
+   */
+  if(ip) {
+      for (i=0; i < NR_BOOT_PROCS; i++) {
+          if(image[i].endpoint == endpoint) {
+              *ip = &image[i];
+              break;
+          }
+      }
+      if(i == NR_BOOT_PROCS) {
+          panic("RS", "boot image table lookup failed", NO_NUM);
+      }
+  }
+
+  /* When requested, locate the corresponding entry in the boot image priv table
+   * or panic if not found.
+   */
+  if(pp) {
+      for (i=0; boot_image_priv_table[i].endpoint != NULL_BOOT_NR; i++) {
+          if(boot_image_priv_table[i].endpoint == endpoint) {
+              *pp = &boot_image_priv_table[i];
+              break;
+          }
+      }
+      if(i == NULL_BOOT_NR) {
+          panic("RS", "boot image priv table lookup failed", NO_NUM);
+      }
+  }
+
+  /* When requested, locate the corresponding entry in the boot image sys table
+   * or resort to the default entry if not found.
+   */
+  if(sp) {
+      for (i=0; boot_image_sys_table[i].endpoint != DEFAULT_BOOT_NR; i++) {
+          if(boot_image_sys_table[i].endpoint == endpoint) {
+              *sp = &boot_image_sys_table[i];
+              break;
+          }
+      }
+      if(boot_image_sys_table[i].endpoint == DEFAULT_BOOT_NR) {
+          *sp = &boot_image_sys_table[i];         /* accept the default entry */
+      }
+  }
+
+  /* When requested, locate the corresponding entry in the boot image dev table
+   * or resort to the default entry if not found.
+   */
+  if(dp) {
+      for (i=0; boot_image_dev_table[i].endpoint != DEFAULT_BOOT_NR; i++) {
+          if(boot_image_dev_table[i].endpoint == endpoint) {
+              *dp = &boot_image_dev_table[i];
+              break;
+          }
+      }
+      if(boot_image_dev_table[i].endpoint == DEFAULT_BOOT_NR) {
+          *dp = &boot_image_dev_table[i];         /* accept the default entry */
+      }
+  }
+}
+
+/*===========================================================================*
+ *                           catch_boot_init_ready                          *
+ *===========================================================================*/
+PRIVATE void catch_boot_init_ready(endpoint)
+endpoint_t endpoint;
+{
+/* Block and catch an init ready message from the given source. */
+  int r;
+  message m;
+  struct rproc *rp;
+  int result;
+
+  /* Receive init ready message. */
+  if ((r = receive(endpoint, &m)) != OK) {
+      panic("RS", "unable to receive init reply", r);
+  }
+  if(m.m_type != RS_INIT) {
+      panic("RS", "unexpected reply from service", m.m_source);
+  }
+  result = m.RS_INIT_RESULT;
+  rp = rproc_ptr[_ENDPOINT_P(m.m_source)];
+
+  /* Check result. */
+  if(result != OK) {
+      panic("RS", "unable to complete init for service", m.m_source);
+  }
+
+  /* Mark the slot as no longer initializing. */
+  rp->r_flags &= ~RS_INITIALIZING;
+  rp->r_check_tm = 0;
+  getuptime(&rp->r_alive_tm);
 }
 
 /*===========================================================================*
index 679841c87a44449324a6b36df4684c317ab6bf1f..3d9fbd02fc7fc118201adfae8d668ba3291cc807 100644 (file)
@@ -73,12 +73,14 @@ char *label;
 {
   int control_allowed = 0;
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   int c;
   char *progname;
 
   /* Find name of binary for given label. */
   for (rp = BEG_RPROC_ADDR; rp < END_RPROC_ADDR; rp++) {
-       if (strcmp(rp->r_label, label) == 0) {
+       rpub = rp->r_pub;
+       if (strcmp(rpub->label, label) == 0) {
                break;
        }
   }
@@ -91,7 +93,8 @@ char *label;
 
   /* Check if label is listed in caller's isolation policy. */
   for (rp = BEG_RPROC_ADDR; rp < END_RPROC_ADDR; rp++) {
-       if (rp->r_proc_nr_e == endpoint) {
+       rpub = rp->r_pub;
+       if (rpub->endpoint == endpoint) {
                break;
        }
   }
@@ -141,6 +144,7 @@ message *m_ptr;                                     /* request message pointer */
 /* A request was made to start a new system service. 
  */
   register struct rproc *rp;                   /* system process table */
+  register struct rprocpub *rpub;              /* public entry */
   int slot_nr;                                 /* local table entry */
   int arg_count;                               /* number of arguments */
   char *cmd_ptr;                               /* parse command string */
@@ -152,6 +156,7 @@ message *m_ptr;                                     /* request message pointer */
   int r;
   endpoint_t ep;
   struct rproc *tmp_rp;
+  struct rprocpub *tmp_rpub;
   struct rs_start rs_start;
 
   /* This call requires special privileges. */
@@ -168,6 +173,7 @@ message *m_ptr;                                     /* request message pointer */
       printf("RS: do_up: system process table full\n");
        return ENOMEM;
   }
+  rpub = rp->r_pub;
 
   /* Ok, there is space. Get the request structure. */
   s= sys_datacopy(m_ptr->m_source, (vir_bytes) m_ptr->RS_CMD_ADDR, 
@@ -210,38 +216,36 @@ message *m_ptr;                                   /* request message pointer */
   else
        cmd_ptr= rp->r_argv[0];
   len= strlen(cmd_ptr);
-  if (len > P_NAME_LEN-1)
-       len= P_NAME_LEN-1;      /* truncate name */
-  memcpy(rp->r_proc_name, cmd_ptr, len);
-  rp->r_proc_name[len]= '\0';
+  if (len > RS_MAX_LABEL_LEN-1)
+       len= RS_MAX_LABEL_LEN-1;        /* truncate name */
+  memcpy(rpub->proc_name, cmd_ptr, len);
+  rpub->proc_name[len]= '\0';
   if(rs_verbose)
       printf("RS: do_up: using proc_name (from binary %s) '%s'\n",
-          rp->r_argv[0], rp->r_proc_name);
+          rp->r_argv[0], rpub->proc_name);
 
   if(rs_start.rss_label.l_len > 0) {
        /* RS_UP caller has supplied a custom label for this service. */
        int s = copy_label(m_ptr->m_source, &rs_start.rss_label,
-               rp->r_label, sizeof(rp->r_label));
+               rpub->label, sizeof(rpub->label));
        if(s != OK)
                return s;
         if(rs_verbose)
-         printf("RS: do_up: using label (custom) '%s'\n", rp->r_label);
+         printf("RS: do_up: using label (custom) '%s'\n", rpub->label);
   } else {
        /* Default label for the service. */
-       label = rp->r_proc_name;
+       label = rpub->proc_name;
        len= strlen(label);
-       if (len > MAX_LABEL_LEN-1)
-               len= MAX_LABEL_LEN-1;   /* truncate name */
-       memcpy(rp->r_label, label, len);
-       rp->r_label[len]= '\0';
+       memcpy(rpub->label, label, len);
+       rpub->label[len]= '\0';
         if(rs_verbose)
           printf("RS: do_up: using label (from proc_name) '%s'\n",
-               rp->r_label);
+               rpub->label);
   }
 
   if(rs_start.rss_nr_control > 0) {
        int i, s;
-       if (rs_start.rss_nr_control > RSS_NR_CONTROL)
+       if (rs_start.rss_nr_control > RS_NR_CONTROL)
        {
                printf("RS: do_up: too many control labels\n");
                return EINVAL;
@@ -269,10 +273,11 @@ message *m_ptr;                                   /* request message pointer */
          continue;
       if (tmp_rp == rp)
          continue;                             /* Our slot */
-      if (strcmp(tmp_rp->r_label, rp->r_label) == 0)
+      tmp_rpub = tmp_rp->r_pub;
+      if (strcmp(tmp_rpub->label, rpub->label) == 0)
       {
          printf("RS: found duplicate label '%s': slot %d\n",
-               rp->r_label, slot_nr);
+               rpub->label, slot_nr);
          return EBUSY;
       }
   }
@@ -289,11 +294,11 @@ message *m_ptr;                                   /* request message pointer */
   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_flags & RSS_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);
+               printf("rs: ipc list too long for '%s'\n", rpub->label);
                return EINVAL;
        }
        s=sys_datacopy(m_ptr->m_source, (vir_bytes) rs_start.rss_ipc, 
@@ -304,20 +309,22 @@ message *m_ptr;                                   /* request message pointer */
   else
        rp->r_ipc_list[0]= '\0';
 
-  rp->r_sys_flags = DSRV_SF;
+  rpub->sys_flags = DSRV_SF;
   rp->r_exec= NULL;
-  if (rs_start.rss_flags & RF_COPY) {
+  if (rs_start.rss_flags & RSS_COPY) {
        int exst_cpy;
        struct rproc *rp2;
+       struct rprocpub *rpub2;
        exst_cpy = 0;
        
-       if(rs_start.rss_flags & RF_REUSE) {
+       if(rs_start.rss_flags & RSS_REUSE) {
                 int i;
 
                 for(i = 0; i < NR_SYS_PROCS; i++) {
                        rp2 = &rproc[i];
-                        if(strcmp(rp->r_proc_name, rp2->r_proc_name) == 0 &&
-                           (rp2->r_sys_flags & SF_USE_COPY)) {
+                       rpub2 = rproc[i].r_pub;
+                        if(strcmp(rpub->proc_name, rpub2->proc_name) == 0 &&
+                           (rpub2->sys_flags & SF_USE_COPY)) {
                                 /* We have found the same binary that's
                                  * already been copied */
                                  exst_cpy = 1;
@@ -334,7 +341,7 @@ message *m_ptr;                                     /* request message pointer */
        if (s != OK)
                return s;
 
-       rp->r_sys_flags |= SF_USE_COPY;
+       rpub->sys_flags |= SF_USE_COPY;
   }
 
   /* All dynamically created services get the same privilege flags, and
@@ -375,40 +382,42 @@ message *m_ptr;                                   /* request message pointer */
                rp->r_priv.s_io_tab[i].ior_limit);
   }
 
-  if (rs_start.rss_nr_pci_id > RSS_NR_PCI_ID)
+  if (rs_start.rss_nr_pci_id > RS_NR_PCI_DEVICE)
   {
        printf("RS: do_up: too many PCI device IDs\n");
        return EINVAL;
   }
-  rp->r_nr_pci_id= rs_start.rss_nr_pci_id;
-  for (i= 0; i<rp->r_nr_pci_id; i++)
+  rpub->pci_acl.rsp_nr_device = rs_start.rss_nr_pci_id;
+  for (i= 0; i<rpub->pci_acl.rsp_nr_device; i++)
   {
-       rp->r_pci_id[i].vid= rs_start.rss_pci_id[i].vid;
-       rp->r_pci_id[i].did= rs_start.rss_pci_id[i].did;
+       rpub->pci_acl.rsp_device[i].vid= rs_start.rss_pci_id[i].vid;
+       rpub->pci_acl.rsp_device[i].did= rs_start.rss_pci_id[i].did;
        if(rs_verbose)
           printf("RS: do_up: PCI %04x/%04x\n",
-               rp->r_pci_id[i].vid, rp->r_pci_id[i].did);
+               rpub->pci_acl.rsp_device[i].vid,
+               rpub->pci_acl.rsp_device[i].did);
   }
-  if (rs_start.rss_nr_pci_class > RSS_NR_PCI_CLASS)
+  if (rs_start.rss_nr_pci_class > RS_NR_PCI_CLASS)
   {
        printf("RS: do_up: too many PCI class IDs\n");
        return EINVAL;
   }
-  rp->r_nr_pci_class= rs_start.rss_nr_pci_class;
-  for (i= 0; i<rp->r_nr_pci_class; i++)
+  rpub->pci_acl.rsp_nr_class= rs_start.rss_nr_pci_class;
+  for (i= 0; i<rpub->pci_acl.rsp_nr_class; i++)
   {
-       rp->r_pci_class[i].class= rs_start.rss_pci_class[i].class;
-       rp->r_pci_class[i].mask= rs_start.rss_pci_class[i].mask;
+       rpub->pci_acl.rsp_class[i].class= rs_start.rss_pci_class[i].class;
+       rpub->pci_acl.rsp_class[i].mask= rs_start.rss_pci_class[i].mask;
        if(rs_verbose)
            printf("RS: do_up: PCI class %06x mask %06x\n",
-               rp->r_pci_class[i].class, rp->r_pci_class[i].mask);
+               rpub->pci_acl.rsp_class[i].class,
+               rpub->pci_acl.rsp_class[i].mask);
   }
 
   /* Copy 'system' call number bits */
   if (sizeof(rs_start.rss_system[0]) == sizeof(rp->r_call_mask[0]) &&
        sizeof(rs_start.rss_system) == sizeof(rp->r_call_mask))
   {
-       for (i= 0; i<RSS_NR_SYSTEM; i++)
+       for (i= 0; i<RS_SYS_CALL_MASK_SIZE; i++)
                rp->r_call_mask[i]= rs_start.rss_system[i];
   }
   else
@@ -419,21 +428,25 @@ message *m_ptr;                                   /* request message pointer */
   }
 
   /* Initialize some fields. */
-  rp->r_period = rs_start.rss_period;
-  rp->r_dev_nr = rs_start.rss_major;
-  rp->r_dev_style = STYLE_DEV; 
+  rpub->period = rs_start.rss_period;
+  rpub->dev_nr = rs_start.rss_major;
+  rpub->dev_style = STYLE_DEV; 
   rp->r_restarts = -1;                                 /* will be incremented */
   rp->r_set_resources= 1;                      /* set resources */
 
-  if (sizeof(rp->r_vm) == sizeof(rs_start.rss_vm) &&
-      sizeof(rp->r_vm[0]) == sizeof(rs_start.rss_vm[0]))
+  if (sizeof(rpub->vm_call_mask) == sizeof(rs_start.rss_vm) &&
+      sizeof(rpub->vm_call_mask[0]) == sizeof(rs_start.rss_vm[0]))
   {
-         memcpy(rp->r_vm, rs_start.rss_vm, sizeof(rp->r_vm));
+          int basic_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C };
+         memcpy(rpub->vm_call_mask, rs_start.rss_vm,
+               sizeof(rpub->vm_call_mask));
+         fill_call_mask(basic_vmc, NR_VM_CALLS,
+               rpub->vm_call_mask, VM_RQ_BASE, FALSE);
   }
   else
   {
-         printf("RS: do_up: internal inconsistency: bad size of r_vm\n");
-         memset(rp->r_vm, '\0', sizeof(rp->r_vm));
+         printf("RS: internal inconsistency: bad size of vm_call_mask\n");
+         memset(rpub->vm_call_mask, '\0', sizeof(rpub->vm_call_mask));
   }
 
   /* All information was gathered. Now try to start the system service. */
@@ -449,9 +462,10 @@ message *m_ptr;                                    /* request message pointer */
 PUBLIC int do_down(message *m_ptr)
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   size_t len;
   int s, proc;
-  char label[MAX_LABEL_LEN];
+  char label[RS_MAX_LABEL_LEN];
 
   /* This call requires special privileges. */
   if (!caller_is_root(m_ptr->m_source)) return(EPERM);
@@ -466,7 +480,11 @@ PUBLIC int do_down(message *m_ptr)
   label[len]= '\0';
 
   for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
-      if (rp->r_flags & RS_IN_USE && strcmp(rp->r_label, label) == 0) {
+      rpub = rp->r_pub;
+      if (rp->r_flags & RS_IN_USE && strcmp(rpub->label, label) == 0) {
+       /* Core system services should never go down. */
+       if (rpub->sys_flags & SF_CORE_SRV) return(EPERM);
+
        if(rs_verbose)
          printf("RS: stopping '%s' (%d)\n", label, rp->r_pid);
        stop_service(rp,RS_EXITING);
@@ -494,9 +512,10 @@ PUBLIC int do_down(message *m_ptr)
 PUBLIC int do_restart(message *m_ptr)
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   size_t len;
   int s, proc, r;
-  char label[MAX_LABEL_LEN];
+  char label[RS_MAX_LABEL_LEN];
   endpoint_t ep;
 
   len= m_ptr->RS_CMD_LEN;
@@ -515,7 +534,8 @@ PUBLIC int do_restart(message *m_ptr)
   }
 
   for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
-      if ((rp->r_flags & RS_IN_USE) && strcmp(rp->r_label, label) == 0) {
+      rpub = rp->r_pub;
+      if ((rp->r_flags & RS_IN_USE) && strcmp(rpub->label, label) == 0) {
          if(rs_verbose) printf("RS: restarting '%s' (%d)\n", label, rp->r_pid);
          if (rp->r_pid >= 0)
          {
@@ -545,9 +565,10 @@ PUBLIC int do_restart(message *m_ptr)
 PUBLIC int do_refresh(message *m_ptr)
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   size_t len;
   int s;
-  char label[MAX_LABEL_LEN];
+  char label[RS_MAX_LABEL_LEN];
 
   len= m_ptr->RS_CMD_LEN;
   if (len >= sizeof(label))
@@ -565,9 +586,15 @@ PUBLIC int do_refresh(message *m_ptr)
   }
 
   for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
-      if (rp->r_flags & RS_IN_USE && strcmp(rp->r_label, label) == 0) {
+      rpub = rp->r_pub;
+      if (rp->r_flags & RS_IN_USE && strcmp(rpub->label, label) == 0) {
+          /* Only system processes not including RS can refresh. */
+          if(!(rp->r_priv.s_flags & SYS_PROC) || rpub->endpoint == RS_PROC_NR) {
+              return EPERM;
+          }
+
           if(rs_verbose) {
-              printf("RS: refreshing %s (%d)\n", rp->r_label, rp->r_pid);
+              printf("RS: refreshing %s (%d)\n", rpub->label, rp->r_pid);
           }
          stop_service(rp,RS_REFRESHING);
          return(OK);
@@ -593,15 +620,65 @@ PUBLIC int do_shutdown(message *m_ptr)
   return(OK);
 }
 
+
+/*===========================================================================*
+ *                             do_init_ready                                *
+ *===========================================================================*/
+PUBLIC int do_init_ready(message *m_ptr)
+{
+  int who_p;
+  struct rproc *rp;
+  struct rprocpub *rpub;
+  int result;
+
+  who_p = _ENDPOINT_P(m_ptr->m_source);
+  rp = rproc_ptr[who_p];
+  rpub = rp->r_pub;
+  result = m_ptr->RS_INIT_RESULT;
+
+  /* Make sure the originating service was requested to initialize. */
+  if(! (rp->r_flags & RS_INITIALIZING) ) {
+      if(rs_verbose) {
+          printf("RS: do_init_ready: got unexpected init ready msg from %d\n",
+              m_ptr->m_source);
+      }
+      return(EINVAL);
+  }
+
+  /* Mark the slot as no longer initializing. */
+  rp->r_flags &= ~RS_INITIALIZING;
+  rp->r_check_tm = 0;
+  getuptime(&rp->r_alive_tm);
+
+  /* Check if something went wrong and the service failed to init.
+   * In that case, kill it and make sure it won't be restarted.
+   */
+  if(result != OK) {
+      if(rs_verbose)
+          printf("RS: initialization failed for service %d: %d\n",
+              rpub->endpoint, result);
+      rp->r_flags |= RS_EXITING;
+      kill(rp->r_pid, SIGKILL);
+  }
+  else {
+      if(rs_verbose)
+          printf("RS: initialization succeeded for service %d\n",
+              rpub->endpoint);
+  }
+
+  return(EDONTREPLY);
+}
+
 /*===========================================================================*
  *                             do_update                                    *
  *===========================================================================*/
 PUBLIC int do_update(message *m_ptr)
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   size_t len;
   int s;
-  char label[MAX_LABEL_LEN];
+  char label[RS_MAX_LABEL_LEN];
   int lu_state;
   int prepare_maxtime;
 
@@ -614,6 +691,12 @@ PUBLIC int do_update(message *m_ptr)
   if (s != OK) return(s);
   label[len]= '\0';
 
+  /* This call requires special privileges. */
+  if (! (caller_can_control(m_ptr->m_source, label) ||
+      caller_is_root(m_ptr->m_source))) {
+      return(EPERM);
+  }
+
   /* Retrieve live update state. */
   lu_state = m_ptr->RS_LU_STATE;
   if(lu_state == SEF_LU_STATE_NULL) {
@@ -641,20 +724,26 @@ PUBLIC int do_update(message *m_ptr)
 
   /* Try to start the update process. */
   for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
-      if (rp->r_flags & RS_IN_USE && strcmp(rp->r_label, label) == 0) {
+      rpub = rp->r_pub;
+      if (rp->r_flags & RS_IN_USE && strcmp(rpub->label, label) == 0) {
+          /* Only system processes not including RS can update. */
+          if(!(rp->r_priv.s_flags & SYS_PROC) || rpub->endpoint == RS_PROC_NR) {
+              return EPERM;
+          }
+
           if(rs_verbose) {
-             printf("RS: updating %s (%d)\n", rp->r_label, rp->r_pid);
+             printf("RS: updating %s (%d)\n", rpub->label, rp->r_pid);
          }
-         
+
          rp->r_flags |= RS_UPDATING;
          rupdate.flags |= RS_UPDATING;
          getuptime(&rupdate.prepare_tm);
           rupdate.prepare_maxtime = prepare_maxtime;
          rupdate.rp = rp;
-         
+
          m_ptr->m_type = RS_LU_PREPARE;
-         asynsend(rp->r_proc_nr_e, m_ptr);  /* request to prepare for update */
-         
+         asynsend(rpub->endpoint, m_ptr);  /* request to update */
+
          return(OK);
       }
   }
@@ -679,7 +768,7 @@ PUBLIC int do_upd_ready(message *m_ptr)
   rp = rproc_ptr[who_p];
   result = m_ptr->RS_LU_RESULT;
 
-  /* Make sure the originating process was requested to prepare for update. */
+  /* Make sure the originating service was requested to prepare for update. */
   if(! (rp->r_flags & RS_UPDATING) ) {
       if(rs_verbose) {
           printf("RS: do_upd_ready: got unexpected update ready msg from %d\n",
@@ -688,7 +777,7 @@ PUBLIC int do_upd_ready(message *m_ptr)
       return(EINVAL);
   }
 
-  /* Check if something went wrong and the process failed to prepare
+  /* Check if something went wrong and the service failed to prepare
    * for the update. In that case, end the update process.
    */
   if(result != OK) {
@@ -696,17 +785,17 @@ PUBLIC int do_upd_ready(message *m_ptr)
       switch(result) {
           case EACCES:
               printf("RS: update failed: %s\n",
-                  "process does not support live update");
+                  "service does not support live update");
           break;
 
           case EINVAL:
               printf("RS: update failed: %s\n",
-                  "process does not support the required state");
+                  "service does not support the required state");
           break;
 
           case EBUSY:
               printf("RS: update failed: %s\n",
-                  "process is not able to prepare for the update now");
+                  "service is not able to prepare for the update now");
           break;
 
           case EGENERIC:
@@ -721,7 +810,7 @@ PUBLIC int do_upd_ready(message *m_ptr)
           break;
       }
 
-      return ENOTREADY;
+      return(OK);
   }
 
   /* Kill the process now and mark it for refresh, the new version will
@@ -731,7 +820,7 @@ PUBLIC int do_upd_ready(message *m_ptr)
   rp->r_flags |= RS_REFRESHING;
   kill(rp->r_pid, SIGKILL);
 
-  return(OK);
+  return(EDONTREPLY);
 }
 
 /*===========================================================================*
@@ -742,6 +831,9 @@ PRIVATE void update_period(message *m_ptr)
   clock_t now = m_ptr->NOTIFY_TIMESTAMP;
   short has_update_timed_out;
   message m;
+  struct rprocpub *rpub;
+
+  rpub = rupdate.rp->r_pub;
 
   /* See if a timeout has occurred. */
   has_update_timed_out = (now - rupdate.prepare_tm > rupdate.prepare_maxtime);
@@ -754,7 +846,7 @@ PRIVATE void update_period(message *m_ptr)
       /* Prepare cancel request. */
       m.m_type = RS_LU_PREPARE;
       m.RS_LU_STATE = SEF_LU_STATE_NULL;
-      asynsend(rupdate.rp->r_proc_nr_e, &m);
+      asynsend(rpub->endpoint, &m);
   }
 }
 
@@ -766,15 +858,12 @@ PRIVATE void end_update(clock_t now)
   /* End the update process and mark the affected service as no longer under
    * update. Eventual late ready to update message (if any) will simply be
    * ignored and the service can continue executing.
-   * Also, if the service has a period, update the alive and check timestamps
-   * of the service to force a status request in the next period.
+   * We reset the check timestamp, so that if the service has a period a status
+   * request will be forced in the next period.
    */
   rupdate.flags &= ~RS_UPDATING;
   rupdate.rp->r_flags &= ~RS_UPDATING;
-  if(rupdate.rp->r_period > 0 ) {
-      rupdate.rp->r_alive_tm = now;
-      rupdate.rp->r_check_tm = now - rupdate.rp->r_period - 1;
-  }
+  rupdate.rp->r_check_tm = 0;
 }
 
 /*===========================================================================*
@@ -783,6 +872,7 @@ PRIVATE void end_update(clock_t now)
 PUBLIC void do_exit(message *m_ptr)
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   pid_t exit_pid;
   int exit_status, r, slot_nr;
   endpoint_t ep;
@@ -841,16 +931,17 @@ PUBLIC void do_exit(message *m_ptr)
        * This should always succeed. 
        */
       for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
+          rpub = rp->r_pub;
           if ((rp->r_flags & RS_IN_USE) && rp->r_pid == exit_pid) {
              int proc;
-             proc = _ENDPOINT_P(rp->r_proc_nr_e);
+             proc = _ENDPOINT_P(rpub->endpoint);
 
               rproc_ptr[proc] = NULL;          /* invalidate */
              rp->r_pid= -1;
 
              /* If PCI properties are set, inform the PCI driver. */
-              if(rp->r_nr_pci_id || rp->r_nr_pci_class) {
-                  pci_del_acl(rp->r_proc_nr_e);
+              if(rpub->pci_acl.rsp_nr_device || rpub->pci_acl.rsp_nr_class) {
+                  pci_del_acl(rpub->endpoint);
               }
 
               if ((rp->r_flags & RS_EXITING) || shutting_down) {
@@ -868,7 +959,6 @@ PUBLIC void do_exit(message *m_ptr)
                      short is_updating = rp->r_flags & RS_UPDATING;
 
                      /* Refresh */
-                     rp->r_restarts = -1;              /* reset counter */
                      if (rp->r_script[0] != '\0')
                        run_script(rp);
                      else {
@@ -911,7 +1001,7 @@ rp->r_restarts= 0;
                                rp->r_cmd, rp->r_backoff);
                      rp->r_backoff = 1 << MIN(rp->r_restarts,(BACKOFF_BITS-2));
                      rp->r_backoff = MIN(rp->r_backoff,MAX_BACKOFF); 
-                     if ((rp->r_sys_flags & SF_USE_COPY) && rp->r_backoff > 1)
+                     if ((rpub->sys_flags & SF_USE_COPY) && rp->r_backoff > 1)
                        rp->r_backoff= 1;
                  }
                  else {
@@ -937,9 +1027,11 @@ PUBLIC void do_period(m_ptr)
 message *m_ptr;
 {
   register struct rproc *rp;
+  register struct rprocpub *rpub;
   clock_t now = m_ptr->NOTIFY_TIMESTAMP;
   int s;
   endpoint_t ep;
+  long period;
 
   /* If an update is in progress, check its status. */
   if(rupdate.flags & RS_UPDATING) {
@@ -950,8 +1042,15 @@ message *m_ptr;
    * updating.
    */
   for (rp=BEG_RPROC_ADDR; rp<END_RPROC_ADDR; rp++) {
+      rpub = rp->r_pub;
       if ((rp->r_flags & RS_IN_USE) && !(rp->r_flags & RS_UPDATING)) {
 
+          /* Compute period. */
+          period = rpub->period;
+          if(rp->r_flags & RS_INITIALIZING) {
+              period = RS_INIT_T;
+          }
+
           /* If the service is to be revived (because it repeatedly exited, 
           * and was not directly restarted), the binary backoff field is  
           * greater than zero. 
@@ -975,7 +1074,7 @@ message *m_ptr;
          /* There seems to be no special conditions. If the service has a 
           * period assigned check its status. 
           */
-         else if (rp->r_period > 0) {
+         else if (period > 0) {
 
              /* Check if an answer to a status request is still pending. If 
               * the service didn't respond within time, kill it to simulate 
@@ -983,12 +1082,15 @@ message *m_ptr;
               * be restarted automatically.
               */
               if (rp->r_alive_tm < rp->r_check_tm) { 
-                 if (now - rp->r_alive_tm > 2*rp->r_period &&
+                 if (now - rp->r_alive_tm > 2*period &&
                      rp->r_pid > 0 && !(rp->r_flags & RS_NOPINGREPLY)) { 
                      if(rs_verbose)
                            printf("RS: service %d reported late\n",
-                               rp->r_proc_nr_e); 
+                               rpub->endpoint); 
                      rp->r_flags |= RS_NOPINGREPLY;
+                     if(rp->r_flags & RS_INITIALIZING) {
+                           rp->r_flags |= RS_EXITING;   /* don't restart */
+                     }
                       kill(rp->r_pid, SIGKILL);                /* simulate crash */
                  }
              }
@@ -996,12 +1098,12 @@ message *m_ptr;
              /* No answer pending. Check if a period expired since the last
               * check and, if so request the system service's status.
               */
-             else if (now - rp->r_check_tm > rp->r_period) {
+             else if (now - rp->r_check_tm > rpub->period) {
 #if 0
                if(rs_verbose)
-                  printf("RS: status request sent to %d\n", rp->r_proc_nr_e);
+                  printf("RS: status request sent to %d\n", rpub->endpoint);
 #endif
-                 notify(rp->r_proc_nr_e);              /* request status */
+                 notify(rpub->endpoint);               /* request status */
                  rp->r_check_tm = now;                 /* mark time */
               }
           }
@@ -1029,17 +1131,20 @@ endpoint_t *endpoint;
   int child_proc_nr_e, child_proc_nr_n;                /* child process slot */
   pid_t child_pid;                             /* child's process id */
   char *file_only;
-  int s, use_copy, slot_nr;
+  int s, use_copy, slot_nr, init_type;
   bitchunk_t *vm_mask;
   message m;
   char * null_env = NULL;
+  struct rprocpub *rpub;
 
-  use_copy= (rp->r_sys_flags & SF_USE_COPY);
+  rpub = rp->r_pub;
+  use_copy= (rpub->sys_flags & SF_USE_COPY);
 
   /* See if we are not using a copy but we do need one to start the service. */
-  if(!use_copy && (rp->r_sys_flags & SF_NEED_COPY)) {
+  if(!use_copy && (rpub->sys_flags & SF_NEED_COPY)) {
        printf("RS: unable to start service %s without an in-memory copy\n",
-           rp->r_label);
+           rpub->label);
+       free_slot(rp);
        return(EPERM);
   }
 
@@ -1097,13 +1202,14 @@ endpoint_t *endpoint;
   child_proc_nr_n = _ENDPOINT_P(child_proc_nr_e);
   rp->r_flags = RS_IN_USE | flags;             /* mark slot in use */
   rp->r_restarts += 1;                         /* raise nr of restarts */
-  rp->r_proc_nr_e = child_proc_nr_e;           /* set child details */
+  rpub->endpoint = child_proc_nr_e;            /* set child details */
   rp->r_pid = child_pid;
   rp->r_check_tm = 0;                          /* not checked yet */
   getuptime(&rp->r_alive_tm);                  /* currently alive */
   rp->r_stop_tm = 0;                           /* not exiting yet */
   rp->r_backoff = 0;                           /* not to be restarted */
   rproc_ptr[child_proc_nr_n] = rp;             /* mapping for fast access */
+  rpub->in_use = TRUE;                         /* public entry is now in use */
 
   /* If any of the calls below fail, the RS_EXITING flag is set. This implies
    * that the process will be removed from RS's process table once it has
@@ -1136,7 +1242,7 @@ endpoint_t *endpoint;
        init_privs(rp, &rp->r_priv);
 
        /* Tell VM about allowed calls. */
-       vm_mask = &rp->r_vm[0];
+       vm_mask = &rpub->vm_call_mask[0];
        if ((s = vm_set_priv(child_proc_nr_e, vm_mask)) < 0) {
            report("RS", "vm_set_priv call failed", s);
            kill(child_pid, SIGKILL);
@@ -1155,7 +1261,7 @@ endpoint_t *endpoint;
   }
 
   /* If PCI properties are set, inform the PCI driver about the new service. */
-  if(rp->r_nr_pci_id || rp->r_nr_pci_class) {
+  if(rpub->pci_acl.rsp_nr_device || rpub->pci_acl.rsp_nr_class) {
       init_pci(rp, child_proc_nr_e);
   }
 
@@ -1166,7 +1272,7 @@ endpoint_t *endpoint;
   }
 
   /* Allow the service to run.
-   * XXX FIXME: we should let the service run only after publishing information
+   * XXX: We should let the service run/init only after publishing information
    * about the new system service, but this is not currently possible due to
    * the blocking nature of mapdriver() that expects the service to be running.
    * The current solution is not race-free. This hack can go once service
@@ -1179,6 +1285,12 @@ endpoint_t *endpoint;
       return(s);                                       /* return error */
   }
 
+  /* Initialize service. */
+  init_type = rp->r_restarts > 0 ? SEF_INIT_RESTART : SEF_INIT_FRESH;
+  if((s = init_service(rp, init_type)) != OK) {
+      panic("RS", "unable to initialize service", s);
+  }
+
   /* The purpose of non-blocking forks is to avoid involving VFS in the forking
    * process, because VFS may be blocked on a sendrec() to a MFS that is
    * waiting for a endpoint update for a dead driver. We have just published
@@ -1193,16 +1305,16 @@ endpoint_t *endpoint;
        setuid(0);
 
   /* Map the new service. */
-  if (rp->r_dev_nr > 0) {                              /* set driver map */
-      if ((s=mapdriver(rp->r_label,
-             rp->r_dev_nr, rp->r_dev_style, !!use_copy /* force */)) < 0) {
+  if (rpub->dev_nr > 0) {                              /* set driver map */
+      if ((s=mapdriver(rpub->label,
+             rpub->dev_nr, rpub->dev_style, !!use_copy /* force */)) < 0) {
           report("RS", "couldn't map driver (continuing)", errno);
       }
   }
 
   if(rs_verbose)
       printf("RS: started '%s', major %d, pid %d, endpoint %d, proc %d\n", 
-          rp->r_cmd, rp->r_dev_nr, child_pid,
+          rp->r_cmd, rpub->dev_nr, child_pid,
          child_proc_nr_e, child_proc_nr_n);
 
   /* The system service now has been successfully started. The only thing
@@ -1254,6 +1366,10 @@ message *m_ptr;
        src_addr = (vir_bytes) rproc;
        len = sizeof(struct rproc) * NR_SYS_PROCS;
        break; 
+  case SI_PROCPUB_TAB:
+       src_addr = (vir_bytes) rprocpub;
+       len = sizeof(struct rprocpub) * NR_SYS_PROCS;
+       break; 
   default:
        return(EINVAL);
   }
@@ -1281,9 +1397,15 @@ PRIVATE pid_t fork_nb()
 PRIVATE int share_exec(rp_dst, rp_src)
 struct rproc *rp_dst, *rp_src;
 {
+  struct rprocpub *rpub_src;
+  struct rprocpub *rpub_dst;
+
+  rpub_src = rp_src->r_pub;
+  rpub_dst = rp_dst->r_pub;
+
   if(rs_verbose) {
       printf("RS: share_exec: sharing exec image from %s to %s\n",
-          rp_src->r_label, rp_dst->r_label);
+          rpub_src->label, rpub_dst->label);
   }
 
   /* Share exec image from rp_src to rp_dst. */
@@ -1350,10 +1472,13 @@ PRIVATE void free_slot(rp)
 struct rproc *rp;
 {
   int slot_nr, has_shared_exec;
+  struct rprocpub *rpub;
   struct rproc *other_rp;
 
+  rpub = rp->r_pub;
+
   /* Free memory if necessary. */
-  if(rp->r_sys_flags & SF_USE_COPY) {
+  if(rpub->sys_flags & SF_USE_COPY) {
       /* Search for some other slot sharing the same exec image. */
       has_shared_exec = FALSE;
       for (slot_nr = 0; slot_nr < NR_SYS_PROCS; slot_nr++) {
@@ -1367,7 +1492,8 @@ struct rproc *rp;
       /* If nobody uses our copy of the exec image, we can get rid of it. */
       if(!has_shared_exec) {
           if(rs_verbose) {
-              printf("RS: free_slot: free exec image from %s\n", rp->r_label);
+              printf("RS: free_slot: free exec image from %s\n",
+                  rpub->label);
           }
           free(rp->r_exec);
           rp->r_exec = NULL;
@@ -1377,7 +1503,8 @@ struct rproc *rp;
 
   /* Mark slot as no longer in use.. */
   rp->r_flags = 0;
-  rproc_ptr[_ENDPOINT_P(rp->r_proc_nr_e)] = NULL;
+  rpub->in_use = FALSE;
+  rproc_ptr[_ENDPOINT_P(rpub->endpoint)] = NULL;
 }
 
 /*===========================================================================*
@@ -1386,12 +1513,14 @@ struct rproc *rp;
 PRIVATE void run_script(rp)
 struct rproc *rp;
 {
-       int r, proc_nr_e;
+       int r, endpoint;
        pid_t pid;
        char *reason;
        char incarnation_str[20];       /* Enough for a counter? */
        char *envp[1] = { NULL };
+       struct rprocpub *rpub;
 
+       rpub = rp->r_pub;
        if (rp->r_flags & RS_REFRESHING)
                reason= "restart";
        else if (rp->r_flags & RS_NOPINGREPLY)
@@ -1406,14 +1535,14 @@ struct rproc *rp;
        {
                printf(
                "RS: run_script: can't find reason for termination of '%s'\n",
-                       rp->r_label);
+                       rpub->label);
                return;
        }
        sprintf(incarnation_str, "%d", rp->r_restarts);
 
        if(rs_verbose) {
          printf("RS: calling script '%s'\n", rp->r_script);
-         printf("RS: sevice name: '%s'\n", rp->r_label);
+         printf("RS: sevice name: '%s'\n", rpub->label);
          printf("RS: reason: '%s'\n", reason);
          printf("RS: incarnation: '%s'\n", incarnation_str);
        }
@@ -1425,20 +1554,20 @@ struct rproc *rp;
                printf("RS: run_script: fork failed: %s\n", strerror(errno));
                break;
        case 0:
-               execle(rp->r_script, rp->r_script, rp->r_label, reason,
+               execle(rp->r_script, rp->r_script, rpub->label, reason,
                        incarnation_str, NULL, envp);
                printf("RS: run_script: execl '%s' failed: %s\n",
                        rp->r_script, strerror(errno));
                exit(1);
        default:
                /* Set the privilege structure for the child process. */
-               proc_nr_e = getnprocnr(pid);
-               if ((r = sys_privctl(proc_nr_e, SYS_PRIV_SET_USER, NULL))
+               endpoint = getnprocnr(pid);
+               if ((r = sys_privctl(endpoint, SYS_PRIV_SET_USER, NULL))
                        != OK) {
                        printf("RS: run_script: can't set privileges: %d\n",r);
                }
-               /* Allow the process to run. */
-               if ((r = sys_privctl(proc_nr_e, SYS_PRIV_ALLOW, NULL)) != OK) {
+               /* Allow the service to run. */
+               if ((r = sys_privctl(endpoint, SYS_PRIV_ALLOW, NULL)) != OK) {
                        printf("RS: run_script: process can't run: %d\n",r);
                }
                /* Do not wait for the child */
@@ -1473,7 +1602,7 @@ char *caller_label;
                if (q == p)
                        continue;
                len= q-p;
-               if (len > MAX_LABEL_LEN)
+               if (len > RS_MAX_LABEL_LEN)
                {
                        printf(
        "rs:get_next_label: bad ipc list entry '.*s' for %s: too long\n",
@@ -1499,35 +1628,38 @@ struct priv *privp;
        /* Add IPC send permissions to a process based on that process's IPC
         * list.
         */
-       char label[MAX_LABEL_LEN+1], *p;
+       char label[RS_MAX_LABEL_LEN+1], *p;
        struct rproc *tmp_rp;
-       endpoint_t proc_nr_e;
+       struct rprocpub *tmp_rpub;
+       endpoint_t endpoint;
        int r;
        int slot_nr, priv_id;
        struct priv priv;
+       struct rprocpub *rpub;
 
+       rpub = rp->r_pub;
        p = rp->r_ipc_list;
 
-       while ((p = get_next_label(p, label, rp->r_label)) != NULL) {
+       while ((p = get_next_label(p, label, rpub->label)) != NULL) {
 
                if (strcmp(label, "SYSTEM") == 0)
-                       proc_nr_e= SYSTEM;
+                       endpoint= SYSTEM;
                else if (strcmp(label, "USER") == 0)
-                       proc_nr_e= INIT_PROC_NR; /* all user procs */
+                       endpoint= INIT_PROC_NR; /* all user procs */
                else if (strcmp(label, "PM") == 0)
-                       proc_nr_e= PM_PROC_NR;
+                       endpoint= PM_PROC_NR;
                else if (strcmp(label, "VFS") == 0)
-                       proc_nr_e= FS_PROC_NR;
+                       endpoint= FS_PROC_NR;
                else if (strcmp(label, "RS") == 0)
-                       proc_nr_e= RS_PROC_NR;
+                       endpoint= RS_PROC_NR;
                else if (strcmp(label, "LOG") == 0)
-                       proc_nr_e= LOG_PROC_NR;
+                       endpoint= LOG_PROC_NR;
                else if (strcmp(label, "TTY") == 0)
-                       proc_nr_e= TTY_PROC_NR;
+                       endpoint= TTY_PROC_NR;
                else if (strcmp(label, "DS") == 0)
-                       proc_nr_e= DS_PROC_NR;
+                       endpoint= DS_PROC_NR;
                else if (strcmp(label, "VM") == 0)
-                       proc_nr_e= VM_PROC_NR;
+                       endpoint= VM_PROC_NR;
                else
                {
                        /* Try to find process */
@@ -1537,7 +1669,8 @@ struct priv *privp;
                                tmp_rp = &rproc[slot_nr];
                                if (!(tmp_rp->r_flags & RS_IN_USE))
                                        continue;
-                               if (strcmp(tmp_rp->r_label, label) == 0)
+                               tmp_rpub = tmp_rp->r_pub;
+                               if (strcmp(tmp_rpub->label, label) == 0)
                                        break;
                        }
                        if (slot_nr >= NR_SYS_PROCS)
@@ -1547,10 +1680,10 @@ struct priv *privp;
                        "add_forward_ipc: unable to find '%s'\n", label);
                                continue;
                        }
-                       proc_nr_e= tmp_rp->r_proc_nr_e;
+                       endpoint= tmp_rpub->endpoint;
                }
 
-               if ((r = sys_getpriv(&priv, proc_nr_e)) < 0)
+               if ((r = sys_getpriv(&priv, endpoint)) < 0)
                {
                        printf(
                "add_forward_ipc: unable to get priv_id for '%s': %d\n",
@@ -1576,8 +1709,9 @@ struct priv *privp;
         * add these permissions now because the current process may not yet
         * have existed at the time that the other process was initialized.
         */
-       char label[MAX_LABEL_LEN+1], *p;
+       char label[RS_MAX_LABEL_LEN+1], *p;
        struct rproc *rrp;
+       struct rprocpub *rrpub;
        int priv_id, found;
 
        for (rrp=BEG_RPROC_ADDR; rrp<END_RPROC_ADDR; rrp++) {
@@ -1591,11 +1725,12 @@ struct priv *privp;
                if (rrp->r_ipc_list[0]) {
                        found = 0;
 
+                       rrpub = rrp->r_pub;
                        p = rrp->r_ipc_list;
 
-                       while ((p = get_next_label(p, label, rp->r_label)) !=
-                                                                       NULL) {
-                               if (!strcmp(rp->r_label, label)) {
+                       while ((p = get_next_label(p, label,
+                               rrpub->label)) != NULL) {
+                               if (!strcmp(rrpub->label, label)) {
                                        found = 1;
                                        break;
                                }
@@ -1628,7 +1763,7 @@ struct priv *privp;
 
        src_bits_per_word= 8*sizeof(rp->r_call_mask[0]);
        dst_bits_per_word= 8*sizeof(privp->s_k_call_mask[0]);
-       for (src_word= 0; src_word < RSS_NR_SYSTEM; src_word++)
+       for (src_word= 0; src_word < RS_SYS_CALL_MASK_SIZE; src_word++)
        {
                for (src_bit= 0; src_bit < src_bits_per_word; src_bit++)
                {
@@ -1642,7 +1777,7 @@ struct priv *privp;
 #endif
                        dst_word= call_nr / dst_bits_per_word;
                        mask= (1UL << (call_nr % dst_bits_per_word));
-                       if (dst_word >= CALL_MASK_SIZE)
+                       if (dst_word >= SYS_CALL_MASK_SIZE)
                        {
                                printf(
                                "RS: init_privs: call number %d doesn't fit\n",
@@ -1682,53 +1817,13 @@ int endpoint;
        size_t len;
        int i, r;
        struct rs_pci rs_pci;
+       struct rprocpub *rpub;
 
-       if (strcmp(rp->r_label, "pci") == 0)
-       {
-               if(rs_verbose)
-                       printf("RS: init_pci: not when starting 'pci'\n");
-               return;
-       }
-
-       len= strlen(rp->r_label);
-       if (len+1 > sizeof(rs_pci.rsp_label))
-       {
-               if(rs_verbose)
-                 printf("RS: init_pci: label '%s' too long for rsp_label\n",
-                       rp->r_label);
-               return;
-       }
-       strcpy(rs_pci.rsp_label, rp->r_label);
+       rpub = rp->r_pub;
+       rs_pci = rpub->pci_acl;
+       strcpy(rs_pci.rsp_label, rpub->label);
        rs_pci.rsp_endpoint= endpoint;
 
-       rs_pci.rsp_nr_device= rp->r_nr_pci_id;
-       if (rs_pci.rsp_nr_device > RSP_NR_DEVICE)
-       {
-               printf("RS: init_pci: too many PCI devices (max %d) "
-                 "truncating\n",
-                       RSP_NR_DEVICE);
-               rs_pci.rsp_nr_device= RSP_NR_DEVICE;
-       }
-       for (i= 0; i<rs_pci.rsp_nr_device; i++)
-       {
-               rs_pci.rsp_device[i].vid= rp->r_pci_id[i].vid;
-               rs_pci.rsp_device[i].did= rp->r_pci_id[i].did;
-       }
-
-       rs_pci.rsp_nr_class= rp->r_nr_pci_class;
-       if (rs_pci.rsp_nr_class > RSP_NR_CLASS)
-       {
-               printf("RS: init_pci: too many PCI classes "
-                  "(max %d) truncating\n",
-                       RSP_NR_CLASS);
-               rs_pci.rsp_nr_class= RSP_NR_CLASS;
-       }
-       for (i= 0; i<rs_pci.rsp_nr_class; i++)
-       {
-               rs_pci.rsp_class[i].class= rp->r_pci_class[i].class;
-               rs_pci.rsp_class[i].mask= rp->r_pci_class[i].mask;
-       }
-
        if(rs_verbose)
                printf("RS: init_pci: calling pci_set_acl\n");
 
@@ -1754,6 +1849,7 @@ message *m_ptr;
        static char namebuf[100];
        int len, r;
        struct rproc *rrp;
+       struct rprocpub *rrpub;
 
        len = m_ptr->RS_NAME_LEN;
 
@@ -1774,8 +1870,9 @@ message *m_ptr;
        for (rrp=BEG_RPROC_ADDR; rrp<END_RPROC_ADDR; rrp++) {
                if (!(rrp->r_flags & RS_IN_USE))
                        continue;
-               if (!strcmp(rrp->r_label, namebuf)) {
-                       m_ptr->RS_ENDPOINT = rrp->r_proc_nr_e;
+               rrpub = rrp->r_pub;
+               if (!strcmp(rrpub->label, namebuf)) {
+                       m_ptr->RS_ENDPOINT = rrpub->endpoint;
                        return OK;
                }
        }
index 7bccb85ae09a4c8ab2ee0fbc5da1d7f1c8f599a7..09b3a9f178ee46338af33349e8d3fd97a2cb9bca 100644 (file)
@@ -18,13 +18,17 @@ _PROTOTYPE( int do_restart, (message *m));
 _PROTOTYPE( int do_lookup, (message *m));
 _PROTOTYPE( int do_shutdown, (message *m));
 _PROTOTYPE( void do_period, (message *m));
+_PROTOTYPE( int do_init_ready, (message *m));
 _PROTOTYPE( int do_update, (message *m));
 _PROTOTYPE( int do_upd_ready, (message *m));
 _PROTOTYPE( void do_exit, (message *m));
 _PROTOTYPE( int do_getsysinfo, (message *m));
 
 /* utility.c */
+_PROTOTYPE( int init_service, (struct rproc *rp, int type));
 _PROTOTYPE( int publish_service, (struct rproc *rp));
+_PROTOTYPE(void fill_call_mask, ( int *calls, int tot_nr_calls,
+    bitchunk_t *call_mask, int call_base, int is_init));
 
 /* memory.c */
 _PROTOTYPE( void* rs_startup_sbrk, (size_t size));
index 9a8f6c93437dd60074ac6282393b3edebd9f1f7f..cc4884420803957df24fd5fa64f98d87ee395ed3 100644 (file)
@@ -196,12 +196,12 @@ PRIVATE int parse_arguments(int argc, char **argv)
   }
 
   if (req_nr == RS_UP) {
-      rs_start.rss_flags= RF_IPC_VALID;
+      rs_start.rss_flags= RSS_IPC_VALID;
       if (c_flag)
-       rs_start.rss_flags |= RF_COPY;
+       rs_start.rss_flags |= RSS_COPY;
 
       if(r_flag)
-        rs_start.rss_flags |= RF_REUSE;
+        rs_start.rss_flags |= RSS_REUSE;
         
       if (do_run)
       {
@@ -610,10 +610,10 @@ PRIVATE void do_pci_device(config_t *cpe)
                        fatal("do_pci_device: bad ID '%s' at %s:%d",
                                cpe->word, cpe->file, cpe->line);
                }
-               if (rs_start.rss_nr_pci_id >= RSS_NR_PCI_ID)
+               if (rs_start.rss_nr_pci_id >= RS_NR_PCI_DEVICE)
                {
                        fatal("do_pci_device: too many device IDs (max %d)",
-                               RSS_NR_PCI_ID);
+                               RS_NR_PCI_DEVICE);
                }
                rs_start.rss_pci_id[rs_start.rss_nr_pci_id].vid= vid;
                rs_start.rss_pci_id[rs_start.rss_nr_pci_id].did= did;
@@ -662,10 +662,10 @@ PRIVATE void do_pci_class(config_t *cpe)
                                cpe->word, cpe->file, cpe->line);
                }
                class_id= (baseclass << 16) | (subclass << 8) | interface;
-               if (rs_start.rss_nr_pci_class >= RSS_NR_PCI_CLASS)
+               if (rs_start.rss_nr_pci_class >= RS_NR_PCI_CLASS)
                {
                        fatal("do_pci_class: too many class IDs (max %d)",
-                               RSS_NR_PCI_CLASS);
+                               RS_NR_PCI_CLASS);
                }
                rs_start.rss_pci_class[rs_start.rss_nr_pci_class].class=
                        class_id;
@@ -877,10 +877,10 @@ PRIVATE void do_system(config_t *cpe)
                word= call_nr / bits_per_word;
                mask= (1UL << (call_nr % bits_per_word));
 
-               if (word >= RSS_NR_SYSTEM)
+               if (word >= RS_SYS_CALL_MASK_SIZE)
                {
                        fatal(
-                       "do_system: RSS_NR_SYSTEM is too small (%d needed)",
+                       "RS_SYS_CALL_MASK_SIZE is too small (%d needed)",
                                word+1);
                }
                rs_start.rss_system[word] |= mask;
@@ -904,10 +904,10 @@ PRIVATE void do_control(config_t *cpe)
                        fatal("do_control: unexpected string at %s:%d",
                                cpe->file, cpe->line);
                }
-               if (nr_control >= RSS_NR_CONTROL)
+               if (nr_control >= RS_NR_CONTROL)
                {
                        fatal(
-                       "do_control: RSS_NR_CONTROL is too small (%d needed)",
+                       "do_control: RS_NR_CONTROL is too small (%d needed)",
                                nr_control+1);
                }
 
index 84eb51f001c47073e00bf1e3eff72c948b41fcd9..de4c40e70bd146f1003d921f2f552d5e09b8efda 100644 (file)
@@ -8,50 +8,78 @@
 
 #include "inc.h"
 
-/* Define kernel calls that processes are allowed to make. This is not looking
- * very nice, but we need to define the access rights on a per call basis.
+/* Define kernel calls that processes are allowed to make.
  * 
  * Calls are unordered lists, converted by RS to bitmasks
  * once at runtime.
  */
-#define FS_KC SYS_KILL, SYS_VIRCOPY, SYS_SAFECOPYFROM, SYS_SAFECOPYTO, \
+#define FS_KC   SYS_KILL, SYS_VIRCOPY, SYS_SAFECOPYFROM, SYS_SAFECOPYTO, \
     SYS_UMAP, SYS_GETINFO, SYS_EXIT, SYS_TIMES, SYS_SETALARM, \
     SYS_PRIVCTL, SYS_TRACE , SYS_SETGRANT, SYS_PROFBUF, SYS_SYSCTL
 #define DRV_KC FS_KC, SYS_SEGCTL, SYS_IRQCTL, SYS_INT86, SYS_DEVIO, \
     SYS_SDEVIO, SYS_VDEVIO, SYS_SETGRANT, SYS_PROFBUF, SYS_SYSCTL
 
 PRIVATE int
-  fs_kc[] = { FS_KC, SYS_NULL_C },
-  pm_kc[] = { SYS_ALL_C, SYS_NULL_C },
-  ds_kc[] = { SYS_ALL_C, SYS_NULL_C },
-  vm_kc[] = { SYS_ALL_C, SYS_NULL_C },
-  drv_kc[] = { DRV_KC, SYS_NULL_C },
-  tty_kc[] = { DRV_KC, SYS_PHYSCOPY, SYS_ABORT, SYS_IOPENABLE,
+  pm_kc[] =   { SYS_ALL_C, SYS_NULL_C },
+  vfs_kc[] =  { FS_KC, SYS_NULL_C },
+  rs_kc[] =   { SYS_ALL_C, SYS_NULL_C },
+  ds_kc[] =   { SYS_ALL_C, SYS_NULL_C },
+  vm_kc[] =   { SYS_ALL_C, SYS_NULL_C },
+  tty_kc[] =  { DRV_KC, SYS_PHYSCOPY, SYS_ABORT, SYS_IOPENABLE,
       SYS_READBIOS, SYS_NULL_C },
-  mem_kc[] = { DRV_KC, SYS_PHYSCOPY, SYS_IOPENABLE, SYS_NULL_C },
+  mem_kc[] =  { DRV_KC, SYS_PHYSCOPY, SYS_IOPENABLE, SYS_NULL_C},
+  log_kc[] =  { DRV_KC, SYS_NULL_C },
+  mfs_kc[] =  { FS_KC, SYS_NULL_C },
+  pfs_kc[] =  { FS_KC, SYS_NULL_C },
   rusr_kc[] = { SYS_NULL_C },
+  no_kc[] =   { SYS_NULL_C }; /* no kernel call */
 
-  no_kc[] = { SYS_NULL_C }; /* no kernel call */
+/* Define VM calls that processes are allowed to make.
+ * 
+ * Calls are unordered lists, converted by RS to bitmasks
+ * once at runtime.
+ */
+PRIVATE int
+  pm_vmc[] =   { VM_BASIC_CALLS, VM_EXIT, VM_FORK, VM_BRK, VM_EXEC_NEWMEM,
+      VM_PUSH_SIG, VM_WILLEXIT, VM_ADDDMA, VM_DELDMA, VM_GETDMA,
+      VM_NOTIFY_SIG, SYS_NULL_C },
+  vfs_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  rs_vmc[] =   { VM_BASIC_CALLS, VM_RS_SET_PRIV, SYS_NULL_C },
+  ds_vmc[] =   { VM_BASIC_CALLS, SYS_NULL_C },
+  vm_vmc[] =   { SYS_NULL_C },
+  tty_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  mem_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  log_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  mfs_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  pfs_vmc[] =  { VM_BASIC_CALLS, SYS_NULL_C },
+  rusr_vmc[] = { VM_BASIC_CALLS, SYS_NULL_C },
+  no_vmc[] =   { SYS_NULL_C }; /* no vm call */
 
-/* Definition of the boot image priv table. */
+/* Definition of the boot image priv table. The order of entries in this table
+ * reflects the order boot system services are made runnable and initialized
+ * at boot time.
+ */
 PUBLIC struct boot_image_priv boot_image_priv_table[] = {
-  /*endpoint,     label,      flags,  traps,  ipcto,  kcalls  */
-  { VM_PROC_NR,   "vm",       VM_F,   SRV_T,  SRV_M,  vm_kc   },
-  { PM_PROC_NR,   "pm",       SRV_F,  SRV_T,  SRV_M,  pm_kc   },
-  { FS_PROC_NR,   "vfs",      SRV_F,  SRV_T,  SRV_M,  fs_kc   },
-  { DS_PROC_NR,   "ds",       SRV_F,  SRV_T,  SRV_M,  ds_kc   },
-  { TTY_PROC_NR,  "tty",      SRV_F,  SRV_T,  SRV_M,  tty_kc  },
-  { MEM_PROC_NR,  "memory",   SRV_F,  SRV_T,  SRV_M,  mem_kc  },
-  { LOG_PROC_NR,  "log",      SRV_F,  SRV_T,  SRV_M,  drv_kc  },
-  { MFS_PROC_NR,  "fs_imgrd", SRV_F,  SRV_T,  SRV_M,  fs_kc   },
-  { PFS_PROC_NR,  "pfs",      SRV_F,  SRV_T,  SRV_M,  fs_kc   },
-  { INIT_PROC_NR, "init",     RUSR_F, RUSR_T, RUSR_M, rusr_kc },
-  { NULL_BOOT_NR, "",         0,      0,      0,      no_kc   } /* null entry */
+  /*endpoint,     label,      flags,  traps,  ipcto,  kcalls,  vmcalls  */
+  { RS_PROC_NR,   "rs",       RSYS_F, RSYS_T, RSYS_M, rs_kc,   rs_vmc   },
+  { VM_PROC_NR,   "vm",       VM_F,   SRV_T,  SRV_M,  vm_kc,   vm_vmc   },
+  { PM_PROC_NR,   "pm",       SRV_F,  SRV_T,  SRV_M,  pm_kc,   pm_vmc   },
+  { VFS_PROC_NR,  "vfs",      SRV_F,  SRV_T,  SRV_M,  vfs_kc,  vfs_vmc  },
+  { DS_PROC_NR,   "ds",       SRV_F,  SRV_T,  SRV_M,  ds_kc,   ds_vmc   },
+  { TTY_PROC_NR,  "tty",      SRV_F,  SRV_T,  SRV_M,  tty_kc,  tty_vmc  },
+  { MEM_PROC_NR,  "memory",   SRV_F,  SRV_T,  SRV_M,  mem_kc,  mem_vmc  },
+  { LOG_PROC_NR,  "log",      SRV_F,  SRV_T,  SRV_M,  log_kc,  log_vmc  },
+  { MFS_PROC_NR,  "fs_imgrd", SRV_F,  SRV_T,  SRV_M,  mfs_kc,  mfs_vmc  },
+  { PFS_PROC_NR,  "pfs",      SRV_F,  SRV_T,  SRV_M,  pfs_kc,  pfs_vmc  },
+  { INIT_PROC_NR, "init",     RUSR_F, RUSR_T, RUSR_M, rusr_kc, rusr_vmc },
+  { NULL_BOOT_NR, "",         0,      0,      0,      no_kc,   no_vmc   }
 };
 
 /* Definition of the boot image sys table. */
 PUBLIC struct boot_image_sys boot_image_sys_table[] = {
   /*endpoint,         flags                             */
+  { RS_PROC_NR,       SRV_SF                            },
+  { VM_PROC_NR,       VM_SF                             },
   { LOG_PROC_NR,      SRVC_SF                           },
   { MFS_PROC_NR,      SRVC_SF                           },
   { PFS_PROC_NR,      SRVC_SF                           },
index aebd82224a4e58589b791c8687df4b3c1e8927bf..3fce4533f67e2756c369bcd4e94d71a13420d96a 100644 (file)
@@ -6,12 +6,13 @@
 /* Definition of an entry of the boot image priv table. */
 struct boot_image_priv {
   endpoint_t endpoint;         /* process endpoint number */
-  char label[MAX_LABEL_LEN];   /* label to assign to this service */
+  char label[RS_MAX_LABEL_LEN]; /* label to assign to this service */
 
   int flags;                   /* privilege flags */
   short trap_mask;             /* allowed system call traps */
   int ipc_to;                  /* send mask protection */
-  int *k_calls;                /* kernel call protection */
+  int *k_calls;                /* allowed kernel calls */
+  int *vm_calls;               /* allowed vm calls */
 };
 
 /* Definition of an entry of the boot image sys table. */
@@ -32,49 +33,37 @@ struct boot_image_dev {
 
 /* Definition of an entry of the system process table. */
 struct rproc {
-  endpoint_t r_proc_nr_e;      /* process endpoint number */
+  struct rprocpub *r_pub;       /* pointer to the corresponding public entry */
   pid_t r_pid;                 /* process id, -1 if the process is not there */
-  dev_t r_dev_nr;              /* major device number */
-  int r_dev_style;             /* device style */
 
   int r_restarts;              /* number of restarts (initially zero) */
   long r_backoff;              /* number of periods to wait before revive */
   unsigned r_flags;            /* status and policy flags */
-  unsigned r_sys_flags;        /* sys flags */
 
-  long r_period;               /* heartbeat period (or zero) */
   clock_t r_check_tm;          /* timestamp of last check */
   clock_t r_alive_tm;          /* timestamp of last heartbeat */
   clock_t r_stop_tm;           /* timestamp of SIGTERM signal */
   endpoint_t r_caller;         /* RS_LATEREPLY caller */
 
-  char *r_exec;                        /* Executable image */ 
-  size_t r_exec_len;           /* Length of image */
-
-  char r_label[MAX_LABEL_LEN]; /* label of this service */
-  char r_proc_name[P_NAME_LEN];        /* process name of this service */
   char r_cmd[MAX_COMMAND_LEN]; /* raw command plus arguments */
   char r_script[MAX_SCRIPT_LEN]; /* name of the restart script executable */
   char *r_argv[MAX_NR_ARGS+2];  /* parsed arguments vector */
   int r_argc;                          /* number of arguments */
 
-  /* Resources */
-  int r_set_resources;
+  char *r_exec;                        /* Executable image */ 
+  size_t r_exec_len;           /* Length of image */
+
+  int r_set_resources;         /* set when resources must be set. */
   struct priv r_priv;          /* Privilege structure to be passed to the
                                 * kernel.
                                 */
   uid_t r_uid;
   int r_nice;
-  int r_nr_pci_id;             /* Number of PCI devices IDs */
-  struct { u16_t vid; u16_t did; } r_pci_id[RSS_NR_PCI_ID];
-  int r_nr_pci_class;          /* Number of PCI class IDs */
-  struct { u32_t class; u32_t mask; } r_pci_class[RSS_NR_PCI_CLASS];
 
-  u32_t r_call_mask[RSS_NR_SYSTEM];
+  u32_t r_call_mask[RS_SYS_CALL_MASK_SIZE];
   char r_ipc_list[MAX_IPC_LIST];
-  bitchunk_t r_vm[RSS_VM_CALL_SIZE];
   int r_nr_control;
-  char r_control[RSS_NR_CONTROL][MAX_LABEL_LEN];
+  char r_control[RS_NR_CONTROL][RS_MAX_LABEL_LEN];
 };
 
 /* Definition of the global update descriptor. */
index 5caf96c586a083bc4a4b319501dacf3fa246cb48..e58f3fdadf55bda3c901c820e5f1831c60cebb36 100644 (file)
@@ -8,6 +8,30 @@
 
 #include <minix/ds.h>
 
+/*===========================================================================*
+ *                              init_service                                *
+ *===========================================================================*/
+PUBLIC int init_service(rp, type)
+struct rproc *rp;                              /* pointer to process slot */
+int type;                                      /* type of initialization */
+{
+  int r;
+  message m;
+  struct rprocpub *rpub;
+
+  rpub = rp->r_pub;
+
+  rp->r_flags |= RS_INITIALIZING;              /* now initializing */
+  rp->r_check_tm = rp->r_alive_tm + 1;         /* expect reply within period */
+
+  m.m_type = RS_INIT;
+  m.RS_INIT_TYPE = type;
+  m.RS_INIT_RPROCTAB_GID = rinit.rproctab_gid;
+  r = asynsend(rpub->endpoint, &m);
+
+  return r;
+}
+
 /*===========================================================================*
  *                             publish_service                              *
  *===========================================================================*/
@@ -16,17 +40,62 @@ struct rproc *rp;                           /* pointer to process slot */
 {
 /* A new system service has been started. Publish the necessary information. */
   int s;
+  struct rprocpub *rpub;
+
+  rpub = rp->r_pub;
 
   /* Register its label with DS. */
-  s= ds_publish_u32(rp->r_label, rp->r_proc_nr_e);
+  s= ds_publish_u32(rpub->label, rpub->endpoint);
   if (s != OK) {
       return s;
   }
   if (rs_verbose) {
       printf("RS: publish_service: DS label registration done: %s -> %d\n", 
-          rp->r_label, rp->r_proc_nr_e);
+          rpub->label, rpub->endpoint);
   }
 
   return(OK);
 }
 
+/*===========================================================================*
+ *                           fill_call_mask                                 *
+ *===========================================================================*/
+PUBLIC void fill_call_mask(calls, tot_nr_calls, call_mask, call_base, is_init)
+int *calls;                     /* the unordered set of calls */
+int tot_nr_calls;               /* the total number of calls */
+bitchunk_t *call_mask;          /* the call mask to fill in */
+int call_base;                  /* the base offset for the calls */
+int is_init;                    /* set when initializing a call mask */
+{
+/* Fill a call mask from an unordered set of calls. */
+  int i;
+  int call_mask_size, nr_calls;
+
+  call_mask_size = BITMAP_CHUNKS(tot_nr_calls);
+
+  /* Count the number of calls to fill in. */
+  nr_calls = 0;
+  for(i=0; calls[i] != SYS_NULL_C; i++) {
+      nr_calls++;
+  }
+
+  /* See if all calls are allowed and call mask must be completely filled. */
+  if(nr_calls == 1 && calls[0] == SYS_ALL_C) {
+      for(i=0; i < call_mask_size; i++) {
+          call_mask[i] = (~0);
+      }
+  }
+  else {
+      /* When initializing, reset the mask first. */
+      if(is_init) {
+          for(i=0; i < call_mask_size; i++) {
+              call_mask[i] = 0;
+          }
+      }
+      /* Enter calls bit by bit. */
+      for(i=0; i < nr_calls; i++) {
+          SET_BIT(call_mask, calls[i] - call_base);
+      }
+  }
+}
+
index 0c06e53d16a3fc592d227818a4b7b940ae3eb91f..1d7431f9db70134f4be30b9612352bb227c04ccc 100644 (file)
 EXTERN unsigned long calls_stats[NCALLS];
 #endif
 
-FORWARD _PROTOTYPE( void fs_init, (void)                               );
 FORWARD _PROTOTYPE( void get_work, (void)                              );
 FORWARD _PROTOTYPE( void init_root, (void)                             );
 FORWARD _PROTOTYPE( void service_pm, (void)                            );
 
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -61,14 +61,6 @@ PUBLIC int main(void)
   /* SEF local startup. */
   sef_local_startup();
 
-  fs_init();
-
-  SANITYCHECK;
-
-#if DO_SANITYCHECKS
-  FIXME("VFS: DO_SANITYCHECKS is on");
-#endif
-
   /* This is the main loop that gets work, processes it, and sends replies. */
   while (TRUE) {
        SANITYCHECK;
@@ -228,12 +220,106 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
+/*===========================================================================*
+ *                             sef_cb_init_fresh                            *
+ *===========================================================================*/
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
+{
+/* Initialize the virtual file server. */
+  int s;
+  register struct fproc *rfp;
+  struct vmnt *vmp;
+  struct vnode *root_vp;
+  message mess;
+
+  /* Clear endpoint field */
+  last_login_fs_e = NONE;
+  mount_m_in.m1_p3 = (char *) NONE;
+
+  /* Initialize the process table with help of the process manager messages. 
+   * Expect one message for each system process with its slot number and pid. 
+   * When no more processes follow, the magic process number NONE is sent. 
+   * Then, stop and synchronize with the PM.
+   */
+  do {
+       if (OK != (s=sef_receive(PM_PROC_NR, &mess)))
+               panic(__FILE__,"FS couldn't receive from PM", s);
+
+       if (mess.m_type != PM_INIT)
+               panic(__FILE__, "unexpected message from PM", mess.m_type);
+
+       if (NONE == mess.PM_PROC) break; 
+
+       rfp = &fproc[mess.PM_SLOT];
+       rfp->fp_pid = mess.PM_PID;
+       rfp->fp_endpoint = mess.PM_PROC;
+       rfp->fp_realuid = (uid_t) SYS_UID;
+       rfp->fp_effuid = (uid_t) SYS_UID;
+       rfp->fp_realgid = (gid_t) SYS_GID;
+       rfp->fp_effgid = (gid_t) SYS_GID;
+       rfp->fp_umask = ~0;
+       rfp->fp_grant = GRANT_INVALID;
+       rfp->fp_blocked_on = FP_BLOCKED_ON_NONE;
+       rfp->fp_revived = NOT_REVIVING;
+   
+  } while (TRUE);                      /* continue until process NONE */
+  mess.m_type = OK;                    /* tell PM that we succeeded */
+  s = send(PM_PROC_NR, &mess);         /* send synchronization message */
+
+  /* All process table entries have been set. Continue with FS initialization.
+   * Certain relations must hold for the file system to work at all. Some 
+   * extra block_size requirements are checked at super-block-read-in time.
+   */
+  if (OPEN_MAX > 127) panic(__FILE__,"OPEN_MAX > 127", NO_NUM);
+  
+  /* The following initializations are needed to let dev_opcl succeed .*/
+  fp = (struct fproc *) NULL;
+  who_e = who_p = FS_PROC_NR;
+
+  build_dmap();                        /* build device table and map boot driver */
+  init_root();                 /* init root device and load super block */
+  init_select();               /* init select() structures */
+
+
+  vmp = &vmnt[0];              /* Should be the root filesystem */
+  if (vmp->m_dev == NO_DEV)
+       panic(__FILE__, "vfs: no root filesystem", NO_NUM);
+  root_vp= vmp->m_root_node;
+
+  /* The root device can now be accessed; set process directories. */
+  for (rfp=&fproc[0]; rfp < &fproc[NR_PROCS]; rfp++) {
+       FD_ZERO(&(rfp->fp_filp_inuse));
+       if (rfp->fp_pid != PID_FREE) {
+                
+               dup_vnode(root_vp);
+                rfp->fp_rd = root_vp;
+               dup_vnode(root_vp);
+                rfp->fp_wd = root_vp;
+               
+       } else  rfp->fp_endpoint = NONE;
+  }
+
+  system_hz = sys_hz();
+
+  SANITYCHECK;
+
+#if DO_SANITYCHECKS
+  FIXME("VFS: DO_SANITYCHECKS is on");
+#endif
+
+  return(OK);
+}
+
 /*===========================================================================*
  *                             get_work                                     *
  *===========================================================================*/
@@ -347,88 +433,6 @@ int result;                        /* result of the call (usually OK or error #) */
        result, whom, s);
 }
 
-/*===========================================================================*
- *                             fs_init                                      *
- *===========================================================================*/
-PRIVATE void fs_init()
-{
-/* Initialize global variables, tables, etc. */
-  int s;
-  register struct fproc *rfp;
-  struct vmnt *vmp;
-  struct vnode *root_vp;
-  message mess;
-
-  /* Clear endpoint field */
-  last_login_fs_e = NONE;
-  mount_m_in.m1_p3 = (char *) NONE;
-
-  /* Initialize the process table with help of the process manager messages. 
-   * Expect one message for each system process with its slot number and pid. 
-   * When no more processes follow, the magic process number NONE is sent. 
-   * Then, stop and synchronize with the PM.
-   */
-  do {
-       if (OK != (s=sef_receive(PM_PROC_NR, &mess)))
-               panic(__FILE__,"FS couldn't receive from PM", s);
-
-       if (mess.m_type != PM_INIT)
-               panic(__FILE__, "unexpected message from PM", mess.m_type);
-
-       if (NONE == mess.PM_PROC) break; 
-
-       rfp = &fproc[mess.PM_SLOT];
-       rfp->fp_pid = mess.PM_PID;
-       rfp->fp_endpoint = mess.PM_PROC;
-       rfp->fp_realuid = (uid_t) SYS_UID;
-       rfp->fp_effuid = (uid_t) SYS_UID;
-       rfp->fp_realgid = (gid_t) SYS_GID;
-       rfp->fp_effgid = (gid_t) SYS_GID;
-       rfp->fp_umask = ~0;
-       rfp->fp_grant = GRANT_INVALID;
-       rfp->fp_blocked_on = FP_BLOCKED_ON_NONE;
-       rfp->fp_revived = NOT_REVIVING;
-   
-  } while (TRUE);                      /* continue until process NONE */
-  mess.m_type = OK;                    /* tell PM that we succeeded */
-  s = send(PM_PROC_NR, &mess);         /* send synchronization message */
-
-  /* All process table entries have been set. Continue with FS initialization.
-   * Certain relations must hold for the file system to work at all. Some 
-   * extra block_size requirements are checked at super-block-read-in time.
-   */
-  if (OPEN_MAX > 127) panic(__FILE__,"OPEN_MAX > 127", NO_NUM);
-  
-  /* The following initializations are needed to let dev_opcl succeed .*/
-  fp = (struct fproc *) NULL;
-  who_e = who_p = FS_PROC_NR;
-
-  build_dmap();                        /* build device table and map boot driver */
-  init_root();                 /* init root device and load super block */
-  init_select();               /* init select() structures */
-
-
-  vmp = &vmnt[0];              /* Should be the root filesystem */
-  if (vmp->m_dev == NO_DEV)
-       panic(__FILE__, "vfs:fs_init: no root filesystem", NO_NUM);
-  root_vp= vmp->m_root_node;
-
-  /* The root device can now be accessed; set process directories. */
-  for (rfp=&fproc[0]; rfp < &fproc[NR_PROCS]; rfp++) {
-       FD_ZERO(&(rfp->fp_filp_inuse));
-       if (rfp->fp_pid != PID_FREE) {
-                
-               dup_vnode(root_vp);
-                rfp->fp_rd = root_vp;
-               dup_vnode(root_vp);
-                rfp->fp_wd = root_vp;
-               
-       } else  rfp->fp_endpoint = NONE;
-  }
-
-  system_hz = sys_hz();
-}
-
 /*===========================================================================*
  *                             init_root                                    *
  *===========================================================================*/
index 1951464384072fcd7743d6146a45b4e9b2feef92..091c5a3241e339b5190e5629b3287f770b62a322 100644 (file)
@@ -144,8 +144,7 @@ PUBLIC int do_fork(message *msg)
   vmc->vm_flags &= (VMF_INUSE|VMF_SEPARATE|VMF_HASPT);
 
   /* inherit the priv call bitmaps */
-  memcpy(&vmc->vm_call_priv_mask, &vmp->vm_call_priv_mask,
-        sizeof(vmc->vm_call_priv_mask));
+  memcpy(&vmc->vm_call_mask, &vmp->vm_call_mask, sizeof(vmc->vm_call_mask));
 
   /* Tell kernel about the (now successful) FORK. */
   if((r=sys_fork(vmp->vm_endpoint, childproc,
index 65d38517d44a88bc0ad6214d6dad49994b298147..7524eb344b9e89b6103fe608c39289fcec4e8b98 100644 (file)
@@ -18,6 +18,7 @@
 #include <minix/const.h>
 #include <minix/bitmap.h>
 #include <minix/crtso.h>
+#include <minix/rs.h>
 
 #include <errno.h>
 #include <string.h>
@@ -40,21 +41,11 @@ extern int missing_spares;
 #include "../../kernel/config.h" 
 #include "../../kernel/proc.h"
 
-typedef u32_t mask_t;
-#define MINEPM 0
-#define MAXMASK (sizeof(mask_t)*8)
-#define ANYEPM (MINEPM+MAXMASK-1)
-#define NEEDACL (MINEPM+MAXMASK-2)
-#define MAXEPM (NEEDACL-1)
-#define EPM(e) ((1L) << ((e)-MINEPM))
-#define EPMOK(mask, ep) (((mask) & EPM(ANYEPM)) || ((ep) >= MINEPM && (ep) <= MAXEPM && (EPM(ep) & (mask))))
-
 /* Table of calls and a macro to test for being in range. */
 struct {
-       mask_t vmc_callers;             /* bitmap of endpoint numbers */
        int (*vmc_func)(message *);     /* Call handles message. */
        char *vmc_name;                 /* Human-readable string. */
-} vm_calls[VM_NCALLS];
+} vm_calls[NR_VM_CALLS];
 
 /* Macro to verify call range and map 'high' range to 'base' range
  * (starting at 0) in one. Evaluates to zero-based call number if call
@@ -64,11 +55,14 @@ struct {
                        (c) < VM_RQ_BASE + ELEMENTS(vm_calls)) ?        \
                        ((c) - VM_RQ_BASE) : -1)
 
-FORWARD _PROTOTYPE(void vm_init, (void));
+FORWARD _PROTOTYPE(int map_service, (struct rprocpub *rpub));
 FORWARD _PROTOTYPE(int vm_acl_ok, (endpoint_t caller, int call));
 
+extern int unmap_ok;
+
 /* SEF functions and variables. */
 FORWARD _PROTOTYPE( void sef_local_startup, (void) );
+FORWARD _PROTOTYPE( int sef_cb_init_fresh, (int type, sef_init_info_t *info) );
 
 /*===========================================================================*
  *                             main                                         *
@@ -81,19 +75,6 @@ PUBLIC int main(void)
   /* SEF local startup. */
   sef_local_startup();
 
-#if SANITYCHECKS
-  incheck = nocheck = 0;
-  FIXME("VM SANITYCHECKS are on");
-#endif
-
-  vm_paged = 1;
-  env_parse("vm_paged", "d", 0, &vm_paged, 0, 1);
-#if SANITYCHECKS
-  env_parse("vm_sanitychecklevel", "d", 0, &vm_sanitychecklevel, 0, SCL_MAX);
-#endif
-
-  vm_init();
-
   /* This is VM's main loop. */
   while (TRUE) {
        int r, c;
@@ -171,26 +152,41 @@ PUBLIC int main(void)
  *===========================================================================*/
 PRIVATE void sef_local_startup()
 {
+  /* Register init callbacks. */
+  sef_setcb_init_fresh(sef_cb_init_fresh);
+  sef_setcb_init_restart(sef_cb_init_restart_fail);
+
   /* No live update support for now. */
 
   /* Let SEF perform startup. */
   sef_startup();
 }
 
-extern int unmap_ok;
-
 /*===========================================================================*
- *                             vm_init                                      *
+ *                             sef_cb_init_fresh                            *
  *===========================================================================*/
-PRIVATE void vm_init(void)
+PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
 {
+/* Initialize the vm server. */
        int s, i;
        int click, clicksforgotten = 0;
        struct memory mem_chunks[NR_MEMS];
        struct boot_image image[NR_BOOT_PROCS];
        struct boot_image *ip;
+       struct rprocpub rprocpub[NR_BOOT_PROCS];
        phys_bytes limit = 0;
 
+#if SANITYCHECKS
+       incheck = nocheck = 0;
+       FIXME("VM SANITYCHECKS are on");
+#endif
+
+       vm_paged = 1;
+       env_parse("vm_paged", "d", 0, &vm_paged, 0, 1);
+#if SANITYCHECKS
+       env_parse("vm_sanitychecklevel", "d", 0, &vm_sanitychecklevel, 0, SCL_MAX);
+#endif
+
        /* Get chunks of available memory. */
        get_mem_chunks(mem_chunks);
 
@@ -285,7 +281,7 @@ PRIVATE void vm_init(void)
                        vmp->vm_arch.vm_seg[D].mem_len;
 
                if(pt_new(&vmp->vm_pt) != OK)
-                       vm_panic("vm_init: no new pagetable", NO_NUM);
+                       vm_panic("VM: no new pagetable", NO_NUM);
 #define BASICSTACK VM_PAGE_SIZE
                old_stacktop = CLICK2ABS(vmp->vm_arch.vm_seg[S].mem_vir +
                                vmp->vm_arch.vm_seg[S].mem_len);
@@ -314,17 +310,11 @@ PRIVATE void vm_init(void)
        }
 
        /* Set up table of calls. */
-#define CALLMAP(code, func, thecaller) { int i;                              \
+#define CALLMAP(code, func) { int i;                         \
        if((i=CALLNUMBER(code)) < 0) { vm_panic(#code " invalid", (code)); } \
-       if(i >= VM_NCALLS) { vm_panic(#code " invalid", (code)); } \
+       if(i >= NR_VM_CALLS) { vm_panic(#code " invalid", (code)); } \
        vm_calls[i].vmc_func = (func);                                \
        vm_calls[i].vmc_name = #code;                                 \
-       if(((thecaller) < MINEPM || (thecaller) > MAXEPM)               \
-               && (thecaller) != ANYEPM                                \
-               && (thecaller) != NEEDACL ) {                           \
-               vm_panic(#thecaller " invalid", (code));                \
-       }                                                               \
-       vm_calls[i].vmc_callers |= EPM(thecaller);                    \
 }
 
        /* Set call table to 0. This invalidates all calls (clear
@@ -332,35 +322,35 @@ PRIVATE void vm_init(void)
         */
        memset(vm_calls, 0, sizeof(vm_calls));
 
-       /* Requests from PM (restricted to be from PM only). */
-       CALLMAP(VM_EXIT, do_exit, PM_PROC_NR);
-       CALLMAP(VM_FORK, do_fork, PM_PROC_NR);
-       CALLMAP(VM_BRK, do_brk, PM_PROC_NR);
-       CALLMAP(VM_EXEC_NEWMEM, do_exec_newmem, PM_PROC_NR);
-       CALLMAP(VM_PUSH_SIG, do_push_sig, PM_PROC_NR);
-       CALLMAP(VM_WILLEXIT, do_willexit, PM_PROC_NR);
-       CALLMAP(VM_ADDDMA, do_adddma, PM_PROC_NR);
-       CALLMAP(VM_DELDMA, do_deldma, PM_PROC_NR);
-       CALLMAP(VM_GETDMA, do_getdma, PM_PROC_NR);
-       CALLMAP(VM_NOTIFY_SIG, do_notify_sig, PM_PROC_NR);
-
-       /* Requests from RS */
-       CALLMAP(VM_RS_SET_PRIV, do_rs_set_priv, RS_PROC_NR);
-
-       /* Requests from userland (source unrestricted). */
-       CALLMAP(VM_MMAP, do_mmap, ANYEPM);
-       CALLMAP(VM_MUNMAP, do_munmap, ANYEPM);
-       CALLMAP(VM_MUNMAP_TEXT, do_munmap, ANYEPM);
-       CALLMAP(VM_MAP_PHYS, do_map_phys, ANYEPM); /* Does its own checking. */
-       CALLMAP(VM_UNMAP_PHYS, do_unmap_phys, ANYEPM);
-
-       /* Requests from userland (anyone can call but need an ACL bit). */
-       CALLMAP(VM_REMAP, do_remap, NEEDACL);
-       CALLMAP(VM_GETPHYS, do_get_phys, NEEDACL);
-       CALLMAP(VM_SHM_UNMAP, do_shared_unmap, NEEDACL);
-       CALLMAP(VM_GETREF, do_get_refcount, NEEDACL);
-       CALLMAP(VM_CTL, do_ctl, NEEDACL);
-       CALLMAP(VM_QUERY_EXIT, do_query_exit, NEEDACL);
+       /* Basic VM calls. */
+       CALLMAP(VM_MMAP, do_mmap);
+       CALLMAP(VM_MUNMAP, do_munmap);
+       CALLMAP(VM_MUNMAP_TEXT, do_munmap);
+       CALLMAP(VM_MAP_PHYS, do_map_phys);
+       CALLMAP(VM_UNMAP_PHYS, do_unmap_phys);
+
+       /* Calls from PM. */
+       CALLMAP(VM_EXIT, do_exit);
+       CALLMAP(VM_FORK, do_fork);
+       CALLMAP(VM_BRK, do_brk);
+       CALLMAP(VM_EXEC_NEWMEM, do_exec_newmem);
+       CALLMAP(VM_PUSH_SIG, do_push_sig);
+       CALLMAP(VM_WILLEXIT, do_willexit);
+       CALLMAP(VM_ADDDMA, do_adddma);
+       CALLMAP(VM_DELDMA, do_deldma);
+       CALLMAP(VM_GETDMA, do_getdma);
+       CALLMAP(VM_NOTIFY_SIG, do_notify_sig);
+
+       /* Calls from RS */
+       CALLMAP(VM_RS_SET_PRIV, do_rs_set_priv);
+
+       /* Generic calls. */
+       CALLMAP(VM_REMAP, do_remap);
+       CALLMAP(VM_GETPHYS, do_get_phys);
+       CALLMAP(VM_SHM_UNMAP, do_shared_unmap);
+       CALLMAP(VM_GETREF, do_get_refcount);
+       CALLMAP(VM_CTL, do_ctl);
+       CALLMAP(VM_QUERY_EXIT, do_query_exit);
 
        /* Sanity checks */
        if(find_kernel_top() >= VM_PROCSTART)
@@ -372,6 +362,41 @@ PRIVATE void vm_init(void)
        /* Unmap our own low pages. */
        unmap_ok = 1;
        _minix_unmapzero();
+
+       /* Map all the services in the boot image. */
+       if((s = sys_safecopyfrom(RS_PROC_NR, info->rproctab_gid, 0,
+               (vir_bytes) rprocpub, sizeof(rprocpub), S)) != OK) {
+               panic("VM", "sys_safecopyfrom failed", s);
+       }
+       for(i=0;i < NR_BOOT_PROCS;i++) {
+               if(rprocpub[i].in_use) {
+                       if((s = map_service(&rprocpub[i])) != OK) {
+                               vm_panic("unable to map service", s);
+                       }
+               }
+       }
+
+       return(OK);
+}
+
+/*===========================================================================*
+ *                            map_service                                   *
+ *===========================================================================*/
+PRIVATE int map_service(rpub)
+struct rprocpub *rpub;
+{
+/* Map a new service by initializing its call mask. */
+       int r, proc_nr;
+
+       if ((r = vm_isokendpt(rpub->endpoint, &proc_nr)) != OK) {
+               return r;
+       }
+
+       /* Copy the call mask. */
+       memcpy(&vmproc[proc_nr].vm_call_mask, &rpub->vm_call_mask,
+               sizeof(vmproc[proc_nr].vm_call_mask));
+
+       return(OK);
 }
 
 /*===========================================================================*
@@ -381,23 +406,14 @@ PRIVATE int vm_acl_ok(endpoint_t caller, int call)
 {
        int n, r;
 
-       /* Some calls are always allowed by some, or all, processes. */
-       if(EPMOK(vm_calls[call].vmc_callers, caller)) {
-               return OK;
-       }
-
        if ((r = vm_isokendpt(caller, &n)) != OK)
                vm_panic("VM: from strange source.", caller);
 
-       /* Other calls need an ACL bit. */
-       if (!(vm_calls[call].vmc_callers & EPM(NEEDACL))) {
-               return EPERM;
-       }
-       if (!GET_BIT(vmproc[n].vm_call_priv_mask, call)) {
-               printf("VM: no ACL for %s for %d\n",
-                       vm_calls[call].vmc_name, caller);
+       /* See if the call is allowed. */
+       if (!GET_BIT(vmproc[n].vm_call_mask, call)) {
                return EPERM;
        }
 
        return OK;
 }
+
index 5c1a74538c577aba6a36daaf826e6f589128da0a..1eb194f6106522a279171023c3adfb80fcd6783b 100644 (file)
@@ -46,8 +46,8 @@ PUBLIC int do_rs_set_priv(message *m)
 
        if (m->VM_RS_BUF) {
                r = sys_datacopy(m->m_source, (vir_bytes) m->VM_RS_BUF,
-                                SELF, (vir_bytes) vmp->vm_call_priv_mask,
-                                sizeof(vmp->vm_call_priv_mask));
+                                SELF, (vir_bytes) vmp->vm_call_mask,
+                                sizeof(vmp->vm_call_mask));
                if (r != OK)
                        return r;
        }
index 47beedaa7687ec722a2c0f1a876db1e873f20185..dc840956b277f2f024e66345c261bbbc9256de50 100644 (file)
@@ -32,8 +32,7 @@ struct vmproc {
        /* Heap for brk() to extend. */
        struct vir_region *vm_heap;
 
-#define VM_CALL_PRIV_MASK_SIZE BITMAP_CHUNKS(VM_NCALLS)
-       bitchunk_t vm_call_priv_mask[VM_CALL_PRIV_MASK_SIZE];
+       bitchunk_t vm_call_mask[VM_CALL_MASK_SIZE];
 
        /* State for requests pending to be done to vfs on behalf of
         * this process.