home *** CD-ROM | disk | FTP | other *** search
/ The Devil's Doorknob BBS Capture (1996-2003) / devilsdoorknobbbscapture1996-2003.iso / WWIV2.ZIP / UTILITY.C < prev    next >
C/C++ Source or Header  |  1992-12-03  |  24KB  |  1,144 lines

  1. /*****************************************************************************
  2.  
  3.                 WWIV Version 4
  4.                     Copyright (C) 1988-1993 by Wayne Bell
  5.  
  6. Distribution of the source code for WWIV, in any form, modified or unmodified,
  7. without PRIOR, WRITTEN APPROVAL by the author, is expressly prohibited.
  8. Distribution of compiled versions of WWIV is limited to copies compiled BY
  9. THE AUTHOR.  Distribution of any copies of WWIV not compiled by the author
  10. is expressly prohibited.
  11.  
  12.  
  13. *****************************************************************************/
  14.  
  15.  
  16.  
  17. #include "vars.h"
  18.  
  19. #pragma hdrstop
  20.  
  21. #include <dir.h>
  22. #include <math.h>
  23.  
  24.  
  25.  
  26. /* functions for external programs to call */
  27.  
  28. #pragma warn -par
  29.  
  30. void far interrupt inlii(unsigned bp, unsigned di, unsigned si,
  31.                            unsigned ds, unsigned es, unsigned dx,
  32.                            unsigned cx, unsigned bx, unsigned ax,
  33.                            unsigned ip, unsigned cs, unsigned flags,
  34.                            char *s1, char *s2, int i1, int i2)
  35. {
  36.   inli(s1,s2,i1,i2);
  37. }
  38.  
  39. void far interrupt checkai(unsigned bp, unsigned di, unsigned si,
  40.                            unsigned ds, unsigned es, unsigned dx,
  41.                            unsigned cx, unsigned bx, unsigned ax,
  42.                            unsigned ip, unsigned cs, unsigned flags,
  43.                            int *i1, int *i2)
  44. {
  45.   checka(i1,i2);
  46. }
  47.  
  48.  
  49. void far interrupt plai(unsigned bp, unsigned di, unsigned si,
  50.                            unsigned ds, unsigned es, unsigned dx,
  51.                            unsigned cx, unsigned bx, unsigned ax,
  52.                            unsigned ip, unsigned cs, unsigned flags,
  53.                            char *s1, int *i1)
  54. {
  55.   pla(s1,i1);
  56. }
  57.  
  58.  
  59. void far interrupt outchri(unsigned bp, unsigned di, unsigned si,
  60.                            unsigned ds, unsigned es, unsigned dx,
  61.                            unsigned cx, unsigned bx, unsigned ax,
  62.                            unsigned ip, unsigned cs, unsigned flags,
  63.                            char ch)
  64. {
  65.   outchr(ch);
  66. }
  67.  
  68.  
  69. void far interrupt outstri(unsigned bp, unsigned di, unsigned si,
  70.                            unsigned ds, unsigned es, unsigned dx,
  71.                            unsigned cx, unsigned bx, unsigned ax,
  72.                            unsigned ip, unsigned cs, unsigned flags,
  73.                            char *s1)
  74. {
  75.   outstr(s1);
  76. }
  77.  
  78.  
  79. void far interrupt nli(unsigned bp, unsigned di, unsigned si,
  80.                            unsigned ds, unsigned es, unsigned dx,
  81.                            unsigned cx, unsigned bx, unsigned ax,
  82.                            unsigned ip, unsigned cs, unsigned flags)
  83. {
  84.   nl();
  85. }
  86.  
  87.  
  88. void far interrupt pli(unsigned bp, unsigned di, unsigned si,
  89.                            unsigned ds, unsigned es, unsigned dx,
  90.                            unsigned cx, unsigned bx, unsigned ax,
  91.                            unsigned ip, unsigned cs, unsigned flags,
  92.                            char *s1)
  93. {
  94.   pl(s1);
  95. }
  96.  
  97.  
  98. void far interrupt emptyi(unsigned bp, unsigned di, unsigned si,
  99.                            unsigned ds, unsigned es, unsigned dx,
  100.                            unsigned cx, unsigned bx, unsigned ax,
  101.                            unsigned ip, unsigned cs, unsigned flags)
  102. {
  103.   ax=empty();
  104. }
  105.  
  106.  
  107. void far interrupt inkeyi(unsigned bp, unsigned di, unsigned si,
  108.                            unsigned ds, unsigned es, unsigned dx,
  109.                            unsigned cx, unsigned bx, unsigned ax,
  110.                            unsigned ip, unsigned cs, unsigned flags)
  111. {
  112.   ax=(unsigned) empty();
  113. }
  114.  
  115.  
  116. void far interrupt getkeyi(unsigned bp, unsigned di, unsigned si,
  117.                            unsigned ds, unsigned es, unsigned dx,
  118.                            unsigned cx, unsigned bx, unsigned ax,
  119.                            unsigned ip, unsigned cs, unsigned flags)
  120. {
  121.   ax=(unsigned) getkey();
  122. }
  123.  
  124.  
  125. void far interrupt inputi(unsigned bp, unsigned di, unsigned si,
  126.                            unsigned ds, unsigned es, unsigned dx,
  127.                            unsigned cx, unsigned bx, unsigned ax,
  128.                            unsigned ip, unsigned cs, unsigned flags,
  129.                            char *s1, int i)
  130. {
  131.   input(s1,i);
  132. }
  133.  
  134.  
  135. void far interrupt inputli(unsigned bp, unsigned di, unsigned si,
  136.                            unsigned ds, unsigned es, unsigned dx,
  137.                            unsigned cx, unsigned bx, unsigned ax,
  138.                            unsigned ip, unsigned cs, unsigned flags,
  139.                            char *s1, int i)
  140. {
  141.   inputl(s1,i);
  142. }
  143.  
  144.  
  145. void far interrupt yni(unsigned bp, unsigned di, unsigned si,
  146.                            unsigned ds, unsigned es, unsigned dx,
  147.                            unsigned cx, unsigned bx, unsigned ax,
  148.                            unsigned ip, unsigned cs, unsigned flags)
  149. {
  150.   ax=yn();
  151. }
  152.  
  153.  
  154.  
  155. void far interrupt nyi(unsigned bp, unsigned di, unsigned si,
  156.                            unsigned ds, unsigned es, unsigned dx,
  157.                            unsigned cx, unsigned bx, unsigned ax,
  158.                            unsigned ip, unsigned cs, unsigned flags)
  159. {
  160.   ax=ny();
  161. }
  162.  
  163.  
  164. void far interrupt ansici(unsigned bp, unsigned di, unsigned si,
  165.                            unsigned ds, unsigned es, unsigned dx,
  166.                            unsigned cx, unsigned bx, unsigned ax,
  167.                            unsigned ip, unsigned cs, unsigned flags,
  168.                            int i1)
  169. {
  170.   ansic(i1);
  171. }
  172.  
  173.  
  174. void far interrupt oneki(unsigned bp, unsigned di, unsigned si,
  175.                            unsigned ds, unsigned es, unsigned dx,
  176.                            unsigned cx, unsigned bx, unsigned ax,
  177.                            unsigned ip, unsigned cs, unsigned flags,
  178.                            char *s1)
  179. {
  180.   ax=(unsigned) onek(s1);
  181. }
  182.  
  183.  
  184. void far interrupt prti(unsigned bp, unsigned di, unsigned si,
  185.                            unsigned ds, unsigned es, unsigned dx,
  186.                            unsigned cx, unsigned bx, unsigned ax,
  187.                            unsigned ip, unsigned cs, unsigned flags,
  188.                            int i1, char *s1)
  189. {
  190.   prt(i1,s1);
  191. }
  192.  
  193.  
  194.  
  195. void far interrupt mpli(unsigned bp, unsigned di, unsigned si,
  196.                            unsigned ds, unsigned es, unsigned dx,
  197.                            unsigned cx, unsigned bx, unsigned ax,
  198.                            unsigned ip, unsigned cs, unsigned flags,
  199.                            int i1)
  200. {
  201.   mpl(i1);
  202. }
  203.  
  204.  
  205. #pragma warn +par
  206.  
  207. /* end of functions for external programs to call */
  208.  
  209.  
  210. void reset_act_sl(void)
  211. {
  212.   actsl = thisuser.sl;
  213. }
  214.  
  215.  
  216. void remove_from_temp(char *fn, char *dir, int po)
  217. {
  218.   int i,i1,f1,ok;
  219.   char s[81],s1[81];
  220.   struct ffblk ff;
  221.   uploadsrec u;
  222.  
  223.   sprintf(s1,"%s%s",dir,stripfn(fn));
  224.   f1=findfirst(s1,&ff,0);
  225.   ok=1;
  226.   nl();
  227.   while ((f1==0) && (ok)) {
  228.     sprintf(s,"%s%s",dir,ff.ff_name);
  229.     if (po)
  230.       outstr(get_string(919));
  231.       pl(ff.ff_name);
  232.     _chmod(s,1,0);
  233.     unlink(s);
  234.     f1=findnext(&ff);
  235.   }
  236. }
  237.  
  238. void check_event(void)
  239. {
  240.   double tl;
  241.  
  242.   if (syscfg.executetime) {
  243.     tl=time_event-timer();
  244.     if (tl<0.0)
  245.       tl += 24.0*3600.0;
  246.     if ((tl-last_time)>30.0)
  247.       do_event=1;
  248.     last_time=tl;
  249.   }
  250. }
  251.  
  252.  
  253. void run_event(void)
  254. {
  255.   if ((do_event) && (syscfg.executetime)) {
  256.     do_event=0;
  257.     nl();
  258.     pl(get_string(920));
  259.     nl();
  260.     if (syscfg.executestr[0]) {
  261.       holdphone(1);
  262.       shrink_out(syscfg.executestr,0,0,0,1);
  263.       /* run_external(syscfg.executestr); */
  264.       holdphone(0);
  265.     } else
  266.       end_bbs(oklevel);
  267.   }
  268.   clrscrb();
  269. }
  270.  
  271.  
  272. double freek(int dr)
  273. {
  274.   float d;
  275.   struct dfree df;
  276.  
  277.   getdfree(dr,&df);
  278.   d=(float) df.df_avail;
  279.   d*=((float) df.df_bsec);
  280.   d*=((float) df.df_sclus);
  281.   d/=1024.0;
  282.   if (df.df_sclus==0xffff)
  283.     d=-1.0;
  284.   return(d);
  285. }
  286.  
  287.  
  288. unsigned char years_old(unsigned char m, unsigned char d, unsigned char y)
  289. {
  290.   struct date today;
  291.   int a;
  292.  
  293.   getdate(&today);
  294.  
  295.   if (today.da_year-1900<y)
  296.     return(0);
  297.   if (today.da_year-1900==y) {
  298.     if (today.da_mon<m)
  299.       return(0);
  300.     if (today.da_mon==m) {
  301.       if (today.da_day<d)
  302.         return(0);
  303.     }
  304.   }
  305.  
  306.   a=(int) (today.da_year-1900-y);
  307.   if (today.da_mon<m)
  308.     --a;
  309.   else
  310.     if ((today.da_mon==m) && (today.da_day<d))
  311.       --a;
  312.   return((unsigned char)a);
  313. }
  314.  
  315.  
  316.  
  317. void itimer(void)
  318. /* This function initializes the high-resolution timer */
  319. {
  320.   outportb(0x43,0x34);
  321.   outportb(0x40,0x00);
  322.   outportb(0x40,0x00);
  323.  
  324. }
  325.  
  326. double timer(void)
  327. /* This function returns the time, in seconds since midnight. */
  328. {
  329.   double cputim;
  330.   unsigned short int h,m,l1,l2;
  331.  
  332.   disable();
  333.   outportb(0x43,0x00);
  334.   m=peek(0x0040,0x006c);
  335.   h=peek(0x0040,0x006e);
  336.   l1=inportb(0x40);
  337.   l2=inportb(0x40);
  338.   enable();
  339.   l1=((l2*256)+l1) ^ 65535;
  340.   cputim=((h*65536. + m)*65536. + l1)*8.380955e-7;
  341.   return (cputim);
  342. }
  343.  
  344.  
  345. long timer1(void)
  346. /* This function returns the time, in ticks since midnight. */
  347. {
  348.   unsigned short h,m;
  349.   long l;
  350.  
  351.   m=peek(0x0040,0x006c);
  352.   h=peek(0x0040,0x006e);
  353.   l=((long)h)*65536 + ((long)m);
  354.   return(l);
  355. }
  356.  
  357.  
  358. int sysop1(void)
  359. /* This function returns the status of scoll lock.  If scroll lock is active
  360.  * (ie, the user has hit scroll lock + the light is lit if there is a
  361.  * scoll lock LED), the sysop is assumed to be available.
  362.  */
  363. {
  364.   if ((peekb(0,1047) & 0x10)==0)
  365.     return(0);
  366.   else
  367.     return(1);
  368. }
  369.  
  370.  
  371.  
  372. int okansi(void)
  373. /* This function checks the status of the current user's record to see if
  374.  * the user has specified that he wants ANSI graphics displayed.
  375.  */
  376. {
  377.   if (x_only)
  378.     return(0);
  379.   if (thisuser.sysstatus & sysstatus_ansi)
  380.     return(1);
  381.   else
  382.     return(0);
  383. }
  384.  
  385.  
  386. void frequent_init(void)
  387. /* This should be called after a user is logged off, and will initialize
  388.  * screen-access variables.
  389.  */
  390. {
  391.   in_fsed=0;
  392.   curlsub=-1;
  393.   ansiptr=0;
  394.   curatr=0x07;
  395.   outcom=0;
  396.   incom=0;
  397.   charbufferpointer=0;
  398.   andwith=0xff;
  399.   checkit=0;
  400.   topline=0;
  401.   screenlinest=defscreenbottom+1;
  402.   if (!restoring_shrink)
  403.     clrscrb();
  404.   endofline[0]=0;
  405.   hangup=0;
  406.   hungup=0;
  407.   chatcall=0;
  408.   chatreason[0]=0;
  409.   useron=0;
  410.   change_color=0;
  411.   chatting=0;
  412.   echo=1;
  413.   irt[0]=0;
  414.   irt_name[0]=0;
  415.   okskey=0;
  416.   lines_listed=0;
  417.   read_user(1,&thisuser);
  418.   read_qscn(1,qsc,0);
  419.   if (thisuser.inact & inact_deleted)
  420.     fwaiting=0;
  421.   else
  422.     fwaiting=thisuser.waiting;
  423.   okmacro=1;
  424.   okskey=1;
  425.   helpl=0;
  426.   ihelp=0;
  427.   mailcheck=0;
  428.   smwcheck=0;
  429.   in_extern=0;
  430.   gatfn[0]=0;
  431.   use_workspace=0;
  432.   extratimecall=0.0;
  433.   two_color=0;
  434.   using_modem=0;
  435.   set_global_handle(0);
  436.   live_user=1;
  437.   _chmod(dszlog,1,0);
  438.   unlink(dszlog);
  439.   ltime=0;
  440.   set_x_only(0, NULL, 0);
  441.   set_net_num(0);
  442.   set_language(0);
  443. }
  444.  
  445.  
  446. void fix_user_rec(userrec *u)
  447. {
  448.   u->name[sizeof(u->name)-1]=0;
  449.   u->realname[sizeof(u->realname)-1]=0;
  450.   u->callsign[sizeof(u->callsign)-1]=0;
  451.   u->phone[sizeof(u->phone)-1]=0;
  452.   u->pw[sizeof(u->pw)-1]=0;
  453.   u->laston[sizeof(u->laston)-1]=0;
  454.   u->note[sizeof(u->note)-1]=0;
  455.   u->macros[0][sizeof(u->macros[0])-1]=0;
  456.   u->macros[1][sizeof(u->macros[1])-1]=0;
  457.   u->macros[2][sizeof(u->macros[2])-1]=0;
  458. }
  459.  
  460. void close_user(void)
  461. {
  462.   if (userfile!=-1) {
  463.     close(userfile);
  464.     userfile=-1;
  465.   }
  466. }
  467.  
  468. void open_user(void)
  469. {
  470.   char s[81];
  471.  
  472.   if (userfile==-1) {
  473.     sprintf(s,"%sUSER.LST",syscfg.datadir);
  474.     userfile=open(s,O_RDWR | O_BINARY | O_CREAT, S_IREAD | S_IWRITE);
  475.     if (userfile<0) {
  476.       userfile=-1;
  477.     }
  478.   }
  479. }
  480.  
  481.  
  482. int number_userrecs(void)
  483. {
  484.   open_user();
  485.   return((int) (filelength(userfile)/syscfg.userreclen)-1);
  486. }
  487.  
  488. void read_user(unsigned int un, userrec *u)
  489. {
  490.   long pos;
  491.   char s[80];
  492.   int i;
  493.  
  494.   open_user();
  495.   if ((userfile<0) || (un>number_userrecs())) {
  496.     u->inact=inact_deleted;
  497.     fix_user_rec(u);
  498.     return;
  499.   }
  500.  
  501.   if (((useron) && (un==usernum)) || ((wfc) && (un==1))) {
  502.     *u=thisuser;
  503.     fix_user_rec(u);
  504.     return;
  505.   }
  506.   pos=((long) syscfg.userreclen) * ((long) un);
  507.   lseek(userfile,pos,SEEK_SET);
  508.   read(userfile, (void *)u, syscfg.userreclen);
  509.   fix_user_rec(u);
  510. }
  511.  
  512.  
  513. void write_user(unsigned int un, userrec *u)
  514. {
  515.   long pos;
  516.   char s[80];
  517.   unsigned char oldsl;
  518.   int i;
  519.  
  520.   open_user();
  521.  
  522.   if (((useron) && (un==usernum)) || ((wfc) && (un==1))) {
  523.     thisuser=*u;
  524.   }
  525.   pos=((long) syscfg.userreclen) * ((long) un);
  526.   lseek(userfile,pos,SEEK_SET);
  527.   write(userfile, (void *)u, syscfg.userreclen);
  528. }
  529.  
  530. /****************************************************************************/
  531.  
  532. int qscn_file=-1;
  533.  
  534. int open_qscn(void)
  535. {
  536.   char s[81];
  537.  
  538.   if (qscn_file==-1) {
  539.     sprintf(s,"%sUSER.QSC",syscfg.datadir);
  540.     qscn_file=open(s,O_RDWR|O_BINARY|O_CREAT, S_IREAD|S_IWRITE);
  541.     if (qscn_file<0) {
  542.       qscn_file=-1;
  543.       return(0);
  544.     }
  545.   }
  546.   return(1);
  547. }
  548.  
  549. void close_qscn(void)
  550. {
  551.   if (qscn_file!=-1) {
  552.     close(qscn_file);
  553.     qscn_file=-1;
  554.   }
  555. }
  556.  
  557. void read_qscn(unsigned int un, unsigned long *qscn, int stayopen)
  558. {
  559.   long pos;
  560.   int i;
  561.  
  562.   if (((useron) && (un==usernum)) || ((wfc) && (un==1))) {
  563.     for (i=(syscfg.qscn_len/4)-1; i>=0; i--)
  564.       qscn[i]=qsc[i];
  565.     return;
  566.   }
  567.  
  568.   if (open_qscn()) {
  569.     pos=((long)syscfg.qscn_len)*((long)un);
  570.     if (pos + (long)syscfg.qscn_len <= filelength(qscn_file)) {
  571.       lseek(qscn_file,pos,SEEK_SET);
  572.       read(qscn_file,qscn,syscfg.qscn_len);
  573.       if (!stayopen)
  574.         close_qscn();
  575.       return;
  576.     }
  577.   }
  578.  
  579.   if (!stayopen)
  580.     close_qscn();
  581.  
  582.   memset(qsc, 0, syscfg.qscn_len);
  583.   *qsc=999;
  584.   memset(qsc+1,0xff,((syscfg.max_dirs+31)/32)*4);
  585.   memset(qsc+1+(syscfg.max_dirs+31)/32,0xff,((syscfg.max_subs+31)/32)*4);
  586. }
  587.  
  588. void write_qscn(unsigned int un, unsigned long *qscn, int stayopen)
  589. {
  590.   long pos;
  591.   int i;
  592.  
  593.   if (((useron) && (un==usernum)) || ((wfc) && (un==1))) {
  594.     for (i=(syscfg.qscn_len/4)-1; i>=0; i--)
  595.       qsc[i]=qscn[i];
  596.   }
  597.  
  598.   if (open_qscn()) {
  599.     pos=((long)syscfg.qscn_len)*((long)un);
  600.     lseek(qscn_file,pos,SEEK_SET);
  601.     write(qscn_file,qscn,syscfg.qscn_len);
  602.     if (!stayopen)
  603.       close_qscn();
  604.   }
  605. }
  606.  
  607. /****************************************************************************/
  608.  
  609. void save_status(void)
  610. {
  611.   char s[80];
  612.  
  613.   sprintf(s,"%sSTATUS.DAT",syscfg.datadir);
  614.   statusfile=open(s,O_RDWR | O_BINARY);
  615.   write(statusfile, (void *)(&status), sizeof(statusrec));
  616.   close(statusfile);
  617.   statusfile=-1;
  618. }
  619.  
  620.  
  621.  
  622.  
  623. double ratio(void)
  624. {
  625.   double r;
  626.  
  627.   if (thisuser.dk==0)
  628.     return(99.999);
  629.   r=((float) thisuser.uk) / ((float) thisuser.dk);
  630.   if (r>99.998)
  631.     r=99.998;
  632.   return(r);
  633. }
  634.  
  635.  
  636. double post_ratio(void)
  637. {
  638.   double r;
  639.  
  640.   if (thisuser.logons==0)
  641.     return(99.999);
  642.   r=((float) thisuser.msgpost) / ((float) thisuser.logons);
  643.   if (r>99.998)
  644.     r=99.998;
  645.   return(r);
  646. }
  647.  
  648.  
  649. char *nam(userrec *u1, unsigned int un)
  650. {
  651.   static char o[81];
  652.   int i,f,p;
  653.   userrec u;
  654.  
  655.   u=*u1;
  656.   f=1;
  657.   for (p=0; p<strlen(u.name); p++) {
  658.     if (f) {
  659.       if ((u.name[p]>='A') && (u.name[p]<='Z'))
  660.     f=0;
  661.       o[p]=u.name[p];
  662.     } else {
  663.       if ((u.name[p]>='A') && (u.name[p]<='Z'))
  664.         o[p]=u.name[p]-'A'+'a';
  665.       else {
  666.         if ((u.name[p]>=' ') && (u.name[p]<='/'))
  667.           f=1;
  668.         o[p]=u.name[p];
  669.       }
  670.     }
  671.   }
  672.   o[p++]=32;
  673.   o[p++]='#';
  674.   itoa(un,&o[p],10);
  675.   return(o);
  676. }
  677.  
  678.  
  679. char *nam1(userrec *u1, unsigned int un, unsigned int sy)
  680. {
  681.   static char o[81];
  682.   char s[10];
  683.  
  684.   strcpy(o,nam(u1,un));
  685.   if (sy) {
  686.     sprintf(s," @%u",sy);
  687.     strcat(o,s);
  688.   }
  689.   return(o);
  690. }
  691.  
  692. double nsl(void)
  693. {
  694.   double tlt,tlc,tot,tpl,tpd,dd,rtn;
  695.   slrec xx;
  696.  
  697.   dd=timer();
  698.   if (useron) {
  699.     if (timeon>(dd+60.0))
  700.       timeon -= 24.0*3600.0;
  701.     tot=(dd-timeon);
  702.     xx=syscfg.sl[actsl];
  703.     tpl=((double) xx.time_per_logon) * 60.0;
  704.     tpd=((double) xx.time_per_day) * 60.0;
  705.     tlc = tpl - tot + (thisuser.extratime) + extratimecall;
  706.     tlt = tpd - tot - ((double) thisuser.timeontoday) + (thisuser.extratime);
  707.  
  708.     tlt=(((tlc)<(tlt)) ? (tlc) : (tlt));
  709.     if (tlt<0.0)
  710.       tlt=0.0;
  711.     if (tlt>32767.0)
  712.       tlt=32767.0;
  713.     rtn=tlt;
  714.   } else {
  715.     rtn=1.00;
  716.   }
  717.   ltime=0;
  718.   if (syscfg.executetime) {
  719.     tlt=time_event-dd;
  720.     if (tlt<0.0)
  721.       tlt += 24.0*3600.0;
  722.     if (rtn>tlt) {
  723.       rtn=tlt;
  724.       ltime=1;
  725.     }
  726.     check_event();
  727.     if (do_event)
  728.       rtn=0.0;
  729.   }
  730.   if (rtn<0.0)
  731.     rtn=0.0;
  732.   if (rtn>32767.0)
  733.     rtn=32767.0;
  734.   return(rtn);
  735. }
  736.  
  737.  
  738. char *date(void)
  739. {
  740.   static char ds[9];
  741.   struct date today;
  742.  
  743.   getdate(&today);
  744.   sprintf(ds,"%02d/%02d/%02d",today.da_mon,today.da_day,today.da_year-1900);
  745.   return(ds);
  746. }
  747.  
  748. char *times(void)
  749. {
  750.   static char ti[9];
  751.   int h,m,s;
  752.   double t;
  753.  
  754.   t=timer();
  755.   h=(int) (t/3600.0);
  756.   t-=((double) (h)) * 3600.0;
  757.   m=(int) (t/60.0);
  758.   t-=((double) (m)) * 60.0;
  759.   s=(int) (t);
  760.   sprintf(ti,"%02d:%02d:%02d",h,m,s);
  761.   return(ti);
  762. }
  763.  
  764.  
  765. unsigned int finduser(char *s)
  766. {
  767.   int un;
  768.   smalrec *sr;
  769.   userrec u;
  770.   char *ss;
  771.  
  772.   if (strcmp(s,"NEW")==0)
  773.     return(-1);
  774.   if (strcmp(s,"!-@NETWORK@-!")==0)
  775.     return(-2);
  776.   if (strcmp(s,"!-@REMOTE@-!")==0)
  777.     return(-3);
  778.   if (strncmp(s,"!=@",3)==0) {
  779.     ss=s+strlen(s)-3;
  780.     if (strcmp(ss,"@=!")==0) {
  781.       strcpy(s,s+3);
  782.       s[strlen(s)-3]=0;
  783.       return(-4);
  784.     }
  785.   }
  786.  
  787.   if ((un=atoi(s))>0) {
  788.     if (un>number_userrecs())
  789.       return(0);
  790.     read_user(un,&u);
  791.     if (u.inact & inact_deleted)
  792.       return(0);
  793.     return(un);
  794.   }
  795.  
  796.   sr=(smalrec *) bsearch((void *)s,
  797.              (void *)smallist,
  798.              (size_t)status.users,
  799.              (size_t)sizeof(smalrec),
  800.              (int _Cdecl (*) (const void *, const void *))strcmp);
  801.   if (sr==0L)
  802.     return(0);
  803.   else {
  804.     read_user(sr->number,&u);
  805.     if (u.inact & inact_deleted)
  806.       return(0);
  807.     else
  808.       return(sr -> number);
  809.   }
  810. }
  811.  
  812.  
  813. void changedsl(void)
  814. {
  815.   int i,i1,i2,i3,i4,ok,dp,ddp, tp, dtp;
  816.   subboardrec s;
  817.   directoryrec d;
  818.   usersubrec s1;
  819.  
  820.   topscreen();
  821.   dp=ddp=tp=dtp=0;
  822.   dc[dp++]='/';
  823.   dcd[ddp++]='/';
  824.   s1.subnum=-1;
  825.   s1.keys[0]=0;
  826.   for (i=0; i<max_subs; i++)
  827.     usub[i]=s1;
  828.   for (i=0; i<max_dirs; i++)
  829.     udir[i]=s1;
  830.   i1=1;
  831.   i2=0;
  832.   i3=0;
  833.   for (i=0; i<num_subs; i++) {
  834.     ok=1;
  835.     s=subboards[i];
  836.     if (actsl<s.readsl)
  837.       ok=0;
  838.     if (thisuser.age<(s.age&0x7f))
  839.       ok=0;
  840.     if ((s.ar!=0) && (((thisuser.ar) & (s.ar))==0))
  841.       ok=0;
  842.     if ((s.anony & anony_ansi_only) && (!okansi()))
  843.       ok=0;
  844.     if (ok) {
  845.       s1.subnum=i;
  846.       if (s.key!=0) {
  847.         s1.keys[0]=s.key;
  848.         s1.keys[1]=0;
  849.         usub[i3++]=s1;
  850.       } else {
  851.         if (i1<100) {
  852.           if ((i1 % 10)==0)
  853.             dc[dp++]=('0'+(i1/10));
  854.         } else {
  855.           if ((i1 % 100)==0)
  856.             tc[tp++]=('0'+(i1/100));
  857.         }
  858.         itoa(i1++,s1.keys,10);
  859.         for (i4=i3; i4>i2; i4--)
  860.           usub[i4]=usub[i4-1];
  861.         i3++;
  862.         usub[i2++]=s1;
  863.       }
  864.     }
  865.   }
  866.   i1=1;
  867.   i2=0;
  868.   for (i=0; i<num_dirs; i++) {
  869.     ok=1;
  870.     d=directories[i];
  871.     if (thisuser.dsl<d.dsl)
  872.       ok=0;
  873.     if (thisuser.age<d.age)
  874.       ok=0;
  875.     if (d.dar)
  876.       if ((d.dar & thisuser.dar)==0)
  877.         ok=0;
  878.     if (ok) {
  879.       s1.subnum=i;
  880.       if (i==0)
  881.         strcpy(s1.keys,"0");
  882.       else {
  883.         if (i1<100) {
  884.           if ((i1 % 10)==0)
  885.             dcd[ddp++]=('0'+(i1/10));
  886.         } else {
  887.           if ((i1 % 100)==0)
  888.             dtc[dtp++]=('0'+(i1/100));
  889.         }
  890.         itoa(i1++,s1.keys,10);
  891.       }
  892.       udir[i2++]=s1;
  893.     }
  894.   }
  895.   dcd[ddp]=0;
  896.   dc[dp]=0;
  897.   tc[tp]=0;
  898.   dtc[dtp]=0;
  899. }
  900.  
  901.  
  902. void isr(int un, char *name)
  903. {
  904.   int cp,i;
  905.   char s[81];
  906.   smalrec sr;
  907.  
  908.   cp=0;
  909.   while ((cp<status.users) && (strcmp(name,(smallist[cp].name))>0))
  910.     ++cp;
  911.   memmove(&(smallist[cp+1]),&(smallist[cp]),sizeof(smalrec)*(status.users-cp));
  912.   strcpy(sr.name,name);
  913.   sr.number=un;
  914.   smallist[cp]=sr;
  915.   sprintf(s,"%sNAMES.LST",syscfg.datadir);
  916.   i=open(s,O_RDWR | O_BINARY | O_TRUNC);
  917.   if (i<0) {
  918.     printf("%s NOT FOUND.\n",s);
  919.     end_bbs(noklevel);
  920.   }
  921.   ++status.users;
  922.   save_status();
  923.   write(i,(void *) (smallist), (sizeof(smalrec) * status.users));
  924.   close(i);
  925. }
  926.  
  927.  
  928. void dsr(char *name)
  929. {
  930.   int cp,i;
  931.   char s[81];
  932.   smalrec sr;
  933.  
  934.   cp=0;
  935.   while ((cp<status.users) && (strcmp(name,(smallist[cp].name))!=0))
  936.     ++cp;
  937.   if (strcmp(name,(smallist[cp].name))) {
  938.     sprintf(s,get_stringx(1,74),name);
  939.     sl1(0,s);
  940.     sl1(0,get_stringx(1,75));
  941.     return;
  942.   }
  943.   memmove(&(smallist[cp]),&(smallist[cp+1]),sizeof(smalrec)*(status.users-cp));
  944.   sprintf(s,"%sNAMES.LST",syscfg.datadir);
  945.   i=open(s,O_RDWR | O_BINARY | O_TRUNC | O_CREAT, S_IREAD | S_IWRITE);
  946.   if (i<0) {
  947.     printf("%s COULDN'T BE CREATED.\n",s);
  948.     end_bbs(noklevel);
  949.   }
  950.   --status.users;
  951.   save_status();
  952.   write(i,(void *) (smallist), (sizeof(smalrec) * status.users));
  953.   close(i);
  954. }
  955.  
  956.  
  957. void wait(double d)
  958. {
  959.   long l1;
  960.  
  961.   l1=((long) (18.2*d));
  962.   l1 += timer1();
  963.  
  964.   enable();
  965.   while (timer1()<l1)
  966.     ;
  967. }
  968.  
  969. void wait1(long l)
  970. {
  971.   long l1;
  972.  
  973.   l1 = timer1()+l;
  974.  
  975.   enable();
  976.   while (timer1()<l1)
  977.     ;
  978. }
  979.  
  980.  
  981. double freek1(char *s)
  982. {
  983.   int d;
  984.  
  985.   d=cdir[0];
  986.   if (s[1]==':')
  987.     d=s[0];
  988.   d=d-'A'+1;
  989.   return(freek(d));
  990. }
  991.  
  992.  
  993. int exist(char *s)
  994. {
  995.   int i;
  996.   struct ffblk ff;
  997.  
  998.   i=findfirst(s,&ff,FA_HIDDEN);
  999.   if (i)
  1000.     return(0);
  1001.   else
  1002.     return(1);
  1003. }
  1004.  
  1005.  
  1006. void add_ass(int i, char *ss)
  1007. {
  1008.   char s[81],s1[10];
  1009.  
  1010.   strcpy(s,"*** ");
  1011.   sysoplog(s);
  1012.   strcat(s,ss);
  1013.   sysoplog(s);
  1014.   itoa(i,s1,10);
  1015.   strcpy(s,get_stringx(1,76));
  1016.   strcat(s,s1);
  1017.   sysoplog(s);
  1018.   thisuser.ass_pts += i;
  1019. }
  1020.  
  1021.  
  1022. int find_interrupt(void)
  1023. {
  1024.   long far *l;
  1025.   int i;
  1026.  
  1027.   for (i=0x60; i<0xf0; i++) {
  1028.     if ((i<0x70) || (i>0x77)) {
  1029.       l=MK_FP(0,(i*4));
  1030.       if (*l==0)
  1031.         return i;
  1032.     }
  1033.   }
  1034.   return(0);
  1035. }
  1036.  
  1037.  
  1038.  
  1039. /****************************************************************************/
  1040.  
  1041. void send_net(net_header_rec *nh, unsigned int *list, char *text, char *byname)
  1042. {
  1043.   int f;
  1044.   char s[100];
  1045.   long l1;
  1046.  
  1047.   sprintf(s,"%sP1.NET",net_data);
  1048.   f=open(s,O_RDWR | O_BINARY | O_CREAT, S_IREAD | S_IWRITE);
  1049.   lseek(f,0L,SEEK_END);
  1050.   if (!list)
  1051.     nh->list_len=0;
  1052.   if (!text)
  1053.     nh->length=0;
  1054.   if (nh->list_len)
  1055.     nh->tosys=0;
  1056.   l1=nh->length;
  1057.   if (byname && *byname)
  1058.     nh->length += strlen(byname)+1;
  1059.   write(f,(void *)nh,sizeof(net_header_rec));
  1060.   if (nh->list_len)
  1061.     write(f,(void *)list,2*(nh->list_len));
  1062.   if (byname && *byname)
  1063.     write(f,byname, strlen(byname)+1);
  1064.   if (nh->length)
  1065.     write(f,(void *)text,l1);
  1066.   close(f);
  1067. }
  1068.  
  1069. /****************************************************************************/
  1070.  
  1071. unsigned char dow(void)
  1072. /* returns day of week, 0=Sun, 6=Sat */
  1073. {
  1074.   unsigned char ch;
  1075.  
  1076.   _AH=0x2a;
  1077.   geninterrupt(0x21);
  1078.   ch=_AL;
  1079.  
  1080.   return(ch);
  1081. }
  1082.  
  1083. /****************************************************************************/
  1084.  
  1085. static int multitasker;
  1086.  
  1087. #define MT_DESQVIEW 0x01
  1088. #define MT_WINDOWS  0x02
  1089. #define MT_OS2      0x04
  1090.  
  1091. void detect_multitask(void)
  1092. {
  1093.   union REGS r;
  1094.  
  1095.   multitasker=0;
  1096.  
  1097.   r.x.ax=0x2b01;
  1098.   r.x.cx=0x4445;
  1099.   r.x.dx=0x5351;
  1100.   if (int86(0x21, &r, &r)&0xff != 0xff)
  1101.     multitasker |= MT_DESQVIEW;
  1102.  
  1103.   r.h.ah=0x30;
  1104.   if (int86(0x21,&r,&r)&0xff >= 10)
  1105.     multitasker |= MT_OS2;
  1106. }
  1107.  
  1108. void giveup_timeslice(void)
  1109. {
  1110.   if (multitasker & MT_DESQVIEW) {
  1111.     _AX=0x101a;
  1112.     geninterrupt(0x15);
  1113.     _AX=0x1000;
  1114.     geninterrupt(0x15);
  1115.     _AX=0x1025;
  1116.     geninterrupt(0x15);
  1117.   } else if (multitasker & MT_WINDOWS) {
  1118.   }
  1119. }
  1120.  
  1121. void begin_crit(void)
  1122. {
  1123.   if (multitasker & MT_DESQVIEW) {
  1124.     _AX=0x101a;
  1125.     geninterrupt(0x15);
  1126.     _AX=0x101b;
  1127.     geninterrupt(0x15);
  1128.     _AX=0x1025;
  1129.     geninterrupt(0x15);
  1130.   }
  1131. }
  1132.  
  1133. void end_crit(void)
  1134. {
  1135.   if (multitasker & MT_DESQVIEW) {
  1136.     _AX=0x101a;
  1137.     geninterrupt(0x15);
  1138.     _AX=0x101c;
  1139.     geninterrupt(0x15);
  1140.     _AX=0x1025;
  1141.     geninterrupt(0x15);
  1142.   }
  1143. }
  1144.