home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Source Code 1993 July / THE_SOURCE_CODE_CD_ROM.iso / bsd_srcs / sys / kern / init_main.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-05-20  |  8.1 KB  |  332 lines

  1. /*
  2.  * Copyright (c) 1982, 1986, 1989, 1991 Regents of the University of California.
  3.  * All rights reserved.
  4.  *
  5.  * Redistribution and use in source and binary forms, with or without
  6.  * modification, are permitted provided that the following conditions
  7.  * are met:
  8.  * 1. Redistributions of source code must retain the above copyright
  9.  *    notice, this list of conditions and the following disclaimer.
  10.  * 2. Redistributions in binary form must reproduce the above copyright
  11.  *    notice, this list of conditions and the following disclaimer in the
  12.  *    documentation and/or other materials provided with the distribution.
  13.  * 3. All advertising materials mentioning features or use of this software
  14.  *    must display the following acknowledgement:
  15.  *    This product includes software developed by the University of
  16.  *    California, Berkeley and its contributors.
  17.  * 4. Neither the name of the University nor the names of its contributors
  18.  *    may be used to endorse or promote products derived from this software
  19.  *    without specific prior written permission.
  20.  *
  21.  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  22.  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  23.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  24.  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  25.  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  26.  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  27.  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  28.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  29.  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  30.  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  31.  * SUCH DAMAGE.
  32.  *
  33.  *    @(#)init_main.c    7.41 (Berkeley) 5/15/91
  34.  */
  35.  
  36. #include "param.h"
  37. #include "filedesc.h"
  38. #include "kernel.h"
  39. #include "mount.h"
  40. #include "map.h"
  41. #include "proc.h"
  42. #include "resourcevar.h"
  43. #include "signalvar.h"
  44. #include "systm.h"
  45. #include "vnode.h"
  46. #include "seg.h"
  47. #include "conf.h"
  48. #include "buf.h"
  49. #include "clist.h"
  50. #include "malloc.h"
  51. #include "protosw.h"
  52. #include "reboot.h"
  53. #include "user.h"
  54.  
  55. #include "ufs/quota.h"
  56.  
  57. #include "machine/cpu.h"
  58.  
  59. #include "vm/vm.h"
  60.  
  61. char    copyright[] =
  62. "Copyright (c) 1982,1986,1989,1991 The Regents of the University of California.\nAll rights reserved.\n\n";
  63.  
  64. /*
  65.  * Components of process 0;
  66.  * never freed.
  67.  */
  68. struct    session session0;
  69. struct    pgrp pgrp0;
  70. struct    proc proc0;
  71. struct    pcred cred0;
  72. struct    filedesc0 filedesc0;
  73. struct    plimit limit0;
  74. struct    vmspace vmspace0;
  75. struct    proc *curproc = &proc0;
  76. struct    proc *initproc, *pageproc;
  77.  
  78. int    cmask = CMASK;
  79. extern    struct user *proc0paddr;
  80. extern    int (*mountroot)();
  81.  
  82. struct    vnode *rootvp, *swapdev_vp;
  83. int    boothowto;
  84.  
  85. /*
  86.  * System startup; initialize the world, create process 0,
  87.  * mount root filesystem, and fork to create init and pagedaemon.
  88.  * Most of the hard work is done in the lower-level initialization
  89.  * routines including startup(), which does memory initialization
  90.  * and autoconfiguration.
  91.  */
  92. main()
  93. {
  94.     register int i;
  95.     register struct proc *p;
  96.     register struct filedesc0 *fdp;
  97.     int s, rval[2];
  98.  
  99.     /*
  100.      * Initialize curproc before any possible traps/probes
  101.      * to simplify trap processing.
  102.      */
  103.     p = &proc0;
  104.     curproc = p;
  105.     /*
  106.      * Attempt to find console and initialize
  107.      * in case of early panic or other messages.
  108.      */
  109.     consinit();
  110.     printf(copyright);
  111.  
  112.     vm_mem_init();
  113.     kmeminit();
  114.     cpu_startup();
  115.  
  116.     /*
  117.      * set up system process 0 (swapper)
  118.      */
  119.     p = &proc0;
  120.     curproc = p;
  121.  
  122.     allproc = p;
  123.     p->p_prev = &allproc;
  124.     p->p_pgrp = &pgrp0;
  125.     pgrphash[0] = &pgrp0;
  126.     pgrp0.pg_mem = p;
  127.     pgrp0.pg_session = &session0;
  128.     session0.s_count = 1;
  129.     session0.s_leader = p;
  130.  
  131.     p->p_flag = SLOAD|SSYS;
  132.     p->p_stat = SRUN;
  133.     p->p_nice = NZERO;
  134.     bcopy("swapper", p->p_comm, sizeof ("swapper"));
  135.  
  136.     /*
  137.      * Setup credentials
  138.      */
  139.     cred0.p_refcnt = 1;
  140.     p->p_cred = &cred0;
  141.     p->p_ucred = crget();
  142.     p->p_ucred->cr_ngroups = 1;    /* group 0 */
  143.  
  144.     /*
  145.      * Create the file descriptor table for process 0.
  146.      */
  147.     fdp = &filedesc0;
  148.     p->p_fd = &fdp->fd_fd;
  149.     fdp->fd_fd.fd_refcnt = 1;
  150.     fdp->fd_fd.fd_cmask = cmask;
  151.     fdp->fd_fd.fd_ofiles = fdp->fd_dfiles;
  152.     fdp->fd_fd.fd_ofileflags = fdp->fd_dfileflags;
  153.     fdp->fd_fd.fd_nfiles = NDFILE;
  154.  
  155.     /*
  156.      * Set initial limits
  157.      */
  158.     p->p_limit = &limit0;
  159.     for (i = 0; i < sizeof(p->p_rlimit)/sizeof(p->p_rlimit[0]); i++)
  160.         limit0.pl_rlimit[i].rlim_cur =
  161.             limit0.pl_rlimit[i].rlim_max = RLIM_INFINITY;
  162.     limit0.pl_rlimit[RLIMIT_OFILE].rlim_cur = NOFILE;
  163.     limit0.pl_rlimit[RLIMIT_NPROC].rlim_cur = MAXUPRC;
  164.     limit0.p_refcnt = 1;
  165.  
  166.     /*
  167.      * Allocate a prototype map so we have something to fork
  168.      */
  169.     p->p_vmspace = &vmspace0;
  170.     vmspace0.vm_refcnt = 1;
  171.     pmap_pinit(&vmspace0.vm_pmap);
  172.     vm_map_init(&p->p_vmspace->vm_map, round_page(VM_MIN_ADDRESS),
  173.         trunc_page(VM_MAX_ADDRESS), TRUE);
  174.     vmspace0.vm_map.pmap = &vmspace0.vm_pmap;
  175.     p->p_addr = proc0paddr;                /* XXX */
  176.  
  177.     /*
  178.      * We continue to place resource usage info
  179.      * and signal actions in the user struct so they're pageable.
  180.      */
  181.     p->p_stats = &p->p_addr->u_stats;
  182.     p->p_sigacts = &p->p_addr->u_sigacts;
  183.  
  184.     rqinit();
  185.  
  186.     /*
  187.      * configure virtual memory system,
  188.      * set vm rlimits
  189.      */
  190.     vm_init_limits(p);
  191.  
  192.     /*
  193.      * Initialize the file systems.
  194.      *
  195.      * Get vnodes for swapdev and rootdev.
  196.      */
  197.     vfsinit();
  198.     if (bdevvp(swapdev, &swapdev_vp) || bdevvp(rootdev, &rootvp))
  199.         panic("can't setup bdevvp's");
  200.  
  201.     startrtclock();
  202. #if defined(vax)
  203. #include "kg.h"
  204. #if NKG > 0
  205.     startkgclock();
  206. #endif
  207. #endif
  208.  
  209.     /*
  210.      * Initialize tables, protocols, and set up well-known inodes.
  211.      */
  212.     mbinit();
  213.     cinit();
  214. #ifdef SYSVSHM
  215.     shminit();
  216. #endif
  217. #include "sl.h"
  218. #if NSL > 0
  219.     slattach();            /* XXX */
  220. #endif
  221. #include "loop.h"
  222. #if NLOOP > 0
  223.     loattach();            /* XXX */
  224. #endif
  225.     /*
  226.      * Block reception of incoming packets
  227.      * until protocols have been initialized.
  228.      */
  229.     s = splimp();
  230.     ifinit();
  231.     domaininit();
  232.     splx(s);
  233.  
  234. #ifdef GPROF
  235.     kmstartup();
  236. #endif
  237.  
  238.     /* kick off timeout driven events by calling first time */
  239.     roundrobin();
  240.     schedcpu();
  241.     enablertclock();        /* enable realtime clock interrupts */
  242.  
  243.     /*
  244.      * Set up the root file system and vnode.
  245.      */
  246.     if ((*mountroot)())
  247.         panic("cannot mount root");
  248.     /*
  249.      * Get vnode for '/'.
  250.      * Setup rootdir and fdp->fd_fd.fd_cdir to point to it.
  251.      */
  252.     if (VFS_ROOT(rootfs, &rootdir))
  253.         panic("cannot find root vnode");
  254.     fdp->fd_fd.fd_cdir = rootdir;
  255.     VREF(fdp->fd_fd.fd_cdir);
  256.     VOP_UNLOCK(rootdir);
  257.     fdp->fd_fd.fd_rdir = NULL;
  258.     swapinit();
  259.  
  260.     /*
  261.      * Now can look at time, having had a chance
  262.      * to verify the time from the file system.
  263.      */
  264.     boottime = p->p_stats->p_start = time;
  265.  
  266.     /*
  267.      * make init process
  268.      */
  269.     siginit(p);
  270.     if (fork(p, (void *) NULL, rval))
  271.         panic("fork init");
  272.     if (rval[1]) {
  273.         static char initflags[] = "-sf";
  274.         char *ip = initflags + 1;
  275.         vm_offset_t addr = 0;
  276.         extern int icode[];        /* user init code */
  277.         extern int szicode;        /* size of icode */
  278.  
  279.         /*
  280.          * Now in process 1.  Set init flags into icode,
  281.          * get a minimal address space, copy out "icode",
  282.          * and return to it to do an exec of init.
  283.          */
  284.         p = curproc;
  285.         initproc = p;
  286.         if (boothowto&RB_SINGLE)
  287.             *ip++ = 's';
  288. #ifdef notyet
  289.         if (boothowto&RB_FASTBOOT)
  290.             *ip++ = 'f';
  291. #endif
  292.         *ip++ = '\0';
  293.  
  294.         if (vm_allocate(&p->p_vmspace->vm_map, &addr,
  295.             round_page(szicode + sizeof(initflags)), FALSE) != 0 ||
  296.             addr != 0)
  297.             panic("init: couldn't allocate at zero");
  298.  
  299.         /* need just enough stack to exec from */
  300.         addr = trunc_page(USRSTACK - PAGE_SIZE);
  301.         if (vm_allocate(&p->p_vmspace->vm_map, &addr,
  302.             PAGE_SIZE, FALSE) != KERN_SUCCESS)
  303.             panic("vm_allocate init stack");
  304.         p->p_vmspace->vm_maxsaddr = (caddr_t)addr;
  305.         (void) copyout((caddr_t)icode, (caddr_t)0, (unsigned)szicode);
  306.         (void) copyout(initflags, (caddr_t)szicode, sizeof(initflags));
  307.         return;            /* returns to icode */
  308.     }
  309.  
  310.     /*
  311.      * Start up pageout daemon (process 2).
  312.      */
  313.     if (fork(p, (void *) NULL, rval))
  314.         panic("fork pager");
  315.     if (rval[1]) {
  316.         /*
  317.          * Now in process 2.
  318.          */
  319.         p = curproc;
  320.         pageproc = p;
  321.         p->p_flag |= SLOAD|SSYS;        /* XXX */
  322.         bcopy("pagedaemon", curproc->p_comm, sizeof ("pagedaemon"));
  323.         vm_pageout();
  324.         /*NOTREACHED*/
  325.     }
  326.  
  327.     /*
  328.      * enter scheduling loop
  329.      */
  330.     sched();
  331. }
  332.