home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 15 / 15.iso / s / s053 / 8.ddi / usr / include / sys / evsys.h < prev    next >
Encoding:
C/C++ Source or Header  |  1990-12-08  |  60.9 KB  |  1,850 lines

  1. /*    Copyright (c) 1990 UNIX System Laboratories, Inc.    */
  2. /*    Copyright (c) 1984, 1986, 1987, 1988, 1989, 1990 AT&T    */
  3. /*      All Rights Reserved      */
  4.  
  5. /*    THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF         */
  6. /*    UNIX System Laboratories, Inc.                         */
  7. /*    The copyright notice above does not evidence any       */
  8. /*    actual or intended publication of such source code.    */
  9.  
  10. #ifndef _SYS_EVSYS_H
  11. #define _SYS_EVSYS_H
  12.  
  13. #ident    "@(#)/usr/include/sys/evsys.h.sl 1.1 4.0 12/08/90 34742 AT&T-USL"
  14. /*            File Contents
  15. **            =============
  16. **
  17. **    This file contains information used in the implementation
  18. **    of the events VFS.  It is intended for inclusion only in
  19. **    the kernel.  User programs and library routines should not
  20. **    need this file.
  21. */
  22.  
  23.  
  24. /*            Required Header Files
  25. **            =====================
  26. **
  27. **    The following header files must be includes before including
  28. **    this file.
  29. **
  30. **        REQUIRES    sys/types.h
  31. **        REQUIRES    sys/signal.h
  32. **        REQUIRES    sys/evecb.h
  33. **        REQUIRES    sys/hrtcntl.h
  34. **        REQUIRES    sys/priocntl.h
  35. **        REQUIRES    sys/procset.h
  36. **        REQUIRES    sys/events.h
  37. **        REQUIRES    sys/vnode.h
  38. **        REQUIRES    sys.cred.h
  39. */
  40.  
  41. /*            Miscellaneous Defines
  42. **            =====================
  43. **
  44. **    The following defines are just convenient to have around.
  45. */
  46.  
  47. #ifdef _KERNEL
  48.  
  49. #define    TRUE    1
  50. #define    FALSE    0
  51. #define    NULL    0
  52. #define    ERROR    (-1)
  53. #define    ZERO    0
  54.  
  55. #endif    /* _KERNEL    */
  56.  
  57. /*    The following define is used to represent an unused structure.
  58. **    The value must not be a legal file descriptor and must also
  59. **    not be equal to EQ_NOQUEUE (defined in events.h).  For an
  60. **    example of where this is used, see ev_main.c/ev_sig_initinfo.
  61. */
  62.  
  63. #define    EQ_UNUSED    (-1)
  64.  
  65. /*    The following are used as arguments to functions ev_mem_alloc,
  66. **    ev_kev_post, etc. to indicate whether to wait or not.  Do not
  67. **    change the values of these symbols.
  68. */
  69.  
  70. typedef enum evwait {
  71.     EV_NOWAIT,    /* Do not wait.                */
  72.     EV_WAIT        /* Wait if necessary.            */
  73. } evwait_t;
  74.  
  75. /*            Events VFS Parameter Defines
  76. **            ============================
  77. **
  78. **    The following defines set parameters of the events file
  79. **    system type which are not intended to be changable by an
  80. **    administrator.
  81. */
  82.  
  83. #define    EV_NMSZ        18        /* Maximum length of an    */
  84.                     /* events queue name.    */
  85. #define    EV_SLPPRI_INT    (PZERO + 1)    /* Our sleep priority    */
  86.                     /* when we want to be    */
  87.                     /* interruptible.    */
  88. #define    EV_SLPPRI_NINT    PZERO        /* Our sleep priority    */
  89.                     /* when we want to be    */
  90.                     /* non-interruptible.    */
  91. #define    EV_ROOTINBR    2        /* I-number of our root    */
  92.                     /* inode.        */
  93.  
  94. #define    EV_BASEINBR    (EV_ROOTINBR + 1)
  95.                     /* Inode number of our    */
  96.                     /* first queue entry.    */
  97. #define    EV_NSIGS    (NSIG - 1)    /* Actual nbr of signals*/
  98.                     /* which are defined.    */
  99.                     /* NSIG is defined in    */
  100.                     /* sys/signal.h.    */
  101. #define    EV_BSIZE    1024        /* The block size for    */
  102.                     /* our file system.    */
  103.                     /* Must be a power of 2.*/
  104. #define    EV_L2BSIZE    10        /* The base 2 log of    */
  105.                     /* EV_BSIZE.        */
  106. #define    EV_FSNAME    "events"    /* The name of our VFS.    */
  107. #define    EV_PKNAME    "memory"    /* Our "pack name" for    */
  108.                     /* statvfs to return.    */
  109.  
  110. /*            General Typedefs
  111. **            ================
  112. **
  113. **    The following are some generally useful typedefs.
  114. */
  115.  
  116. typedef int        err_t;    /* Type of an error code.    */
  117.  
  118. /*    With ansi C, the best way to represent a general pointer is as
  119. **    a (void *).  However, (void *) will not be available in all
  120. **    old (pre-ansi) compilers.  Therefore, we define a general
  121. **    pointer type as follows.
  122. */
  123.  
  124. #if defined(__STDC__)
  125.     typedef void *    gptr_t;
  126. #else
  127.     typedef char *    gptr_t;
  128. #endif    /* __STDC__    */
  129.  
  130. /*            Miscellaneous Macros
  131. **            ====================
  132. **
  133. **    The following macro does an spl to the proper level for the
  134. **    events VFS.
  135. */
  136.  
  137. #define    spl_ev()    splhi()
  138.  
  139.  
  140. /*    The following macros translate between inode numbers and
  141. **    the corresponding queue entry.  Both macros assume that the
  142. **    queue referred to is an actual event queue and not the queue
  143. **    which represents our root directory.
  144. */
  145.  
  146. #define    ev_inbrtoqp(INBR)  (ev_actqp[(INBR) - EV_BASEINBR].eaq_qp)
  147. #define    ev_qptoinbr(QP)       (((QP)->evq_aqp - ev_actqp) + EV_BASEINBR)
  148.  
  149.  
  150. /*    The following macro converts a directory offset to an inode
  151. **    number.  It assumes that the directory entry is not for "." or
  152. **    ".." which are the first two (pseudo) entries.
  153. */
  154.  
  155. #define    ev_dotoinbr(DO)    (((DO) / EV_DIRSZ) - 2 + EV_BASEINBR)
  156.  
  157.  
  158. /*    The following macro defines the size of a message queue.
  159. **    It counts each event as using sizeof(event_t) bytes plus
  160. **    whatever space is used by the type dependent data.  Data in
  161. **    the ev_data field (EF_QUICKD set) or in shared memory (EF_SHM
  162. **    set) is not counted.
  163. */
  164.  
  165. #define    ev_qsize(QP)    ((QP)->evq_nevents * sizeof(event_t) + \
  166.              (QP)->evq_memsize)
  167.  
  168. /*    The following macro converts a size in bytes to a size in
  169. **    blocks where the block size is that of the events VFS.  The
  170. **    conversion is done by rounding up.
  171. */
  172.  
  173. #define    ev_bytestoblks(BY)  (((BY) + EV_BSIZE - 1) >> EV_L2BSIZE)
  174.  
  175. /*            Miscellaneous Macros (Continued)
  176. **            ================================
  177. **
  178. **    The following macro rounds the value "VAL" up to the next "BND"
  179. **    boundary where "BND" must be a power of 2.
  180. */
  181.  
  182. #define    round(VAL, BND)    (((VAL) + (BND) - 1) & ~((BND) - 1))
  183.  
  184. /*    Get the absolute value of a number.
  185. */
  186.  
  187. #define    abs(VAL)    ((VAL) < 0  ?  -(VAL)  :  (VAL))
  188.  
  189. /*    Get the minimum of two values.
  190. */
  191.  
  192. #define    min(A, B)    ((A) <= (B) ? (A) : (B))
  193.  
  194. /*
  195. **    The following macro is used to reduce the number of
  196. **    unnecessary calls to ev_istrap().
  197. */
  198. #define    EV_ISTRAP(PRP)    ((PRP)->p_evpdp != NULL && ev_istrap(PRP))
  199.  
  200.  
  201. /*            Events Directory Structure (evdir_t)
  202. **            ====================================
  203. **
  204. **    The following is the structure of a directory in the events
  205. **    file system.  This directory is only conceptual.  It does
  206. **    not actually exist anywhere but we manufacture directory
  207. **    entries as needed to make "ls" and stuff like that work.
  208. **
  209. **    The closest thing we have to a directory is the "active queue
  210. **    list" which is an array of pointers to active queues.  The
  211. **    array itself is pointed to by ev_actqp.  The index into the
  212. **    array is used to construct an inumber for the queue.  The list
  213. **    is traversed sequentially to read the directory for readdir.
  214. */
  215.  
  216. typedef struct evdir {
  217.     ino_t    ev_d_ino;        /* The inode number.    */
  218.     char    ev_d_nm[EV_NMSZ + 1];    /* The name.        */
  219. } evdir_t;
  220.  
  221. #define    EV_DIRSZ    sizeof(evdir_t)
  222.  
  223. /*            Data Structure Overview
  224. **            =======================
  225. **
  226. **    We use a number of different data structures to maintain
  227. **    information about events and their connection to queues and
  228. **    processes.  The following pictures show the relationships
  229. **    among the various structures.  An arrow pointing in one
  230. **    direction indicates a singly linked list or a pointer.  An
  231. **    arrow pointing in both directions indicates a doubly-linked
  232. **    list or a ring.  Following the pictures are the declarations
  233. **    for all of these structures.
  234. **
  235. **    An evqueue_t structure represents an event queue.  The evkev_t
  236. **    structures represent events on this queue.  They are in fifo
  237. **    order.  Each queue has a ring of evexref_t structures attached
  238. **    to it.  This gives the set of expressions which have one or
  239. **    more terms referencing the queue.  When an event is posted to
  240. **    a queue, following the evexref_t ring shows what poll and trap
  241. **    expressions must be checked to see if the newly posted event
  242. **    caused them to be satisfied.
  243. **
  244. **    Each evexpr_t structure represents an evpoll or evtrap
  245. **    expression.  By an expression, we mean a list of terms (events)
  246. **    connected by the disjunction (EC_ONE or EC_ANY) or conjunction
  247. **    (EC_ALL) operator.  All of the outstanding trap expressions for
  248. **    a process are on a ring headed by the epd_exprs field of the
  249. **    evpd_t table.  The poll expressions are not on this list as
  250. **    their existence is more transitory and they are never held.
  251. **    They are found via the evexref_t list.  The following picture
  252. **    shows the relation of the evqueue_t, evkev_t, and evexref_t
  253. **    structures.
  254. **
  255. **    The events on a queue can be requested in either fifo or 
  256. **    priority order.  Currently, we must search the list of events
  257. **    on the queue linearly for the highest priority event when
  258. **    requested.  This can be very inefficient if there are many
  259. **    events on the queue.  It would be possible to improve this by
  260. **    keeping the events in priority order, perhaps by using a
  261. **    priority queue (heap) and then running a fifo list through them
  262. **    to satisfy fifo requests.  This is only important if queues
  263. **    accumulate long lists of events and then are polled or trapped
  264. **    in priority order.  Implementing such a priority queue is a
  265. **    possible future enhancement.
  266.  
  267. **            Data Structure Overview (Continued)
  268. **            ===================================
  269. **
  270. **
  271. **      _____________          ____________          ____________
  272. **      |        |         |             |          |         |
  273. **      | evqueue_t |/_______\|  evkev_t |/__________\|     evkev_t |
  274. **      |___________|\       /|__________|\          /|__________|
  275. **           /|\
  276. **            |
  277. **            |
  278. **            |
  279. **            |     ________________          ________________
  280. **          |     |              |            |              |
  281. **          |____\|  evexref_t   |/________\|  evexref_t   |
  282. **           /|______________|\        /|______________|
  283. **               |                  |
  284. **               |                  |
  285. **               |                  |
  286. **   __________     ______\|/_______          _______\|/______
  287. **   |        |     |              |            |              |
  288. **   | proc_t |/___\|   evexpr_t   |/________\|    evexpr_t  |
  289. **   |________|\   /|______________|\        /|______________|
  290. **              /|\                /|\
  291. **               |                  |
  292. **               |                  |
  293. **               |                  |
  294. **                  ______\|/_______          _______\|/______
  295. **            |               |          |              |
  296. **            |   evterm_t   |          |    evterm_t  |
  297. **            |______________|          |______________|
  298. **              /|\                /|\
  299. **               |                  |
  300. **               |                  |
  301. **               |                  |
  302. **                  ______\|/_______          _______\|/______
  303. **            |               |          |              |
  304. **            |   evterm_t   |          |    evterm_t  |
  305. **            |______________|          |______________|
  306.  
  307. **            Data Structure Overview (Continued)
  308. **            ===================================
  309. **
  310. **
  311. **    A satisfied poll or trap expression is represented by an 
  312. **    evsexpr_t structure.  These structures are stacked for nested 
  313. **    trap handler calls.  The top of the stack is pointed to by the
  314. **    epd_asexp member of the evpd_t structure.  Also on this stack 
  315. **    are satisfied poll expressions which have been retained after 
  316. **    the evpoll returned because there is data remaining and the 
  317. **    EF_DISCARD flag was not set or a file descriptor was passed with
  318. **    the event and not given to the caller yet.  Satisfied
  319. **    expressions of either type which have not yet been handled are
  320. **    linked together on a doubly linked ring headed by the
  321. **    epd_ppsexprs or epd_ptsexprs member of the evpd_t structure.
  322. **    The first list is for pending poll satisfied expressions and
  323. **    the second is for pending trap satisfied expressions.  The
  324. **    evsexpr_t structure points to the evexpr_t structure for the
  325. **    expression which is satisfied.  The evsexpr_t structure also
  326. **    contains a ring of evsterm_t structures, one for each term of
  327. **    the satisfied expression.
  328. **
  329. **    Each evsterm_t structure, in turn, points to the corresponding
  330. **    evterm_t structure.  Note that the number of satisfied terms may
  331. **    be less than the total number of terms so the two lists are not
  332. **    necessarily of the same size.  Only satisfied terms are on the
  333. **    satisfied expression's satisfied term ring while all terms of
  334. **    the user's expression are on the term ring.
  335. **    The following picture shows the use of the evsexpr_t and
  336. **    evsterm_t structures.
  337.  
  338. **            Data Structure Overview (Continued)
  339. **            ===================================
  340. **
  341. **  _________________     _______________                       _______________
  342. **  |               |     |             |                       |             |
  343. **  |    proc_t     |  __\|  evsexpr_t  |  ____________________\|  evsexpr_t  |
  344. **  |               |  | /|             |  |     _____________ /|             |
  345. **  |   epd_asexp   |__|  |  evse_next  |__|  __\|           |  |  evse_next  |
  346. **  |               |     |             |     | /|  evexpr_t |  |             |
  347. **  |   epd_ptsexpr |     |   evse_ep   |_____|  |           |  |   evse_ep   |
  348. **  |_______________|     |             |        |           |  |             |
  349. **          /|\           |   evse_stp  |        |   eve_tp  |  |   evse_stp  |
  350. **           |            |_____________|        |___________|  |_____________|
  351. **    ______\|/______           /|\                   /|\     
  352. **    |             |            |                     |      
  353. **    |  evsexpr_t  |     ______\|/______        _____\|/_____
  354. **    |             |     |             |  _____\|           |
  355. **    |             |     |   evsterm_t |  |    /|  evterm_t |
  356. **    |  evse_next  |     |             |  |     |           |
  357. **    |_____________|     |   evst_tp   |__|     |  evt_next |
  358. **          /|\           |             |        |___________|
  359. **           |            |  evst_next  |             /|\     
  360. **    ______\|/______     |_____________|              |      
  361. **    |             |           /|\              _____\|/_____
  362. **    |  evsexpr_t  |            |               |           |
  363. **    |             |     ______\|/______        |  evterm_t |
  364. **    |             |     |             |        |           |
  365. **    |  evse_next  |     |   evsterm_t |        |  evt_next |
  366. **    |_____________|     |             |        |___________|
  367. **                        |   evst_tp   |___          /|\
  368. **                        |             |  |           |
  369. **                        |  evst_next  |  |     _____\|/_____
  370. **                        |_____________|  |     |           |
  371. **                                         |____\|  evterm_t |
  372. **                                              /|           |
  373. **                                               |  evt_next |
  374. **                                               |___________|
  375.  
  376. **            Data Structure Overview (Continued)
  377. **            ===================================
  378. **
  379. **                                                    
  380. **
  381. **    The evtid_t structures are used to keep track of trap
  382. **    identifiers supplied as the "tid" argument of the evtrap
  383. **    function call.  There is a hash table used for looking up trap
  384. **    identifiers.  It is pointed to by ev_tidhtp and has evci_tidhts
  385. **    entries where evci_tidhts is in the evcinfo_t structure 
  386. **    described in events.h.  The hash table enables us to find the
  387. **    evtid_t structure for a particular tid quickly.  We must do
  388. **    this every time we process an evtrap system call.  In
  389. **    addition, every trap expression, represented by an evexpr_t
  390. **    structure, contains a pointer, eve_tidlp, to a list of pointers
  391. **    to evtid_t structures.  These are the trap ids which should be
  392. **    held when this trap is taken.  The evtid_t structure contains
  393. **    the level (etid_lvl) at which it is held or 0 if it is not
  394. **    currently held.  This can be compared with the trap level of
  395. **    the top entry on the epd_asexp active expression stack
  396. **    (evse_lvl).  The following picture shows the relation between
  397. **    the evtid_t structures, the hash table, and the evexpr_t
  398. **    structure and its reference list.
  399. **
  400. **
  401. **  
  402. ** 
  403. **    ________________
  404. **    |              |
  405. **    |   ev_tidhtp  |__
  406. **    |______________|  |
  407. **                      |
  408. **                      |
  409. **     _________________|
  410. **     |  __________     ___________     ___________
  411. **     |_\|        |     |         |     |         |
  412. **       /| tid    |/___\| evtid_t |/___\| evtid_t |
  413. **        | hash   |\   /|_________|\   /|_________|
  414. **        | table  |  .
  415. **        |        |  .  ___________     ___________     ___________
  416. **        |        |/___\|         |     |         |     |         |
  417. **        |________|\   /| evtid_t |/___\| evtid_t |/___\| evtid_t |
  418. **                       |_________|\   /|_________|\   /|_________|
  419. **                                           /|\            /|\
  420. **                                            |              | 
  421. **    _______________     ___________         |              |
  422. **    |             |  __\|         |         |              |
  423. **    |   evexpr_t  |  | /|  expr   |_________|              |
  424. **    |             |  |  |  tid    |                        |
  425. **    |  eve_tidlp  |__|  |  hold   |                        |
  426. **    |_____________|     |  list   |________________________|
  427. **                        |_________| 
  428. */
  429.  
  430. /*            The evlisthd_t Structure
  431. **            ========================
  432. **
  433. **    We use many doubly linked lists of structures in the events 
  434. **    VFS.  Most of these are maintained as a ring instead of a list
  435. **    with head and tail pointers.  The reason is that enqueueing and
  436. **    dequeueing are faster since no special test for an empty list
  437. **    is required.  The following structure is used to represent the
  438. **    head of a general doubly linked list or ring.  When used as a
  439. **    ring, it is empty when:
  440. **
  441. **        lh_first == lh_last == &lh_first
  442. **
  443. **    In order for this trick to work, the link fields for the ring 
  444. **    structure must be the first members of the structure.  We do
  445. **    this for various structures below.  In each case, it is
  446. **    indicated which members must not be moved.
  447. */
  448.  
  449. typedef struct evlisthd {
  450.     struct evlisthd    *lh_first;    /* First structure on    */
  451.                     /* list.        */
  452.     struct evlisthd    *lh_last;    /* Last structure on    */
  453.                     /* list.        */
  454. } evlisthd_t;
  455.  
  456. /*            The evterm_t Structure
  457. **            ======================
  458. **
  459. **    The following structure represents a term of a trap or poll
  460. **    expression.  All of the terms of an expression are linked
  461. **    together in order through the evt_next field.  The list of all
  462. **    the terms of an expression, in order, form the eve_terms ring in
  463. **    the evexpr_t structure.  The first two members of this structure
  464. **    must not be moved.
  465. */
  466.  
  467. typedef struct evterm {
  468.     struct evterm    *evt_next;    /* Next term in the    */
  469.                     /* expression.        */
  470.     struct evterm    *evt_prev;    /* Previous term in the    */
  471.                     /* expression.        */
  472.     event_t        evt_ev;        /* The event which the    */
  473.                     /* user specified.    */
  474.     vnode_t        *evt_vp;    /* Ptr to the vnode for */
  475.                     /* the event queue    */
  476.                     /* evt_ev.ev_eqd.    */
  477.     ushort        evt_seq;    /* Sequence nbr of this */
  478.                     /* term in the list of    */
  479.                     /* terms for the    */
  480.                     /* expression - zero    */
  481.                     /* origin.        */
  482. } evterm_t;
  483.  
  484. /*            The evexpr_t Structure
  485. **            ======================
  486. **
  487. **    The following structure represents a trap or poll expression.
  488. **    A doubly linked ring of these structures which represent all
  489. **    outstanding trap or poll expressions for a process is pointed
  490. **    to by the epd_exprs field of a evpd_t structure entry.  Note
  491. **    that the first two members of this structure must not be moved.
  492. */
  493.  
  494. typedef struct evexpr {
  495.     struct evexpr    *eve_next;    /* Next expression for    */
  496.                     /* this process.    */
  497.     struct evexpr    *eve_prev;    /* Previous  expression */
  498.                     /* for this process.    */
  499.     evlisthd_t    eve_terms;    /* The ring of terms in */
  500.                     /* the expression.    */
  501.     event_t        *eve_uevp;    /* Ptr to user's events */
  502.                     /* array.  This is     */
  503.                     /* where evpoll and    */
  504.                     /* evtrap return     */
  505.                     /* results.        */
  506.     struct proc    *eve_procp;    /* Ptr to process this    */
  507.                     /* expression is for.    */
  508.     void        (*eve_lfunc)();    /* Ptr to our library    */
  509.                     /* routine used to     */
  510.                     /* transfer to a user's    */
  511.                     /* trap handler.    */
  512.     void        (*eve_ufunc)();    /* Ptr to the user's    */
  513.                     /* trap handler     */
  514.                     /* function.        */
  515.     struct evtid    *eve_tidp;    /* Ptr to trap id     */
  516.                     /* struct for this trap    */
  517.                     /* expression.        */
  518.     pcparms_t    eve_schedpri;    /* Scheduling priority    */
  519.                     /* to be set when    */
  520.                     /* invoking a trap    */
  521.                     /* handler if the     */
  522.                     /* eve_trappri flag     */
  523.                     /* is set.        */
  524.     struct evtid    **eve_tidlp;    /* Ptr to an array of    */
  525.                     /* pointers to evtid_t    */
  526.                     /* structures.  The     */
  527.                     /* list of tids to be    */
  528.                     /* held when trapping    */
  529.                     /* on this expression.    */
  530.     ushort        eve_tidls;    /* Nbr of elements in    */
  531.                     /* the eve_tidlp array.    */
  532.     evpollcmds_t    eve_cmd;    /* Expression command.  */
  533.                     /* One of EC_ONE,     */
  534.                     /* EC_ANY, or EC_ALL.    */
  535.  
  536. /*            The evexpr_t Structure (Continued)
  537. **            ==================================
  538. */
  539.  
  540.     ushort        eve_poll    :1;    /* Set for an evpoll    */
  541.                     /* expression.  If not    */
  542.                     /* set, then an evtrap    */
  543.                     /* expression.        */
  544.     ushort        eve_trappri :1;    /* Set if a special    */
  545.                     /* priority was given    */
  546.                     /* with an evtrap.      */
  547.                     /* Never set when     */
  548.                     /* eve_poll is set.    */
  549.     ushort        eve_taken   :1;    /* Set if this         */
  550.                     /* expression has been    */
  551.                     /* satisfied but user's    */
  552.                     /* handler has not been    */
  553.                     /* called yet.  Don't    */
  554.                     /* try to satisfy it    */
  555.                     /* again.  Never set if    */
  556.                     /* eve_poll is.        */
  557.     ushort        eve_holdall :1;    /* Set if all future    */
  558.                     /* traps should be held    */
  559.                     /* when calling the    */
  560.                     /* handler for this     */
  561.                     /* expression.        */
  562.     ushort        eve_canned  :1;    /* Set if this trap    */
  563.                     /* expression has been    */
  564.                     /* cancelled.        */
  565.     ushort        eve_restart :1;    /* Set if restartable    */
  566.                     /* system calls should    */
  567.                     /* be restarted after    */
  568.                     /* trapping on this    */
  569.                     /* expression.  Never    */
  570.                     /* set if eve_poll is.    */
  571.     ushort        eve_astk : 1;    /* Set if we should    */
  572.                     /* switch to alternate    */
  573.                     /* stack before calling    */
  574.                     /* handler for this    */
  575.                     /* expression.        */
  576.     ushort        eve_nterms;    /* Number of terms in    */
  577.                     /* the event expression.*/
  578.     ushort        eve_refcnt;    /* Count of the number    */
  579.                     /* of evsexpr_t structs    */
  580.                     /* which are pointing     */
  581.                     /* to this expression.    */
  582. } evexpr_t;
  583.  
  584. /*            The evexref_t Structure
  585. **            =======================
  586. **
  587. **    The following structure is used to connect an event queue
  588. **    with the outstanding trap and poll expressions which reference
  589. **    the queue.  Each event queue points to a ring of evexref_t
  590. **    structures.  Each evexref_t structure points to one trap or
  591. **    poll expression as represented by an evexpr_t structure.  Each
  592. **    expression pointed to references the indicated queue in at
  593. **    least one of its terms.  The first two members of this
  594. **    structure must not be moved.
  595. */
  596.  
  597. typedef struct evexref {
  598.     struct evexref    *exr_next;    /* Ptr to next reference*/
  599.                     /* on the ring for this    */
  600.                     /* queue.        */
  601.     struct evexref    *exr_prev;    /* Ptr to previous    */
  602.                     /* reference on the     */
  603.                     /* ring for this queue.    */
  604.     evexpr_t    *exr_ep;    /* Ptr to the        */
  605.                     /* expression.        */
  606. } evexref_t;
  607.  
  608. /*            The evsterm_t Structure
  609. **            =======================
  610. **
  611. **    The following structure is used to represent a satisfied term
  612. **    of a satisfied expression.  All the satisfied terms of the
  613. **    satisfied expression are linked together through the evst_next
  614. **    field.  The start of the ring is the evse_sterms field of the
  615. **    evsexpr_t structure.  Note that this list will contain
  616. **    evsterm_t structures only for satisfied terms of the 
  617. **    expression.  This means that for EC_ONE and
  618. **    EC_ANY, there may be fewer terms in the evsterm_t set than in
  619. **    the evterm_t set for the expression.  The evst_tp field of the
  620. **    evsterm_t structure points to the evterm_t structure which is
  621. **    satisfied.  The evt_seq field of the evterm_t structure
  622. **    indicates which event in the user's event list the term
  623. **    corresponds to.  It is used to find the address of the user's
  624. **    event_t structure to which this satisfied term should be copied.
  625. **    The first two members of this structure must not be moved.
  626. */
  627.  
  628. typedef struct evsterm {
  629.     struct evsterm    *evst_next;    /* Next satisfied term.    */
  630.     struct evsterm    *evst_prev;    /* Previous satisfied    */
  631.                     /* term.        */
  632.     evterm_t    *evst_tp;    /* Ptr to the term    */
  633.                     /* which has been    */
  634.                     /* satisfied.        */
  635.     struct evkev    *evst_kevp;    /* Ptr to the event    */
  636.                     /* which satisfies the    */
  637.                     /* term.        */
  638. } evsterm_t;
  639.  
  640. /*            The evsexpr_t Structure
  641. **            =======================
  642. **
  643. **    This structure represents a satisfied poll or trap expression.
  644. **    It will be saved for poll only if the satisfied expression must
  645. **    be retained after the evpoll returns.  This occurs if not all
  646. **    of the data was returned and EF_DISCARD was not set for at
  647. **    least one of the terms in the expression or if a file descriptor
  648. **    was passed with the event and has not yet been given to the
  649. **    receiver of the event.  For trap, there will be one evsexpr_t
  650. **    structure for each active trap handler call.  Note that these
  651. **    can be nested and even recursive since the handler can unblock
  652. **    the automatic block which we impose when we call it.  The
  653. **    evsexpr_t structures are stacked for nested trap handler calls.
  654. **    The top (current) entry is pointed to by the epd_asexpr field of
  655. **    the evpd_t structure.  Satisfied *xpression structures for trap
  656. **    handlers which have not yet been called are doubly linked on a
  657. **    ring whose header is epd_ptsexprs.  Satisfied expressions for
  658. **    polls which have not yet been received by the process doing the
  659. **    poll are on a similar ring whose head is epd_ppsexprs.  The
  660. **    first two members of this structure must not be moved.
  661. */
  662.  
  663. /*            The evsexpr_t Structure (Continued)
  664. **            ===================================
  665. */
  666.  
  667. typedef struct evsexpr {
  668.     struct evsexpr    *evse_next;    /* Ptr to next        */
  669.                     /* satisfied expression    */
  670.                     /* on the stack or on a    */
  671.                     /* list.        */
  672.     struct evsexpr    *evse_prev;    /* Ptr to the previous    */
  673.                     /* satisfied expression    */
  674.                     /* on a list.        */
  675.     evexpr_t    *evse_ep;    /* Ptr to the        */
  676.                     /* expression which has    */
  677.                     /* been satisfied.    */
  678.     evlisthd_t    evse_sterms;    /* The ring of        */
  679.                     /* satisfied terms for    */
  680.                     /* this expression.    */
  681.     short        evse_lvl;    /* The nesting level at    */
  682.                     /* which this trap    */
  683.                     /* handler is running.    */
  684.     ushort        evse_priset :1;    /* Set if the process'    */
  685.                     /* priority has been     */
  686.                     /* set from this  expr.    */
  687.                     /* The priority to     */
  688.                     /* restore is in the    */
  689.                     /* evse_oldpri member.    */
  690.     ushort        evse_astk : 1;    /* Set if we switched    */
  691.                     /* to the alternate    */
  692.                     /* stack when calling     */
  693.                     /* the handler with    */
  694.                     /* this expression.    */
  695.                     /* Not set if already    */
  696.                     /* running on alternate    */
  697.                     /* stack before calling    */
  698.                     /* handler with this    */
  699.                     /* satisfied expression.*/
  700.     pcparms_t    evse_oldpri;    /* The scheduling    */
  701.                     /* priority which was     */
  702.                     /* in effect before    */
  703.                     /* calling the trap    */
  704.                     /* handler.  It must be    */
  705.                     /* restored when the    */
  706.                     /* handler returns.    */
  707. } evsexpr_t;
  708.  
  709. /*            The evtid_t Structure
  710. **            =====================
  711. **
  712. **    The following structure is used to maintain information about
  713. **    trap identifiers.  Trap holds exist at a particular level.
  714. **    Level zero is the main program.  Level one is a trap handler
  715. **    called while running in the main program.  Level 2 is a trap
  716. **    handler called while running in a level 1 trap handler.  In
  717. **    general, level N (for N > 1) is a trap handler called while
  718. **    running in a level N-1 handler.
  719. **
  720. **    Every evtid_t structure is on two rings.  The first is headed
  721. **    by the evpd_t structure field epd_tids.  This list contains
  722. **    every evtid_t structure for the process.  The link fields for
  723. **    this ring are etid_pnextp and etid_pprevp.  The evtid_t
  724. **    structure is also on a hash ring.  The link fields for this
  725. **    ring are etid_hnextp and etid_hprevp.
  726. **
  727. **    The global variable ev_tidhtp points to the hash table for these
  728. **    trap identifier structures hashed on the trap id and process
  729. **    identifier.  This table contains evci_tidhts entries.  Each
  730. **    entry in the hash table is an evlisthd_t structure heading the
  731. **    ring of evtid_t structures.  There is one such structure for
  732. **    each trap identifier being used by a process.  If two processes
  733. **    are using the same tid, there will be two separate evtid_t
  734. **    entries.  Each evtid_t entry indicates the level at which it is
  735. **    being held or TR_NOTHELD if it is not currently held.  In
  736. **    addition to traps being held automatically when a trap handler
  737. **    is called, the user can explicitly hold traps using the evcntl
  738. **    system call.  A trap held in this way will have the etid_holdlvl
  739. **    field set in the same way as for an automatic hold.
  740. **
  741. **    This structure also contains a count of the number of pointers
  742. **    which exist to the structure.  When the last use is released
  743. **    for that tid and process, the evtid_t structure is deleted.
  744. **    The hash is performed on the tid and proc id values.
  745. **
  746. **    The first 4 fields of this structure must not be moved.  Note
  747. **    the special code in ev_subrs.c/ev_tid_hash and
  748. **    ev_subrs.c/ev_tid_init which make assumptions about the 
  749. **    locations of these fields.
  750. */
  751.  
  752. /*            The evtid_t Structure (Continued)
  753. **            =================================
  754. */
  755.  
  756. typedef struct evtid {
  757.     struct evtid    *etid_pnextp;    /* Ptr to the next    */
  758.                     /* evtid_t structure on */
  759.                     /* the proc ring.    */
  760.     struct evtid    *etid_pprevp;    /* Ptr to the previous    */
  761.                     /* evtid_t structure on */
  762.                     /* the proc ring.    */
  763.     struct evtid    *etid_hnextp;    /* Ptr to the next    */
  764.                     /* evtid_t structure on    */
  765.                     /* the hash ring.    */
  766.     struct evtid    *etid_hprevp;    /* Ptr to the previous    */
  767.                     /* evtid_t structure on    */
  768.                     /* the hash ring.    */
  769.     long        etid_tid;    /* The trap identifier    */
  770.                     /* being held.        */
  771.     pid_t        etid_pid;    /* Process id that this    */
  772.                     /* entry belongs to.    */
  773.     short        etid_holdlvl;    /* The level at which    */
  774.                     /* this tid is being     */
  775.                     /* held or TR_NOTHELD    */
  776.                     /* if not currently    */
  777.                     /* held.        */
  778.     ushort        etid_use;    /* Nbr of pointers to    */
  779.                     /* this structure.    */
  780. } evtid_t;
  781.  
  782. #define    TR_NOTHELD    -1        /* Value for         */
  783.                     /* etid_holdlvl when    */
  784.                     /* the trap is not held.*/
  785.  
  786. /*            The evkev_t Structure
  787. **            =====================
  788. **
  789. **    The following structure is used to represent an event in the
  790. **    kernel.  A ring of these events starts from an event queue.
  791. **    The first two members of this structure must not be moved.
  792. */
  793.  
  794. typedef struct evkev {
  795.     struct evkev    *kev_next;    /* Next event on the    */
  796.                     /* same queue as this    */
  797.                     /* one.            */
  798.     struct evkev    *kev_prev;    /* Previous event on     */
  799.                     /* the queue.        */
  800.     event_t        kev_ev;        /* The event info.    */
  801.     struct vnode    *kev_vp;    /* Ptr to the vnode for */
  802.                     /* the queue this event    */
  803.                     /* is to be posted to     */
  804.                     /* or taken from.    */
  805.     struct vnode    *kev_pfdvp;    /* Ptr to the vnode for    */
  806.                     /* the file descriptor    */
  807.                     /* being passed in    */
  808.                     /* ev_pfd if EF_PFD is    */
  809.                     /* set in ev_flags.    */
  810.     union {
  811.         struct anon_map    *kev_amp;    /* Ptr to anon map    */
  812.                         /* structure. For    */
  813.                         /* EF_SHM only.        */
  814.         struct evsigr    *kev_srp;    /* Ptr to evsigr_t    */
  815.                         /* structure or NULL.    */
  816.                         /* If not null, clear    */
  817.                         /* the EVS_F_BLOCK flag    */
  818.                         /* in the evsigr_t     */
  819.                         /* structure when this    */
  820.                         /* event is dequeued.    */
  821.                         /* For ET_SIG events    */
  822.                         /* only.        */
  823.     }        kev_un;        /* An ET_SIG event will    */
  824.                     /* never be in shm.    */
  825.     size_t        kev_datasent;    /* When event sent in      */
  826.                     /* parts, this is     */
  827.                     /* amount already sent.    */
  828.                     /* The value of        */
  829.                     /* kev_ev.ev_datasize    */
  830.                     /* can be used to    */
  831.                     /* determine the amount    */
  832.                     /* of data remaining.    */
  833.  
  834. /*            The evkev_t Structure (Continued)
  835. **            =================================
  836. */
  837.  
  838.     ushort        kev_onqueue :1;    /* Set if this event is    */
  839.                     /* on a queue.        */
  840.     ushort        kev_taken   :1;    /* Set if this event     */
  841.                     /* has been taken (at    */
  842.                     /* least temporarily)     */
  843.                     /* to satisfy a poll or    */
  844.                     /* trap request.    */
  845.     char        kev_pfdflags;    /* The f_flag field of    */
  846.                     /* the file table entry    */
  847.                     /* for the passed file    */
  848.                     /* descriptor ev_pfd if    */
  849.                     /* EF_PFD is set in    */
  850.                     /* ev_flags.        */
  851. } evkev_t;
  852.  
  853. /*            The evqueue_t Structure
  854. **            =======================
  855. **
  856. **    The following structure is used within the kernel to represent
  857. **    an event queue.  In VFS terms, it is the inode which is pointed
  858. **    to by the vnode.  The following are some notes on the usage of
  859. **    certain fields of this structure.
  860. **
  861. **        evq_memsize    This is the total number of bytes of
  862. **                data in private memory for all events on
  863. **                the queue.  It is the sum of the 
  864. **                ev_datasize fields of all events on the
  865. **                queue for which the EF_SHM and
  866. **                EF_QUICKD flags are off and the
  867. **                ev_datasize is greater than zero.  The 
  868. **                total file size will be the number of 
  869. **                events on the queue (evq_nevents) times
  870. **                the size of an event (sizeof(event_t)) 
  871. **                plus the value of the evq_memsize field.
  872. **                This approximates the space taken up by
  873. **                the event.
  874. **
  875. **        evq_atime    The access time is updated when an
  876. **                event is removed from the queue via 
  877. **                either evpoll or evtrap.
  878. **
  879. **        evq_mtime    The modify time is updated when an
  880. **                event is placed on the queue via 
  881. **                evpost, evsig, or any other mechanism
  882. **                such as hrtcntl, asynchronous system
  883. **                call, etc.
  884. **
  885. **        evq_ctime    The change time is updated when the
  886. **                status of an event queue is changed via
  887. **                one of the evqcntl commands.
  888. **
  889. **    The event queues are kept on a hash ring based on the file name
  890. **    of the queue (evq_name).  The hash table is pointed to by the
  891. **    global variable ev_fnhtp.  The links for the ring are evq_next
  892. **    and evq_prev.  The first two members of this structure must not
  893. **    be moved.
  894. */
  895.  
  896. /*            The evqueue_t Structure (Continued)
  897. **            ===================================
  898. */
  899.  
  900. typedef struct evqueue {
  901.     struct evqueue    *evq_next;    /* Ptr to the next    */
  902.                     /* active event queue    */
  903.                     /* on the ev_fnhtp hash    */
  904.                     /* ring.        */
  905.     struct evqueue    *evq_prev;    /* Ptr to previous    */
  906.                     /* event queue on the    */
  907.                     /* hash ring.        */
  908.     evlisthd_t    evq_events;    /* The ring of events    */
  909.                     /* on the queue.    */
  910.     evlisthd_t    evq_exrefs;    /* The ring of        */
  911.                     /* references to exprs    */
  912.                     /* which reference this    */
  913.                     /* queue.        */
  914.     ulong        evq_memsize;    /* Total bytes of    */
  915.                     /* private data on the    */
  916.                     /* queue.  Events with    */
  917.                     /* data in shared     */
  918.                     /* memory or in the    */
  919.                     /* ev_data member of an    */
  920.                     /* event will not be    */
  921.                     /* counted in this    */
  922.                     /* member.        */
  923.     ulong        evq_shmsize;    /* Total bytes of    */
  924.                     /* shared memory data     */
  925.                     /* used by all events    */
  926.                     /* on this queue.    */
  927.     ushort        evq_nevents;    /* Total number of    */
  928.                     /* events on this queue.*/
  929.     evcm_t        evq_closemd :3;    /* The close mode of    */
  930.                     /* the queue.  One of    */
  931.                     /* the ECM_XXXX values    */
  932.                     /* defined in events.h.    */
  933.                     /* We have left an     */
  934.                     /* extra bit in case     */
  935.                     /* any new values have    */
  936.                     /* to be added to the    */
  937.                     /* enumeration.        */
  938.     ushort        evq_wspace  :1;    /* Set if a process is    */
  939.                     /* waiting for space to    */
  940.                     /* post an event to    */
  941.                     /* this queue.        */
  942.     ushort        evq_wevent  :1;    /* Set if a process is    */
  943.                     /* waiting for an    */
  944.                     /* event to be posted    */
  945.                     /* to this queue.    */
  946.     ushort        evq_locked  :1;    /* Set if this queue is    */
  947.                     /* locked.        */
  948.     ushort        evq_wanted  :1;    /* Set if someone is    */
  949.                     /* waiting for the lock    */
  950.                     /* evq_locked to clear.    */
  951.  
  952. /*            The evqueue_t Structure (Continued)
  953. **            ===================================
  954. */
  955.  
  956.     uid_t        evq_uid;    /* User id of owner of    */
  957.                     /* queue.        */
  958.     gid_t        evq_gid;    /* Group id of owner of    */
  959.                     /* queue.        */
  960.     mode_t        evq_mode;    /* File mode of queue.    */
  961.     ushort        evq_opencnt;    /* Count of number of    */
  962.                     /* open's on this queue.*/
  963.     struct evactq    *evq_aqp;    /* Ptr to the entry in    */
  964.                     /* the ev_actqp array    */
  965.                     /* for this queue.    */
  966.     time_t        evq_atime;    /* Access time of queue.*/
  967.     time_t        evq_mtime;    /* Modify time of queue.*/
  968.     time_t        evq_ctime;    /* Change time of queue.*/
  969.     ulong        evq_maxev;    /* Max nbr of events    */
  970.                     /* allowed on the queue.*/
  971.     ulong        evq_maxdpe;    /* Max nbr of bytes of    */
  972.                     /* data per event.    */
  973.     ulong        evq_maxmem;    /* Max value for    */
  974.                     /* evq_memsize.        */
  975.     struct vnode    evq_vnode;    /* The vnode for this    */
  976.                     /* queue.        */
  977.  
  978.     char        evq_name[EV_NMSZ + 1];
  979.                     /* The name of the    */
  980.                     /* queue.        */
  981. } evqueue_t;
  982.  
  983. /*    The following is the default close mode for a newly created
  984. **    event queue.
  985. */
  986.  
  987. #define    ECM_DEFAULT    ECM_DELALL
  988.  
  989.  
  990. /*    The locking of an event queue is based on the fact that
  991. **    interrupt level routines are allowed to post events to a
  992. **    queue but not to remove them from the queue.  For this reason,
  993. **    any process manipulating the evq_events ring must do an spl_ev()
  994. **    to block out interrupts.
  995. **
  996. **    In addition, there are some routines which sleep in a loop
  997. **    which is traversing the events ring.  These routines must lock
  998. **    the queue using ev_rwlock to prevent interactions.
  999. */
  1000.  
  1001. /*            The evretry_t Structure
  1002. **            =======================
  1003. **
  1004. **    The following structure is used only by the ev_evpost function
  1005. **    in ev_main.c.  It is used to remember events which couldn't be
  1006. **    posted immediately but which should be retried.
  1007. */
  1008.  
  1009. typedef struct evretry {
  1010.     struct evretry    *ert_next;    /* Next one on        */
  1011.                     /* double-linked ring.    */
  1012.     struct evretry    *ert_prev;    /* Previous one on ring.*/
  1013.     event_t        *ert_uevp;    /* Ptr to the user's    */
  1014.                     /* event structure in    */
  1015.                     /* user address space.    */
  1016.     evkev_t        *ert_kevp;    /* Pointer to the    */
  1017.                     /* kernel event to be    */
  1018.                     /* posted.        */
  1019.     vnode_t        *ert_vp;    /* Ptr to the vnode for    */
  1020.                     /* the queue to which    */
  1021.                     /* the event should be    */
  1022.                     /* posted.        */
  1023. } evretry_t;
  1024.  
  1025. /*            The evexitr_t Structure
  1026. **            =======================
  1027. **
  1028. **    The following structure is used to implement the evexit
  1029. **    function.  A ring of these structures exists for each process.
  1030. **    The head of this list is the epd_exits member of the evpd_t
  1031. **    structure.  The first two members of this structure must not
  1032. **    be moved.
  1033. */
  1034.  
  1035. typedef struct evexitr {
  1036.     struct evexitr    *evx_next;    /* Next entry on the    */
  1037.                     /* ring.        */
  1038.     struct evexitr    *evx_prev;    /* Previous entry on     */
  1039.                     /* the ring.        */
  1040.     evkev_t        *evx_kevp;    /* Ptr to preallocated    */
  1041.                     /* event structure.    */
  1042.     vnode_t        *evx_vp;    /* Ptr to the vnode for    */
  1043.                     /* the queue to which    */
  1044.                     /* the event should be    */
  1045.                     /* posted.        */
  1046. } evexitr_t;
  1047.  
  1048. /*    The following structure is used to pass parameters between
  1049. **    ev_evexit and the functions ev_exit_add and ev_exit_cancel which
  1050. **    ev_evexit calls indirectly via os/subr.c/dotoprocs.
  1051. */
  1052.  
  1053. typedef struct evexitprms {
  1054.     cred_t    *exp_crdp;    /* Ptr to the credentials for    */
  1055.                 /* the process doing the evexit.*/
  1056.     vnode_t    *exp_vp;    /* Ptr to the vnode for the    */
  1057.                 /* queue to which the exit    */
  1058.                 /* event is to be posted.    */
  1059.     ecb_t    *exp_ecbp;    /* Ptr to the event control    */
  1060.                 /* block describing the event    */
  1061.                 /* to post.            */
  1062.     cnt_t    *exp_rvp;    /* Pointer to where the return    */
  1063.                 /* value should be stored.    */
  1064.     err_t    exp_error;    /* An error returned by the     */
  1065.                 /* function we call.        */
  1066. } evexitprms_t;
  1067.  
  1068. /*            The evsigr_t Structure
  1069. **            ======================
  1070. **
  1071. **    The following structure is used to implement the evsig
  1072. **    function.  An array of these structures is pointed to by the
  1073. **    epd_sigrp member of the evpd_t structure.  The size of this
  1074. **    array is EV_NSIGS.  The index into the array is the signal
  1075. **    number minus one since signal numbers start at one.  The only
  1076. **    valid elements of this array are those for which the signal
  1077. **    number is in the set epd_sigset in the proc table.
  1078. */
  1079.  
  1080. typedef struct evsigr {
  1081.     long        evs_pri;    /* Priority of event     */
  1082.                     /* to post.        */
  1083.     int        evs_eqd;    /* Event queue        */
  1084.                     /* descriptor from     */
  1085.                     /* which we got evs_vp.    */
  1086.     vnode_t        *evs_vp;    /* Queue to which event */
  1087.                     /* should be posted.    */
  1088.     ushort        evs_noqueue :1;    /* Set if signal    */
  1089.                     /* queueing is not to    */
  1090.                     /* be done.  Don't post    */
  1091.                     /* an event for the    */
  1092.                     /* signal if one has    */
  1093.                     /* already been posted    */
  1094.                     /* and not received by    */
  1095.                     /* a process.        */
  1096.     ushort        evs_blocked :1;    /* Set if an event is    */
  1097.                     /* not to be posted for    */
  1098.                     /* this signal.  Used     */
  1099.                     /* to implement the    */
  1100.                     /* evs_noqueue function.*/
  1101. } evsigr_t;
  1102.  
  1103. /*            The evpd_t Structure
  1104. **            ====================
  1105. **
  1106. **    The following structure contains data concerning a process
  1107. **    using the events facility.  One of these structures is pointed
  1108. **    to by the p_evpdp field of the proc table entry.  The structure
  1109. **    is allocated the first time a process uses any of the events
  1110. **    system calls.  At each point where a process can enter the 
  1111. **    events VFS for the first time, we must check that an evpd_t
  1112. **    structure is allocated and, if not, allocate one.  There are
  1113. **    not very many such places since most events operations occur on
  1114. **    an open file descriptor and will only get to the events VFS if
  1115. **    an event queue has been opened.  The places where we must check
  1116. **    are currently:
  1117. **
  1118. **        ev_vnodeops.c/ev_open    Opening an event queue.
  1119. **        ev_vnodeops.c/ev_create    Creating an event queue.
  1120. **        ev_sysint.c/ev_evsys    The evsys system call which is
  1121. **                    used for events stuff which does
  1122. **                    not apply to a particular event
  1123. **                    queue.
  1124. **        ev_sysint.c/ev_fork    Must set up the child based on
  1125. **                    the state of the parent.
  1126. **
  1127. **    The evpd_t structure is freed in ev_exit when the process exits.
  1128. **
  1129. **    If new entry points are added to events, they may also need
  1130. **    checks to insure that an evpd_t structure is always allocated.
  1131. **    In particular, be carful when extending events to work in a
  1132. **    distributed environment.
  1133. */
  1134.  
  1135. /*            The evpd_t Structure (Continued)
  1136. **            ================================
  1137. */
  1138.  
  1139. typedef struct evpd {
  1140.     evlisthd_t    epd_exprs;    /* Head of a ring of    */
  1141.                     /* all of the event    */
  1142.                     /* expressions for    */
  1143.                     /* which this process    */
  1144.                     /* has an outstanding    */
  1145.                     /* evtrap.        */
  1146.     evlisthd_t    epd_ppsexprs;    /* Head of a ring of    */
  1147.                     /* pending poll        */
  1148.                     /* satisfied        */
  1149.                     /* expressions for the    */
  1150.                     /* process.        */
  1151.     evlisthd_t    epd_ptsexprs;    /* Head of a ring of    */
  1152.                     /* pending trap        */
  1153.                     /* satisfied        */
  1154.                     /* expressions for the    */
  1155.                     /* process.        */
  1156.     evlisthd_t    epd_tids;    /* Head of a ring of    */
  1157.                     /* evtid_t structures    */
  1158.                     /* for this process.    */
  1159.     k_sigset_t    epd_sigset;    /* Set of signals for    */
  1160.                     /* which an event is to    */
  1161.                     /* be generated.    */
  1162.     k_sigset_t    epd_sigignset;    /* Set of signals to    */
  1163.                     /* set back to SIG_DFL    */
  1164.                     /* after the evsig is    */
  1165.                     /* cancelled.        */
  1166.     evsexpr_t    *epd_asexp;    /* Ptr to the top of    */
  1167.                     /* the stack of active    */
  1168.                     /* satisfied poll and    */
  1169.                     /* trap expressions.    */
  1170.                     /* Trap handlers for    */
  1171.                     /* all of the trap     */
  1172.                     /* exprs are currently    */
  1173.                     /* active and calls to    */
  1174.                     /* them are nested.    */
  1175.                     /* Recursive calls of     */
  1176.                     /* the same handler are    */
  1177.                     /* possible.        */
  1178.     evsigr_t    *epd_sigrp;    /* Ptr to the start of    */
  1179.                     /* an array of        */
  1180.                     /* descriptions of    */
  1181.                     /* events to be     */
  1182.                     /* generated for    */
  1183.                     /* signals.        */
  1184.     evlisthd_t    epd_exits;    /* Head of a ring of    */
  1185.                     /* descriptions of    */
  1186.                     /* events to be        */
  1187.                     /* generated when this    */
  1188.                     /* process exits.    */
  1189.  
  1190. /*            The evpd_t Structure (Continued)
  1191. **            ================================
  1192. */
  1193.  
  1194.     ushort        epd_ntraps;    /* Nbr of trap        */
  1195.                     /* expressions for this    */
  1196.                     /* process.  Ring of    */
  1197.                     /* these expressions is    */
  1198.                     /* headed by epd_exprs.    */
  1199.     ushort        epd_maxtraps;    /* Max nbr of trap    */
  1200.                     /* expressions allowed    */
  1201.                     /* for this process.    */
  1202.     ushort        epd_maxeterms;    /* Max nbr of terms    */
  1203.                     /* allowed per         */
  1204.                     /* expression for this    */
  1205.                     /* process.        */
  1206.     ushort        epd_holdall :1;    /* Set if a TR_ALL hold    */
  1207.                     /* has been imposed on    */
  1208.                     /* the process by the    */
  1209.                     /* call of a trap    */
  1210.                     /* handler or by an    */
  1211.                     /* evcntl EC_TRAPHOLD    */
  1212.                     /* or EC_TRAPSET type    */
  1213.                     /* function.        */
  1214.     ushort        epd_restart :1;    /* Flag set if we    */
  1215.                     /* interrupted process    */
  1216.                     /* to call trap handler    */
  1217.                     /* which specified    */
  1218.                     /* restart.        */
  1219.     ushort        epd_astk : 1;    /* The process has    */
  1220.                     /* specified an        */
  1221.                     /* alternate stack.    */
  1222.     ushort        epd_onastk : 1;    /* The process is     */
  1223.                     /* currently running on    */
  1224.                     /* the alternate stack.    */
  1225.     ushort        epd_lvl;    /* Trap expression    */
  1226.                     /* nesting level on    */
  1227.                     /* epd_asexp stack.    */
  1228.                     /*            */
  1229.                     /*  0 = No stacked     */
  1230.                     /*      expressions.    */
  1231.                     /*  1 = Stacked trap    */
  1232.                     /*      expression from */
  1233.                     /*      main program    */
  1234.                     /*      level.        */
  1235.                     /*  2 = Trap handler    */
  1236.                     /*      called while in    */
  1237.                     /*      level 1 trap    */
  1238.                     /*      handler.    */
  1239.     caddr_t        epd_astkp;    /* Ptr to the user's    */
  1240.                     /* alternate stack.    */
  1241.     ulong        epd_astks;    /* Size of the user's    */
  1242.                     /* alternate stack in    */
  1243.                     /* bytes.        */
  1244. } evpd_t;
  1245.  
  1246. /*            The evactq_t Structure
  1247. **            ======================
  1248. **
  1249. **    We keep an array of structures to refer to the active event
  1250. **    queues.  The global variable ev_actqp is a pointer to the start
  1251. **    of this array.  The array is allocated in ev_init at system 
  1252. **    startup time.  It has as many entries as the maximum number of
  1253. **    event queues we will ever create (evcinfo.evci_mevqueues).  Each
  1254. **    entry in the array has the structure defined below.  The 
  1255. **    routines ev_aq_* manipulate this array.
  1256. **
  1257. **    This array is used for several purposed.  One is to provide a
  1258. **    "directory" to read.  Since user's must be able to seek to a
  1259. **    particular directory entry and read from there, we must have
  1260. **    some way of consistently defining where we are in the "/events"
  1261. **    directory.  We can't run down a linked list of queues both for
  1262. **    performance reasons and because this could give inconsistent
  1263. **    results (like returning the same entry twice of an earlier
  1264. **    entry was deleted between successive reads).
  1265. **
  1266. **    Another use for this array is to maintain something like inode
  1267. **    numbers which we can use to return for the va_nodeid (inode
  1268. **    number) member of the vattr_t structure.  The macros
  1269. **    ev_inbrtoqp and ev_qptoinbr are used to translate back and
  1270. **    forth between a pointer to a queue and an inumber.  These
  1271. **    macros use the index into the ev_actqp array.
  1272. **
  1273. **    Yet another use of the ev_actqp array is to keep track of
  1274. **    generation numbers.  This is needed for NFS.  Because it doesn't
  1275. **    keep any state, an inode number can be reused behind its back.
  1276. **    The generation number is used to detect that this has happened.
  1277. */
  1278.  
  1279. typedef struct evactq {
  1280.     evqueue_t    *eaq_qp;    /* Ptr to the queue or     */
  1281.                     /* NULL if not queue    */
  1282.                     /* is allocated for     */
  1283.                     /* this entry.        */
  1284.     long        eaq_gen;    /* The generation     */
  1285.                     /* number for this slot.*/
  1286. } evactq_t;
  1287.  
  1288. /*            The evfid_t Structure
  1289. **            =====================
  1290. **
  1291. **    This structure describes or "file identifier".  It is used to
  1292. **    keep track of generation numbers.  This is needed for dumb old
  1293. **    stateless NFS which never knows what is going on.
  1294. **
  1295. **    This structure must map on top of the fid_t structure defined
  1296. **    in sys/vfs.h.  A limit on the size of this structure is also
  1297. **    defined there.
  1298. */
  1299.  
  1300. typedef struct evfid {
  1301.     ushort        efid_len;    /* Length of the rest    */
  1302.                     /* of this structure    */
  1303.                     /* not including this    */
  1304.                     /* member.        */
  1305.     evactq_t    *efid_aqp;    /* Ptr to the entry in    */
  1306.                     /* the ev_actqp array    */
  1307.                     /* for the file (queue).*/
  1308.     long        efid_gen;    /* The saved generation    */
  1309.                     /* number of a file.    */
  1310. } evfid_t;
  1311.  
  1312. /*            Memory Manager Interface
  1313. **            ========================
  1314. **
  1315. **    The following definitions are for the different memory types
  1316. **    which the memory manager in evmmgt.c must handle.  These
  1317. **    symbols are used as the first argument to ev_mem_alloc and
  1318. **    ev_mem_free.
  1319. **
  1320. **    Note that enumeration members are guaranteed to be allocated
  1321. **    consecutive values starting at zero unless specific values are
  1322. **    assigned.  The code relies on this fact.
  1323. */
  1324.  
  1325. typedef enum evmt {
  1326.  
  1327.     EV_MT_NONE,    /* No data required indicator.        */
  1328.     EV_MT_EVQ,    /* An evqueue_t structure.        */
  1329.     EV_MT_KEV,    /* A evkev_t structure.            */
  1330.     EV_MT_EXREF,    /* An evexref_t structure.        */
  1331.     EV_MT_EXPR,    /* An evexpr_t structure.        */
  1332.     EV_MT_TERM,    /* An evterm_t structure.        */
  1333.     EV_MT_SEXPR,    /* An evsexpr_t structure.        */
  1334.     EV_MT_STERM,    /* An evsterm_t structure.        */
  1335.     EV_MT_TID,    /* An evtid_t structure.        */
  1336.     EV_MT_RETRY,    /* An evretry_t structure.        */
  1337.     EV_MT_EXITR,    /* An evexitr_t structure.        */
  1338.     EV_MT_SIGR,    /* An array of evsigr_t structure.    */
  1339.     EV_MT_PD,    /* An evpd_t structure.            */
  1340.     EV_MT_FID,    /* An evfid_t structure.        */
  1341.     EV_MT_EXITD,    /* An evd_exit_t structure.        */
  1342.     EV_MT_STREAMD,    /* An evd_stream_t structure.        */
  1343.     EV_MT_DIRENT,    /* An events dirent_t structure.    */
  1344.     EV_MT_DATA,    /* Space for event type dependent data    */
  1345.             /* and other miscellaneous uses.    */
  1346.  
  1347.     EV_MT_NBR    /* The number of different memory types    */
  1348.             /* we handle.  This member must be the    */
  1349.             /* last one in the enumeration.  Add    */
  1350.             /* new types before this one.        */
  1351. } evmt_t;
  1352.  
  1353. #define    EV_MT_NMSZ    16    /* Size for the emmi_name field    */
  1354.                 /* below.  Should be large     */
  1355.                 /* for the largest name plus a    */
  1356.                 /* terminating null byte.    */
  1357.  
  1358. /*            The evmminfo_t Structure
  1359. **            ========================
  1360. **
  1361. **    This structure is used by the memory management routines in the
  1362. **    file ev_mmgt.c.  No other part of the events VFS should
  1363. **    reference this structure.  The structure contains data about
  1364. **    one of the data items which the memory manager allocates.  An
  1365. **    array of these items, evmminfo, is indexed by the item codes
  1366. **    EV_MT_XXX defined above.
  1367. */
  1368.  
  1369. typedef struct evmminfo {
  1370.     ushort        emmi_size;    /* Size of the item.    */
  1371.     ushort        emmi_wanted :1;    /* Set if one or more    */
  1372.                     /* processes are     */
  1373.                     /* waiting to allocate    */
  1374.                     /* one of these items    */
  1375.                     /* because the number     */
  1376.                     /* allocated reached     */
  1377.                     /* the limit.        */
  1378.     int        emmi_nalloced;    /* The nbr of items     */
  1379.                     /* allocated.        */
  1380.     int        emmi_maxalloc;    /* The maximum nbr of    */
  1381.                     /* items to allocate.    */
  1382.                     /* This member is    */
  1383.                     /* initialized from the    */
  1384.                     /* evcinfo table     */
  1385.                     /* defined in our     */
  1386.                     /* master file.        */
  1387.     char        *emmi_firstp;    /* Ptr to start of the    */
  1388.                     /* allocated area.      */
  1389.                     /* Used only for    */
  1390.                     /* debugging.        */
  1391.     char        *emmi_lastp;    /* Ptr to next byte    */
  1392.                     /* beyond end of the    */
  1393.                     /* allocated area.    */
  1394.                     /* Used only for     */
  1395.                     /* debugging.        */
  1396.     char        *emmi_freep;    /* Ptr to head of free    */
  1397.                     /* list of structures.    */
  1398.  
  1399.     char        emmi_name[EV_MT_NMSZ];
  1400.                     /* Name to be used in    */
  1401.                     /* messages about this    */
  1402.                     /* structure.        */
  1403. } evmminfo_t;
  1404.  
  1405. /*            The evdr_t Structure
  1406. **            ====================
  1407. **
  1408. **    This structure is used by drivers and streams modules which
  1409. **    wish to post events.  A pointer to one of these structures is
  1410. **    an argument to the ev_dr_post function in ev_sysint.c.  The
  1411. **    driver interface is described on the evdri(7) manual page.
  1412. */
  1413.  
  1414. typedef struct evdr {
  1415.     long        evdr_flags;    /* Same as ev_flags in    */
  1416.                     /* the event_t         */
  1417.                     /* structure.        */
  1418.     long        evdr_eid;    /* Same as ev_eid in    */
  1419.                     /* the event_t         */
  1420.                     /* structure.        */
  1421.     long        evdr_pri;    /* Same as ev_pri in    */
  1422.                     /* the event_t         */
  1423.                     /* structure.        */
  1424.     hostid_t    evdr_hostid;    /* Same as ev_hostid in    */
  1425.                     /* the event_t         */
  1426.                     /* structure.        */
  1427.     pid_t        evdr_pid;    /* Same as ev_pid in    */
  1428.                     /* the event_t         */
  1429.                     /* structure.        */
  1430.     uid_t        evdr_uid;    /* Same as ev_uid in    */
  1431.                     /* the event_t         */
  1432.                     /* structure.        */
  1433.     size_t        evdr_datasize;    /* Same as ev_datasize    */
  1434.                     /* in the event_t    */
  1435.                     /* structure.        */
  1436.     char        *evdr_data;    /* Same as ev_data in    */
  1437.                     /* the event_t         */
  1438.                     /* structure.        */
  1439. } evdr_t;
  1440.  
  1441. /*            The evcntxt_t Structure
  1442. **            =======================
  1443. **
  1444. **    The following structure is an event trap handler context.
  1445. **    It is the structure which is built on the stack when calling
  1446. **    a trap handler.  A pointer to this structure is the last
  1447. **    argument to the user's handler and is the argument a user must
  1448. **    supply to the EC_TRAPRET evcntl command to return to the 
  1449. **    interrupted context.
  1450. */
  1451.  
  1452. typedef struct evcntxt {
  1453.     event_t        *ectxt_elp;    /* Ptr to list of     */
  1454.                     /* events from trap.    */
  1455.     int        ectxt_els;    /* Nbr of events in the    */
  1456.                     /* list extxt_elp.    */
  1457.     long        ectxt_tid;    /* The trap identifier    */
  1458.                     /* for the expression    */
  1459.                     /* which was satisfied.    */
  1460.     struct evcntxt    *ectxt_cntxtp;    /* Pointer to this     */
  1461.                     /* context.        */
  1462.     uint        ectxt_lvl;    /* The nesting level of    */
  1463.                     /* this handler.  This    */
  1464.                     /* is the level of the    */
  1465.                     /* handler called with    */
  1466.                     /* a ptr to this     */
  1467.                     /* structure as its     */
  1468.                     /* argument.        */
  1469.  
  1470.     void        (*ectxt_ufunc)();
  1471.                     /* Ptr to the user's    */
  1472.                     /* trap handler     */
  1473.                     /* function.        */
  1474. } evcntxt_t;
  1475.  
  1476. /*            Global Data
  1477. **            ===========
  1478. **
  1479. **    The following data is defined in the events master file.
  1480. */
  1481.  
  1482. #ifdef    _KERNEL
  1483.  
  1484. extern evcinfo_t    evcinfo;    /* Event configuration     */
  1485.                     /* information.        */
  1486.  
  1487.  
  1488. /*    The following data is in evfilenames.c
  1489. */
  1490.  
  1491. extern evlisthd_t    *ev_fnhtp;    /* Ptr to the hash     */
  1492.                     /* table for file names.*/
  1493.  
  1494. /*    The following data is defined in evqueues.c.
  1495. */
  1496.  
  1497. extern evactq_t        *ev_actqp;    /* Ptr to an array of    */
  1498.                     /* ptrs to active    */
  1499.                     /* queues.        */
  1500.  
  1501. /*    The following data is defined in evtids.c.
  1502. */
  1503.  
  1504. extern evlisthd_t    *ev_tidhtp;    /* Ptr to the hash     */
  1505.                     /* table for the trap    */
  1506.                     /* identifiers.        */
  1507.  
  1508. /*    The following data is defined in evvfsops.c.
  1509. */
  1510.  
  1511. extern evdir_t        ev_dotdirs[];    /* The directory     */
  1512.                     /* entries for "." and    */
  1513.                     /* "..".        */
  1514. extern vnode_t        *ev_rootvp;    /* Ptr to the vnode     */
  1515.                     /* for the root of the    */
  1516.                     /* events VFS.        */
  1517. extern evqueue_t    *ev_rootqp;    /* Ptr to the queue for    */
  1518.                     /* the root of the    */
  1519.                     /* events VFS.        */
  1520. extern dev_t        ev_dev;        /* Our device code.    */
  1521. extern short        ev_fstype;    /* Our file system type.*/
  1522. extern off_t        ev_dirsize;    /* Total size of our     */
  1523.                     /* directory.        */
  1524. extern unchar        ev_mounted;    /* Flag set if our VFS    */
  1525.                     /* is mounted.        */
  1526. extern unchar        ev_init_ok;    /* Flag set if events    */
  1527.                     /* vfs initialization     */
  1528.                     /* is completed        */
  1529.                     /* successfully.    */
  1530.  
  1531. /*            Global Data (Continued)
  1532. **            =======================
  1533. **
  1534. **    The following is kernel (non-events) data which we reference.
  1535. */
  1536.  
  1537. extern int        mau_present;    /* Set if a mau is    */
  1538.                     /* present on the     */
  1539.                     /* system.        */
  1540.  
  1541. /*            Function Declarations
  1542. **            =====================
  1543. **
  1544. **    The following are all the functions in the events files.
  1545. **
  1546. **    The following functions are in evcntl.c.
  1547. */
  1548.  
  1549. extern err_t        ev_cntl_evsys();
  1550. extern err_t        ev_evcntl();
  1551. extern err_t        ev_cntl_traphold();
  1552. extern err_t        ev_cntl_trapset();
  1553. extern err_t        ev_cntl_traprelse();
  1554. extern err_t        ev_cntl_trappause();
  1555. extern err_t        ev_cntl_trapret();
  1556. extern err_t        ev_cntl_trapend();
  1557. extern err_t        ev_cntl_altstack();
  1558. extern err_t        ev_cntl_getprinfo();
  1559. extern err_t        ev_cntl_setprinfo();
  1560. extern err_t        ev_cntl_getcfginfo();
  1561. extern err_t        ev_cntl_getmeminfo();
  1562.  
  1563. /*    The following functions are in evexit.c.
  1564. */
  1565.  
  1566. extern err_t        ev_exit_evsys();
  1567. extern err_t        ev_evexit();
  1568. extern err_t        ev_exit_add();
  1569. extern err_t        ev_exit_cancel();
  1570. extern void        ev_exit_post();
  1571. extern void        ev_exit_free();
  1572.  
  1573. /*    These functions are in evexprs.c.
  1574. */
  1575.  
  1576. extern err_t        ev_expr_bld();
  1577. extern err_t        ev_expr_bldholdlist();
  1578. extern err_t        ev_expr_satisfy();
  1579. extern err_t        ev_expr_satisfymore();
  1580. extern err_t        ev_term_check();
  1581. extern err_t        ev_term_satisfy();
  1582. extern err_t        ev_expr_dup();
  1583. extern err_t        ev_term_dup();
  1584. extern void        ev_expr_free();
  1585. extern void        ev_term_free();
  1586. extern err_t        ev_expr_list();
  1587. extern void        ev_expr_unlist();
  1588. extern err_t        ev_expr_tolist();
  1589. extern void        ev_expr_fromlist();
  1590.  
  1591. /*            Functions Declarations (Continued)
  1592. **            ==================================
  1593. **
  1594. **    The following functions are in evfilenames.c.
  1595. */
  1596.  
  1597. extern err_t        ev_fn_lookup();
  1598. extern void        ev_fn_insert();
  1599. extern void        ev_fn_delete();
  1600. extern evqueue_t    *ev_fn_hash();
  1601.  
  1602. /*    The following functions are in evkevs.c
  1603. */
  1604.  
  1605. extern err_t        ev_kev_post();
  1606. extern void        ev_kev_free();
  1607. extern void        ev_kev_enq();
  1608. extern void        ev_kev_deq();
  1609.  
  1610. /*    These functions are in evmmgt.c.
  1611. */
  1612.  
  1613. extern err_t        ev_mem_init();
  1614. extern err_t        ev_mem_alloc();
  1615. extern void        ev_mem_free();
  1616. extern void        ev_mem_rtrninfo();
  1617. extern void        ev_mem_statvfs();
  1618.  
  1619. /*    The following functions are in evpoll.c.
  1620. */
  1621.  
  1622. extern err_t        ev_poll_evsys();
  1623. extern err_t        ev_evpoll();
  1624. extern void        ev_poll_timeout();
  1625. extern err_t        ev_poll_quick();
  1626. extern err_t        ev_poll_dupexpr();
  1627. extern err_t        ev_poll_bldsexpr();
  1628. extern err_t        ev_pollmore_evsys();
  1629. extern err_t        ev_evpollmore();
  1630.  
  1631. /*    These functions are in evpost.c.
  1632. */
  1633.  
  1634. extern err_t        ev_post_evsys();
  1635. extern err_t        ev_evpost();
  1636. extern err_t        ev_post_event();
  1637. extern err_t        ev_post_retry();
  1638. extern err_t        ev_post_getpfd();
  1639. extern err_t        ev_post_getmem();
  1640. extern err_t        ev_post_getshm();
  1641. extern err_t        ev_post_err();
  1642.  
  1643. /*            Functions Declarations (Continued)
  1644. **            ==================================
  1645. **
  1646. **    The following functions are in evqcntl.c.
  1647. */
  1648.  
  1649. extern err_t        ev_qcntl_evsys();
  1650. extern err_t        ev_evqcntl();
  1651. extern err_t        ev_qcntl_getcm();
  1652. extern err_t        ev_qcntl_setcm();
  1653. extern err_t        ev_qcntl_getqinfo();
  1654. extern err_t        ev_qcntl_setqinfo();
  1655. extern err_t        ev_qcntl_getevinfo();
  1656.  
  1657. /*    The following functions are in evqueues.c.
  1658. */
  1659.  
  1660. extern void        ev_aq_insert();
  1661. extern void        ev_aq_delete();
  1662. extern err_t        ev_qaccess();
  1663. extern void        ev_qtrunc();
  1664.  
  1665. /*    The following functions are in evsexprs.c.
  1666. */
  1667.  
  1668. extern void        ev_sexpr_toproc();
  1669. extern err_t        ev_sexpr_dupstk();
  1670. extern evsexpr_t    *ev_sexpr_dup();
  1671. extern err_t        ev_sexpr_tousr();
  1672. extern err_t        ev_sterm_tousr();
  1673. extern err_t        ev_sterm_memtousr();
  1674. extern err_t        ev_sterm_shmtousr();
  1675. extern void        ev_sterm_quickdtousr();
  1676. extern err_t        ev_sterm_pfdtousr();
  1677. extern void        ev_sexpr_hipri();
  1678. extern evsexpr_t    *ev_sexpr_findpending();
  1679. extern evsexpr_t    *ev_sexpr_getpending();
  1680. extern void        ev_sexpr_push();
  1681. extern evsexpr_t    *ev_sexpr_pop();
  1682. extern void        ev_sexpr_unsatisfy();
  1683. extern void        ev_sexpr_free();
  1684. extern void        ev_sterm_free();
  1685.  
  1686. /*            Functions Declarations (Continued)
  1687. **            ==================================
  1688. **
  1689. **    The following functions are in evsig.c.
  1690. */
  1691.  
  1692. extern err_t        ev_sig_evsys();
  1693. extern err_t        ev_evsig();
  1694. extern void        ev_sig_initinfo();
  1695. extern void        ev_sig_saveinfo();
  1696. extern err_t        ev_sig_rtrninfo();
  1697. extern err_t        ev_sig_dup();
  1698. extern void        ev_sig_del();
  1699.  
  1700. /*    The following functions are in evsubrs.c.
  1701. */
  1702.  
  1703. extern void        ev_proc_check();
  1704. extern struct proc    *ev_checkq();
  1705. extern void        ev_proc_clean();
  1706. extern err_t        ev_trapret();
  1707. extern void        ev_untrap();
  1708. extern caddr_t        ev_trap_getstk();
  1709. extern err_t        ev_eqdtovp();
  1710. extern err_t        ev_read_dir();
  1711. extern err_t        ev_write_getdata();
  1712. extern void        ev_nonfatalerr();
  1713.  
  1714. /*    These functions are in evsysint.c.
  1715. */
  1716.  
  1717. extern err_t        ev_evsys();
  1718. extern int        ev_istrap();
  1719. extern int        ev_intr_restart();
  1720. extern void        ev_traptousr();
  1721. extern err_t        ev_evtrapret();
  1722. extern void        ev_exec();
  1723. extern void        ev_exit();
  1724. extern err_t        ev_fork();
  1725. extern void        ev_gotsig();
  1726. extern void        ev_signal();
  1727. extern void        ev_newpri();
  1728. extern err_t        ev_stream_post();
  1729. extern err_t        ev_dr_post();
  1730.  
  1731. /*            Functions Declarations (Continued)
  1732. **            ==================================
  1733. **
  1734. **    The following functions are in evtids.c.
  1735. */
  1736.  
  1737. extern err_t        ev_tid_init();
  1738. extern err_t        ev_tid_dupproclist();
  1739. extern err_t        ev_tid_dupexprlist();
  1740. extern void        ev_tid_clean();
  1741. extern evtid_t        *ev_tid_add();
  1742. extern void        ev_tid_rem();
  1743. extern evtid_t        *ev_tid_find();
  1744. extern void        ev_tid_hold();
  1745. extern void        ev_tid_relse();
  1746. extern evtid_t        *ev_tid_hash();
  1747.  
  1748. /*    The following functions are in evtrap.c.
  1749. */
  1750.  
  1751. extern err_t        ev_trap_evsys();
  1752. extern err_t        ev_evtrap();
  1753. extern err_t        ev_trapcan_evsys();
  1754. extern err_t        ev_evtrapcancel();
  1755. extern void        ev_trapcancel();
  1756.  
  1757. /*    The following are all of the functions in evvfsops.c.  They
  1758. **    must be here because they are forward referenced to define
  1759. **    the ev_vfsops array in that file.
  1760. */
  1761.  
  1762. extern void        ev_init();
  1763. extern err_t        ev_mount();
  1764. extern err_t        ev_unmount();
  1765. extern err_t        ev_root();
  1766. extern err_t        ev_statvfs();
  1767. extern err_t        ev_sync();
  1768. extern err_t        ev_vget();
  1769. extern err_t        ev_mountroot();
  1770. extern err_t        ev_swapvp();
  1771.  
  1772. /*            Functions Declarations (Continued)
  1773. **            ==================================
  1774. **
  1775. **    The following are all of the functions in evvnodeops.c.  They
  1776. **    must be here because they are forward referenced to define the
  1777. **    ev_vnodeops array in that file.
  1778. */
  1779.  
  1780. extern err_t        ev_open();
  1781. extern err_t        ev_close();
  1782. extern err_t        ev_read();
  1783. extern err_t        ev_write();
  1784. extern err_t        ev_ioctl();
  1785. extern err_t        ev_setfl();
  1786. extern err_t        ev_getattr();
  1787. extern err_t        ev_setattr();
  1788. extern err_t        ev_access();
  1789. extern err_t        ev_lookup();
  1790. extern err_t        ev_create();
  1791. extern err_t        ev_remove();
  1792. extern err_t        ev_link();
  1793. extern err_t        ev_rename();
  1794. extern err_t        ev_mkdir();
  1795. extern err_t        ev_rmdir();
  1796. extern err_t        ev_readdir();
  1797. extern err_t        ev_symlink();
  1798. extern err_t        ev_readlink();
  1799. extern err_t        ev_fsync();
  1800. extern void        ev_inactive();
  1801. extern err_t        ev_fid();
  1802. extern void        ev_rwlock();
  1803. extern void        ev_rwunlock();
  1804. extern err_t        ev_seek();
  1805. extern int        ev_cmp();
  1806. extern err_t        ev_frlock();
  1807. extern err_t        ev_space();
  1808. extern err_t        ev_realvp();
  1809.  
  1810. /*            Function Declarations (Continued)
  1811. **            =================================
  1812. **
  1813. **    These are all of the kernel (non-events) functions which we
  1814. **    use.
  1815. */
  1816.  
  1817. extern struct seg    *as_segat();    /* Find the segment    */
  1818.                     /* containing a     */
  1819.                     /* particular virtual    */
  1820.                     /* address for a    */
  1821.                     /* particular process.    */
  1822. extern struct seg    *amtoseg();    /* Find the segment     */
  1823.                     /* which refers to a    */
  1824.                     /* particular anon_map     */
  1825.                     /* for a process.    */
  1826. extern struct anon_map    *as_shmlookup();/* Find the anon_map     */
  1827.                     /* for the shared memory*/
  1828.                     /* segment containing    */
  1829.                     /* a particular virtual    */
  1830.                     /* address in this     */
  1831.                     /* address space.    */
  1832. extern int        ttimeout();    /* Call a kernel    */
  1833.                     /* function after a    */
  1834.                     /* specified time    */
  1835.                     /* interval in ticks.    */
  1836. extern int        untimeout();    /* Cancel a timer set    */
  1837.                     /* with the timeout    */
  1838.                     /* function.        */
  1839. extern int        reglock();    /* Lock a region.    */
  1840. extern int        regrele();    /* Unlock a region.    */
  1841. extern void        freereg();    /* Free a region.    */
  1842. extern int        getudev();    /* Get an unused major    */
  1843.                     /* device code.        */
  1844. extern int        fixuserpsw();    /* Fix a psw to be    */
  1845.                     /* valid for running in    */
  1846.                     /* user mode.        */
  1847. #endif    /* _KERNEL    */
  1848.  
  1849. #endif    /* _SYS_EVSYS_H */
  1850.