home *** CD-ROM | disk | FTP | other *** search
/ Beijing Paradise BBS Backup / PARADISE.ISO / software / BBSDOORW / UUPC11XT.ZIP / RN / NGDATA.C < prev    next >
Encoding:
C/C++ Source or Header  |  1992-11-21  |  10.2 KB  |  459 lines

  1. /* $Header: E:\SRC\UUPC\RN\RCS/NGDATA.C 1.1 1992/11/21 06:14:58 ahd Exp $
  2.  *
  3.  * $Log: NGDATA.C $
  4.  * Revision 1.1  1992/11/21  06:14:58  ahd
  5.  * Initial
  6.  *
  7.  *
  8.  *    Rev 1.0   18 Nov 1990  0:22:10
  9.  * Initial revision.
  10.  * Revision 4.3.2.10  90/04/14  22:05:15  sob
  11.  * Removed redundant declaration of active_name
  12.  *
  13.  * Revision 4.3.2.9  90/03/22  23:04:55  sob
  14.  * Fixes provided by Wayne Davison <drivax!davison>
  15.  *
  16.  * Revision 4.3.2.8  90/03/17  20:50:51  sob
  17.  * Fixes provided by stewart@netxcom.iad-nxe.global-mis.dhl.com to handle
  18.  * flaky transfers of the active file from the server.
  19.  *
  20.  * Revision 4.3.2.7  90/03/17  17:11:08  sob
  21.  * Added support for CNEWS active file flags.
  22.  *
  23.  * Revision 4.3.2.6  89/12/08  22:42:04  sob
  24.  * Corrected typo in an #ifdef statement pointed out by
  25.  * jik@pit-manager.mit.edu
  26.  *
  27.  * Revision 4.3.2.5  89/11/28  01:51:14  sob
  28.  * Removed redundant #include directive.
  29.  *
  30.  * Revision 4.3.2.4  89/11/27  01:31:07  sob
  31.  * Altered NNTP code per ideas suggested by Bela Lubkin
  32.  * <filbo@gorn.santa-cruz.ca.us>
  33.  *
  34.  * Revision 4.3.2.3  89/11/08  02:41:40  sob
  35.  * Removed unneeded subroutine.
  36.  *
  37.  * Revision 4.3.2.2  89/11/08  02:24:31  sob
  38.  * Integrated modifications from other RRN patches colleceted from USENET
  39.  *
  40.  * Revision 4.3.2.1  89/11/06  00:42:43  sob
  41.  * Added RRN support from NNTP 1.5
  42.  *
  43.  * Revision 4.3  85/05/01  11:44:38  lwall
  44.  * Baseline for release with 4.3bsd.
  45.  *
  46.  */
  47.  
  48. #include "EXTERN.h"
  49. #include "common.h"
  50. #include "ndir.h"
  51. #include "rcstuff.h"
  52. #include "rn.h"
  53. #include "intrp.h"
  54. #include "final.h"
  55. #include "rcln.h"
  56. #include "util.h"
  57.  
  58. #ifdef SERVER
  59. #include "server.h"
  60. #endif
  61.  
  62. #include "INTERN.h"
  63. #include "ngdata.h"
  64.  
  65. void
  66.   ngdata_init()
  67. {
  68.  
  69. #ifdef SERVER
  70.    char ser_line[256];
  71.    char *cp;
  72.    int entries;
  73.  
  74. #endif
  75.  
  76. /* The following is only for systems that do not zero globals properly */
  77.  
  78. #ifdef ZEROGLOB
  79.  
  80. #ifdef CACHEFIRST
  81.    for (i = 0; i < MAXRCLINE; i++)
  82.       abs1st[i] = 0;
  83. #endif
  84.  
  85. #endif                       /* ZEROGLOB */
  86.  
  87.    /* open the active file */
  88.  
  89. #ifdef SERVER
  90.    put_server("LIST");       /* tell server we want
  91.                               * the active file */
  92.    get_server(ser_line, sizeof (ser_line));
  93.    if (*ser_line != CHAR_OK)
  94.    {                         /* and then see if
  95.                               * that's ok */
  96.       fprintf(stdout, "Can't get active file from server: \n%s\n", ser_line);
  97.       finalize(1);
  98.    }
  99.  
  100.    cp = filexp("/tmp/rrnact.%$");       /* make a temporary name */
  101.    strcpy(active_name, cp);
  102.    actfp = fopen(active_name, "w+");    /* and get ready */
  103.    if (actfp == Nullfp)
  104.    {
  105.       printf(cantopen, active_name) FLUSH;
  106.       finalize(1);
  107.    }
  108.  
  109.    entries = 0;
  110.    while (1)
  111.    {
  112.       if (get_server(ser_line, sizeof (ser_line)) < 0)
  113.       {
  114.          printf("Can't get active file from server:\ntransfer failed after %d entries\n", entries);
  115.          finalize(1);
  116.       }
  117.       if (ser_line[0] == '.')/* while there's another
  118.                               * line */
  119.          break;              /* get it and write it
  120.                               * to */
  121.       entries++;
  122.       fputs(ser_line, actfp);
  123.       putc('\n', actfp);
  124.    }
  125.  
  126.    fseek(actfp, 0L, 0);      /* just get to the
  127.                               * beginning */
  128.  
  129. #else                        /* not SERVER */
  130.  
  131.    actfp = fopen(filexp(ACTIVE), "r");
  132.    if (actfp == Nullfp)
  133.    {
  134.       printf(cantopen, filexp(ACTIVE)) FLUSH;
  135.       finalize(1);
  136.    }
  137. #endif                       /* SERVER */
  138. }
  139.  
  140. /* find the maximum article number of a newsgroup */
  141.  
  142. ART_NUM
  143. getngsize(num)
  144.    register NG_NUM num;
  145. {
  146.    register int len;
  147.    register char *nam;
  148.    char tmpbuf[80];
  149.    ART_POS oldsoft;
  150.  
  151.    nam = rcline[num];
  152.    len = rcnums[num] - 1;
  153.    softtries++;
  154.  
  155. #ifdef DEBUGGING
  156.    if (debug & DEB_SOFT_POINTERS)
  157.       printf("Softptr = %ld\n", (long) softptr[num]) FLUSH;
  158. #endif
  159.  
  160.    oldsoft = softptr[num];
  161.    if ((softptr[num] = findact(tmpbuf, nam, len, (long) oldsoft)) >= 0)
  162.    {
  163.       if (softptr[num] != oldsoft)
  164.       {
  165.          softmisses++;
  166.          writesoft = TRUE;
  167.       }
  168.    }
  169.    else
  170.    {
  171.       softptr[num] = 0;
  172.       if (rcchar[num] == ':')/* unsubscribe quietly */
  173.          rcchar[num] = NEGCHAR;
  174.       return TR_BOGUS;       /* well, not so quietly,
  175.                               * actually */
  176.    }
  177.  
  178. #ifdef DEBUGGING
  179.    if (debug & DEB_SOFT_POINTERS)
  180.    {
  181.       printf("Should be %ld\n", (long) softptr[num]) FLUSH;
  182.    }
  183. #endif
  184.  
  185. #ifdef MININACT
  186.    {
  187.       register char *s;
  188.       ART_NUM tmp;
  189.  
  190.       for (s = tmpbuf + len + 1; isdigit(*s); s++);
  191.       if (tmp = atol(s))
  192.  
  193. #ifdef CACHEFIRST
  194.          abs1st[num] = tmp;
  195. #else
  196.          abs1st = tmp;
  197. #endif
  198.  
  199.       if (!in_ng)
  200.       {
  201.          for (s++; isdigit(*s); s++);
  202.          while (isspace(*s))
  203.             s++;
  204.          switch (*s)
  205.          {
  206.           case 'n':
  207.             moderated = getval("NOPOSTRING", " (no posting)");
  208.             break;
  209.           case 'm':
  210.             moderated = getval("MODSTRING", " (moderated)");
  211.             break;
  212.             /* This shouldn't even occur.  What are we doing in a non-existent
  213.              * group?  Disallow it. */
  214.           case 'x':
  215.             return TR_BOGUS;
  216.             /* what should be done about refiled groups?  rn shouldn't even be
  217.              * in them (ie, if sci.aquaria is refiled to rec.aquaria, then get
  218.              * the news there) */
  219.           case '=':
  220.             return TR_BOGUS;
  221.           default:
  222.             moderated = nullstr;
  223.          }
  224.       }
  225.    }
  226. #endif
  227.  
  228.    return atol(tmpbuf + len + 1);
  229. }
  230.  
  231. #ifndef msdos
  232. #endif
  233.  
  234. ACT_POS
  235. findact(outbuf, nam, len, suggestion)
  236.    char *outbuf;
  237.    char *nam;
  238.    int len;
  239.    long suggestion;
  240. {
  241.    ACT_POS retval;
  242.  
  243.    fseek(actfp, 100000L, 1); /* hopefully this forces
  244.                               * a reread */
  245.    if (suggestion == 0L || fseek(actfp, suggestion, 0) < 0 ||
  246.          fgets(outbuf, 80, actfp) == Nullch ||
  247.          outbuf[len] != ' ' ||
  248.          strnNE(outbuf, nam, len))
  249.    {
  250.  
  251. #ifdef DEBUGGING
  252.       if (debug & DEB_SOFT_POINTERS)
  253.          printf("Missed, looking for %s in %sLen = %d\n", nam, outbuf, len)
  254.             FLUSH;
  255. #endif
  256.  
  257.       fseek(actfp, 0L, 0);
  258.  
  259. #ifndef lint
  260.       retval = (ACT_POS) ftell(actfp);
  261. #else
  262.       retval = Null(ACT_POS);
  263. #endif                       /* lint */
  264.  
  265.       while (fgets(outbuf, 80, actfp) != Nullch)
  266.       {
  267.          if (outbuf[len] == ' ' && strnEQ(outbuf, nam, len))
  268.             return retval;
  269.  
  270. #ifndef lint
  271.          retval = (ACT_POS) ftell(actfp);
  272. #endif                       /* lint */
  273.       }
  274.       return (ACT_POS) - 1;  /* well, not so quietly,
  275.                               * actually */
  276.    }
  277.    else
  278.  
  279. #ifndef lint
  280.       return (ACT_POS) suggestion;
  281. #else
  282.       return retval;
  283. #endif                       /* lint */
  284.  
  285.    /* NOTREACHED */
  286. }
  287.  
  288. #if 0
  289. ACT_POS
  290. findact(outbuf, nam, len, suggestion)
  291.    char *outbuf;
  292.    char *nam;
  293.    int len;
  294.    long suggestion;
  295. {
  296.    long minart;
  297.    long maxart;
  298.    char mode;
  299.  
  300.    if (!get_ng_info(nam, &minart, &maxart, &mode))
  301.       return -1L;
  302.    sprintf(outbuf, "%s %10.10ld %10.10ld %c\n",
  303.            nam, maxart, minart, mode);
  304.    return suggestion;
  305. }
  306.  
  307. #endif                       /* msdos */
  308.  
  309. /* determine the absolutely first existing article number */
  310.  
  311. #ifdef SERVER
  312. ART_NUM
  313. getabsfirst(ngnum, ngsize)
  314.    register NG_NUM ngnum;
  315.    ART_NUM ngsize;
  316. {
  317.    register ART_NUM a1st;
  318.  
  319. #ifndef MININACT
  320.    char ser_line[256];
  321.    ART_NUM x, y;
  322.  
  323. #endif
  324.  
  325. #ifdef CACHEFIRST
  326.    if (a1st = abs1st[ngnum])
  327.       return a1st;
  328. #endif
  329.  
  330. #ifdef MININACT
  331.    getngsize(ngnum);
  332.  
  333. #ifdef CACHEFIRST
  334.    return abs1st[ngnum];
  335. #else
  336.    return abs1st;
  337. #endif
  338.  
  339. #else
  340.    sprintf(cp, "GROUP %s", rcline[ngnum]);
  341.    put_server(cp);
  342.    if (get_server(ser_line, sizeof (ser_line)) < 0)
  343.    {
  344.       fprintf(stderr, "rrn: Unexpected close of server socket.\n");
  345.       finalize(1);
  346.    }
  347.    if (*ser_line != CHAR_OK)
  348.    {                         /* and then see if
  349.                               * that's ok */
  350.       a1st = ngsize + 1;     /* nothing there */
  351.    }
  352.    (void) sscanf(ser_line, "%d%d%d", &x, &y, &a1st);
  353.  
  354. #ifdef CACHEFIRST
  355.    abs1st[ngnum] = a1st;
  356. #endif
  357.  
  358.    return a1st;
  359. #endif
  360. }
  361.  
  362. /* we already know the lowest article number with NNTP */
  363. ART_NUM
  364. getngmin(dirname, floor)
  365.    char *dirname;
  366.    ART_NUM floor;
  367. {
  368.    return (floor);
  369. }
  370.  
  371. #else
  372. ART_NUM
  373. getabsfirst(ngnum, ngsize)
  374.    register NG_NUM ngnum;
  375.    ART_NUM ngsize;
  376. {
  377.    register ART_NUM a1st;
  378.  
  379. #ifndef MININACT
  380.    char dirname[MAXFILENAME];
  381.  
  382. #endif
  383.  
  384. #ifdef CACHEFIRST
  385.    if (a1st = abs1st[ngnum])
  386.       return a1st;
  387. #endif
  388.  
  389. #ifdef MININACT
  390.    getngsize(ngnum);
  391.  
  392. #ifdef CACHEFIRST
  393.    return abs1st[ngnum];
  394. #else
  395.    return abs1st;
  396. #endif
  397.  
  398. #else                        /* not MININACT */
  399.    strcpy(dirname, getngdir(rcline[ngnum]));
  400.    a1st = getngmin(dirname, 0L);
  401.    if (!a1st)                /* nothing there at all? */
  402.       a1st = ngsize + 1;     /* aim them at end of newsgroup */
  403.  
  404. #ifdef CACHEFIRST
  405.    abs1st[ngnum] = a1st;
  406. #endif
  407.  
  408.    return a1st;
  409. #endif                       /* MININACT */
  410. }
  411.  
  412. /* scan a directory for minimum article number greater than floor */
  413.  
  414. ART_NUM
  415. getngmin(dirname, floor)
  416.    char *dirname;
  417.    ART_NUM floor;
  418. {
  419.  
  420. #ifndef msdos
  421.    register DIR *dirp;
  422.    register struct DIRTYPE *dp;
  423.    register ART_NUM min = 1000000;
  424.    register ART_NUM maybe;
  425.    register char *p;
  426.    char tmpbuf[128];
  427.  
  428.    dirp = opendir(dirname);
  429.    if (!dirp)
  430.       return 0;
  431.    while ((dp = readdir(dirp)) != Null(struct DIRTYPE *))
  432.    {
  433.       if ((maybe = atol(dp->d_name)) < min && maybe > floor)
  434.       {
  435.          for (p = dp->d_name; *p; p++)
  436.             if (!isdigit(*p))
  437.                goto nope;
  438.          if (*dirname == '.' && !dirname[1])
  439.             stat(dp->d_name, &filestat);
  440.          else
  441.          {
  442.             sprintf(tmpbuf, "%s/%s", dirname, dp->d_name);
  443.             stat(tmpbuf, &filestat);
  444.          }
  445.          if (!(filestat.st_mode & S_IFDIR))
  446.             min = maybe;
  447.       }
  448. nope:
  449.       ;
  450.    }
  451.    closedir(dirp);
  452.    return min == 1000000 ? 0 : min;
  453. #else
  454.    return floor;
  455. #endif
  456. }
  457.  
  458. #endif
  459.