home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / misc / volume1 / 8707 / 62 / getidle.c < prev    next >
Encoding:
C/C++ Source or Header  |  1990-07-13  |  3.8 KB  |  183 lines

  1. /*
  2.  *    getidle() - determine idle information for terminals (privileged)
  3.  *
  4.  * revision history
  5.  *
  6.  * 05b 18Jul86 cal .Modified to reference system variables as externs.
  7.  *                  Wrote exe_ipid_to_epid() using asm()s.
  8.  * 05a 01Apr86 cal .Converted to VMS V4.
  9.  * 04a 19Mar84 cal .First "c" version.
  10.  *
  11.  * synopsis
  12.  *
  13.  * #include <sys/types.h>
  14.  *
  15.  * int status, getidle();
  16.  * long *ap_tim;
  17.  * u_long *ap_tim;
  18.  *
  19.  * status = getidle([&ap_tim], &ap_pid, [&ap_net]);
  20.  *
  21.  *    ap_tim - pointer to receive idle time buffer (optional)
  22.  *    ap_pid - pointer to receive pid buffer
  23.  *    ap_net - pointer to receive net address buffer (optional)
  24.  *    status - returned VMS status
  25.  *
  26.  * The optional arguments may be replaced with "0". The idle times,
  27.  * process ids, and net values are stored in the buffers in consecutive
  28.  * elements with a zero longword in the pid buffer to mark end of the
  29.  * list.
  30.  *
  31.  * The net address buffer contains either the Decnet logical link number
  32.  * for a remote terminal or else the host address for a "nty" port.
  33.  *
  34.  * The information is ordered by terminal name.
  35.  *
  36.  * Note: Use of this routine requires the privilege CMKRNL.
  37.  *
  38.  */
  39.  
  40. #include <sys/types.h>
  41. #include <netinet/in.h>
  42.  
  43. #include "vms/ucbdef.h"
  44. #include "vms/ddbdef.h"
  45. #include "vms/ttyucbdef.h"
  46. #include "vms/dcdef.h"
  47. #include "vms/devdef.h"
  48. #include "vms/ssdef.h"
  49.  
  50. static struct XUCB {
  51.     char xucb_dummy[0x13c];
  52.     u_long xucb$x_netaddr;
  53. };
  54.  
  55. extern struct DDB *ioc$gl_devlist;
  56. extern int exe$gl_abstim;
  57.  
  58. static int idlekrn();
  59. static u_long exe_ipid_to_epid();
  60.  
  61. /*
  62.  *    Useful constants
  63.  */
  64.  
  65. #define FUDGE 2                /* add this to exe$gl_abstim */
  66. #define MAX_UNITS 128            /* max units to report about */
  67.  
  68. static long bl_tim[MAX_UNITS];
  69. static u_long bl_pid[MAX_UNITS];
  70. static u_long bl_net[MAX_UNITS];
  71.  
  72. getidle(ap_tim, ap_pid, ap_net)
  73.     long **ap_tim;
  74.     u_long **ap_pid;
  75.     u_long **ap_net;
  76. {
  77.     register int i;
  78.  
  79. #ifdef notdef
  80.     status = sys$lkwset();
  81.     if (status != SS$_WASCLR && status != SS$_WASSET)
  82.         return(status);
  83. #endif
  84.     i = sys$cmkrnl(idlekrn, 0);
  85. #ifdef notdef
  86.     status = sys$ulwset();
  87.     if (status != SS$_WASCLR && status != SS$_WASSET)
  88.         return(status);
  89. #endif
  90.     if (i != SS$_NORMAL)
  91.         return(i);
  92.     if (ap_tim)
  93.         *ap_tim = bl_tim;
  94.     *ap_pid = bl_pid;
  95.     if (ap_net)
  96.         *ap_net = bl_net;
  97.     return(SS$_NORMAL);
  98. }
  99.  
  100. /*
  101.  *    Entry point for the privileged search and slurp.
  102.  */
  103.  
  104. static u_long *nty = (u_long *)"\003NTY";
  105. static u_long *nta = (u_long *)"\003NTA";
  106.  
  107. static idlekrn()
  108. {
  109.     register int i;
  110.     register struct UCB *up;
  111.     register struct DDB *dp;
  112.     register u_long *p_pid;
  113.     register long *p_tim;
  114.     register u_long *p_net;
  115.     char *cp;
  116.     int now;
  117.     int status;
  118.      
  119.     i = 0;
  120.     status = SS$_NORMAL;
  121.     p_tim = bl_tim;
  122.     p_pid = bl_pid;
  123.     p_net = bl_net;
  124.  
  125.     now = exe$gl_abstim + FUDGE;
  126. #ifdef notdef
  127.     asm("jsb    _sch$iolockr");
  128. #endif
  129.  
  130.     for (dp = ioc$gl_devlist; dp; dp = dp->ddb$l_link) {
  131.         if ((up = dp->ddb$l_ucb) == 0 || up->ucb$b_devclass != DC$_TERM)
  132.             continue;
  133.         for ( ; up; up = up->ucb$l_link) {
  134.             if (up->ucb$l_pid == 0)
  135.                 continue;
  136.  
  137.             /* Store process id */
  138.             *p_pid++ = exe_ipid_to_epid(up->ucb$l_pid);
  139.  
  140.             /* Get idle time */
  141.             if ((up->ucb$w_sts & UCB$M_TIM) != 0 ||
  142.                 (up->ucb$w_sts & UCB$M_BSY) == 0 ||
  143.                 (*p_tim = now - up->ucb$l_duetim) < 0)
  144.                 *p_tim = 0;
  145.             p_tim++;
  146.  
  147.             /* Get network info (if a rta, nty, or nta) */
  148.             *p_net = 0;
  149.             if ((up->ucb$l_devchar2 & DEV$M_RTT) != 0)
  150.                 *p_net = ((struct TTYUCB *)up)->ucb$w_rtt_link;
  151.             else if (*nty == *(u_long *)dp->ddb$t_name ||
  152.                  *nta == *(u_long *)dp->ddb$t_name)
  153.                 *p_net = ((struct XUCB *)up)->xucb$x_netaddr;
  154.             p_net++;
  155.  
  156.             if (++i >= MAX_UNITS) {
  157.                 status = SS$_BUFFEROVF;
  158.                 goto done;
  159.             }
  160.         }
  161.     }
  162. done:
  163.  
  164. #ifdef notdef
  165.     asm("jsb    _sch$iounlock");
  166. #endif
  167.     *p_pid = 0;
  168.     return(status);
  169. }
  170.  
  171. static u_long
  172. exe_ipid_to_epid(pid)
  173.     u_long pid;
  174. {
  175. #ifdef lint
  176.     return(pid);
  177. #else
  178.     asm("movl    4(ap),r0");
  179.     asm("jsb    _exe$ipid_to_epid");
  180.     asm("ret");
  181. #endif
  182. }
  183.