home *** CD-ROM | disk | FTP | other *** search
/ Source Code 1992 March / Source_Code_CD-ROM_Walnut_Creek_March_1992.iso / unix_c / usenet / dtmnbtch.sh < prev    next >
Encoding:
Text File  |  1989-03-21  |  8.5 KB  |  309 lines

  1. 23-Nov-85 07:10:23-MST,9009;000000000001
  2. Return-Path: <unix-sources-request@BRL.ARPA>
  3. Received: from BRL-TGR.ARPA by SIMTEL20.ARPA with TCP; Sat 23 Nov 85 07:10:05-MST
  4. Received: from usenet by TGR.BRL.ARPA id a004133; 23 Nov 85 8:40 EST
  5. From: Charlie Perkins <charliep@polaris.uucp>
  6. Newsgroups: net.sources
  7. Subject: Retrieving data from broken UUCP transfers
  8. Message-ID: <300@polaris.UUCP>
  9. Date: 22 Nov 85 02:18:42 GMT
  10. To:       unix-sources@BRL-TGR.ARPA
  11.  
  12. =========
  13. Many, many times I have discovered TM files remaining in
  14. our uucp spool directory resulting from incomplete uucp
  15. sessions.  Moreover, a significant minority of those files
  16. contained information that was never retransmitted, for
  17. reasons that I cannot undestand.  I am a fanatic about not
  18. losing data, so I wrote the following programs to make
  19. maximum use of the incomplete TM files.  This has the
  20. effect of sometimes duplicating mail that WAS eventually
  21. retransmitted correctly, but my users don't mind that at
  22. all.  Duplicate news articles are later recognized
  23. as such.  When all the articles are retrieved from the TM
  24. files, they can be moved to the junk directory and
  25. processed using "process_junk" which I have posted
  26. separately.
  27.  
  28. The files are deTM, deTMunbatch.c, and mv2junk.
  29. deTM does not autmatically invoke mv2junk so that it can
  30. work without having to lock the news files.  mv2junk just
  31. has the effect of transferring deTM's results into the
  32. junk news directory so that process_junk can get to it.
  33. I would recommend at least reading the comments in
  34. deTM before trying to run it.
  35.  
  36. deTM_unbatch is a C program, it was too crappy to do as a
  37. shell script.  I would be willing to install #define's for
  38. portability if anybody wants to contribute them.  deTM_unbatch
  39. has the effect of breaking down a batched news file into its
  40. constituent articles.
  41.  
  42. ============================================================
  43. deTM
  44. ============================================================
  45. SPOOL=/usr/spool/news
  46. LIB=/usr/local/lib/news
  47. ACTIVE=$LIB/active
  48. LOG=$LIB/log
  49. JUNK=$SPOOL/junk
  50. NEWSBIN=$SPOOL/bin
  51. UUCPDIR=$SPOOL/uucp
  52. PATH=/usr/local:/bin:/usr/bin:$NEWSBIN
  53. FOO=trash    # Only needed to prevent "set" headaches.
  54. #
  55. #    Process TM files.  Three cases are known:
  56. #        1. Empty file (that is easy!)
  57. #        2. Mail file -- send it to the intended
  58. #            recipient.
  59. #        3. Compressed mail -- this is the case
  60. #            that takes all the code.
  61. #
  62. #    This script assumes that the TM files have been moved into the
  63. #    directory $UUCPDIR/TM.  It is unwise to process the TM
  64. #    files in /usr/spool/uucp without somehow turning off all the
  65. #    uucp stuff, and moving the files is easy enough to do.
  66. #
  67. cd $UUCPDIR/TM
  68. for i in TM.?????.???
  69. do
  70.     filetype=`file $i | sed "s/.*:    //"`
  71.     case "$filetype" in
  72.     empty)        rm -f $i ;;
  73.     "ascii text")    receiver=`sed "s/^To: //p/" $i`
  74.             case "$receiver" in
  75.             "")    ;;
  76.             *)    mail $receiver < $i
  77.             esac ;;
  78.     data)        testing=`( /usr/local/lib/news/compress -d < $i 2>&1 ) |
  79.                             sed 1q`
  80.             case "$testing" in
  81.             "stdin: not in compressed format"*)
  82.                 testing=`( tar tvf $i 2>&1 ) | sed 1q`
  83.                 case "$testing" in
  84.                 "tar: errno returned 0, Can't read input"*) ;;
  85.                 "directory checksum error"*) ;;
  86.                 *)    echo $i may be a tar-format data file. 1>&2
  87.                     continue
  88.                 esac
  89.                 testing=`( cpio -itv < $i 2>&1 ) | sed 1q`
  90.                 case "$testing" in
  91.                 "Out of phase--get help")
  92.                     echo $i is a data file of undetermined format ;;
  93.                 *)    echo $i may be a cpio-format data file. 1>&2
  94.                 esac
  95.                 continue
  96.             esac
  97.             (mkdir $UUCPDIR/$i 2>&1) > /dev/null
  98.             cd $UUCPDIR/$i
  99.             /usr/local/lib/news/compress -d < $UUCPDIR/TM/$i |
  100.                 deTM_unbatch $i
  101.             cd $UUCPDIR/TM ;;
  102.     *)        echo "filetype is $filetype!!" 1>&2 ;;
  103.     esac
  104. done
  105.  
  106. #
  107. #    Make a directory containing all the news articles, without
  108. #    duplication.  "deTM_unbatch" creates files named after their article ID.
  109. #    "deTM_unbatch" also creates in each of the "TM" directories containing
  110. #    the news articles, a file called "index" that is a list of all the
  111. #    article ID's (== filenames) in the TM directory.
  112. #
  113. cd $UUCPDIR
  114. zerodirs=`find $UUCPDIR/*/index -size 0 -print`
  115. rm -f `echo $zerodirs`
  116. rmdir `echo $zerodirs | sed "s/.index//g"`
  117. mkdir all_articles
  118. for i in TM.?????.???
  119. do
  120.     if test ! -d $UUCPDIR/$i
  121.     then
  122.         echo Oh, how terrible -- $UUCPDIR/$i not a directory! 1>&2
  123.         exit
  124.     fi
  125.     cd $UUCPDIR/$i
  126.     for j in *
  127.     do
  128.         case "$j" in
  129.         index)    continue ;;
  130.         [1-9]*)    destination=$UUCPDIR/all_articles/$j
  131.             if test ! -f "$destination"
  132.             then
  133.                 ln $j "$destination"
  134.             else
  135.                 set $FOO `ls -l "$destination"`
  136.                 oldsize=$6
  137.                 set $FOO `ls -l $UUCPDIR/$i/$j`
  138.                 newsize=$6
  139.                 if test "$oldsize" -lt "$newsize"
  140.                 then
  141.                     rm -f "$destination"
  142.                     ln $UUCPDIR/$i/$j $destination
  143.                 fi
  144.             fi ;;
  145.         *)    echo Oooh, what a weird file -- $UUCPDIR/$i/$j 1>&2
  146.         esac
  147.     done
  148. done
  149. #
  150. #    Now run "mv2junk", and then "process_junk".  Those two programs should
  151. #    be run with normal news processing disabled, to avoid having two
  152. #    programs simultaneously trying to update $ACTIVE.
  153. #
  154. ============================================================
  155. de_TMunbatch.c
  156. ============================================================
  157. /*
  158.  * unbatchnews: extract news in batched format and process it one article
  159.  * at a time.  The format looks like
  160.  *    #! rnews 1234
  161.  *    article containing 1234 characters
  162.  *    #! rnews 4321
  163.  *    article containing 4321 characters
  164.  *
  165.  *    Special purpose processing: Create new files in
  166.  *        ~news/uucp/TM* using the article ID as the filename.
  167.  */
  168.  
  169. #ifndef lint
  170. static char    *SccsId = "@(#)unbatch.c    1.8    9/3/84";
  171. #endif !lint
  172.  
  173. # include <stdio.h>
  174.  
  175. char buf[BUFSIZ];
  176. char hdr[BUFSIZ];
  177.  
  178. static char RNEWS_STR[] = "#! rnews ";
  179. static char MSG_STR[] = "Message-ID: <";
  180. static char TMPNAME[(sizeof "/usr/spool/news/uucp/") + (sizeof "TM.xxxxx.xxx")] =
  181.     "/usr/spool/news/uucp/";
  182.  
  183. main(argc, argv)
  184. int argc;
  185. char **argv;
  186. {
  187.     register int length, x;
  188.     register FILE *ndx_pfn, *pfn = NULL;
  189.     register long size;
  190.     register char *angle_brack, *idptr;
  191.     char filename[BUFSIZ];
  192.     char *index(), *gets();
  193.     long atol();
  194.  
  195.     if ((argc != 2) ||
  196.         (strlen (argv[1]) != 12) ||
  197.         (0 != strncmp ("TM.", argv[1], 3)))
  198.     {
  199.         fprintf (stderr, "Argument error, argv[1]=%s.\n", argv[1]);
  200.         exit (1);
  201.     }
  202.  
  203.     strcat (TMPNAME, argv[1]);
  204.     sprintf (filename, "%s/index", TMPNAME);
  205.     if (0 == (ndx_pfn = fopen (filename, "w")))
  206.         perror();
  207.     gets (buf);
  208.     while (0 == (x = strncmp (buf, RNEWS_STR, (sizeof RNEWS_STR) - 1)))
  209.     {
  210.         size = atol (buf - 1 + (sizeof RNEWS_STR));
  211.         if(size <= 0)
  212.         {
  213.             fprintf (stderr, "Bad size=%d.\n", size);
  214.             exit (3);
  215.         }
  216.         *hdr = NULL;
  217.         pfn = NULL;
  218.         while ((pfn == NULL)  &&  (size > 0)  &&  !feof(stdin))
  219.         {
  220.             fgets (buf, BUFSIZ, stdin);
  221.             /* Save header info until article ID arrives. */
  222.             strcat (hdr, buf);
  223.             if (0 == strncmp (MSG_STR, buf, (sizeof MSG_STR) - 1))
  224.             {
  225.                 idptr = buf + (sizeof MSG_STR) - 1;
  226.                 if (angle_brack = index (idptr, '>'))
  227.                 {
  228.                     *angle_brack = NULL;
  229.                     sprintf(filename,"%s/%s",TMPNAME,idptr);
  230.                     pfn = fopen(filename, "w");
  231.                     fprintf (ndx_pfn, "%s\n", idptr);
  232.                     fwrite (hdr,length = strlen(hdr),1,pfn);
  233.                     if ( 0 >= (size -= length))
  234.                     {
  235.                         fprintf (stderr,
  236.                         "Oops, header size too big.\n");
  237.                         exit (4);
  238.                     }
  239.                 }
  240.                 else
  241.                 {
  242.                     fprintf (stderr,
  243.                         "Oops, bad Message-ID.\n");
  244.                     exit (5);
  245.                 }
  246.             }
  247.         }
  248.         if (pfn == NULL)    /* Article ID was not found... */
  249.             exit();
  250.         while (fgets (buf, BUFSIZ, stdin)    &&    (0 < size))
  251.         {
  252.             fwrite (buf, length=strlen(buf), 1, pfn);
  253.             size -= length;
  254.         }
  255.         if (size != 0)
  256.         {
  257.             fprintf (stderr, "Article size != %d, filename=%s.\n",
  258.                     size, filename);
  259.             exit (6);
  260.         }
  261.         fclose(pfn);
  262.     }
  263.     if (x)    /* x != 0   implies that the RNEWS strncmp test failed above. */
  264.     {
  265.         fprintf(stderr, "out of sync, skipping %s\n", buf);
  266.         exit (2);
  267.     }
  268. }
  269. ============================================================
  270. mv2junk
  271. ============================================================
  272. SPOOL=/usr/spool/news
  273. NEWSBIN=$SPOOL/bin
  274. LIB=/usr/local/lib/news
  275. ACTIVE=$LIB/active
  276. JUNK=$SPOOL/junk
  277.  
  278. PATH=/usr/local:/bin:/usr/bin:$NEWSBIN
  279. (cd $LIB; tar cf - active ) | (cd /usr/tmp; tar xpvf - )    # Save a $ACTIVE
  280. count=`awk '$1 == "junk" {print $2}' $ACTIVE`
  281. case "$count" in
  282. "")    exit
  283. esac
  284. curdir=`pwd | sed "s/ //"`
  285. for artdir in $*
  286. do
  287.     cd $curdir/$artdir
  288.     oldarts=`ls | sort +n`  ||
  289.     { echo Something went wrong during $JUNK cleanup.
  290.       exit ; }
  291.     for article in $oldarts
  292.     do
  293.         count=`expr $count + 1`
  294.         if test -f $count
  295.         then
  296.             echo ln $article $count fails during $JUNK cleanup.
  297.         else
  298.             ln $article $JUNK/$count
  299.         fi
  300.     done
  301. done
  302. modactive junk $count
  303. echo diff $LIB/active /usr/tmp/active
  304. diff $LIB/active /usr/tmp/active
  305. -- 
  306.  
  307. Charlie Perkins, IBM T.J. Watson Research    philabs!polaris!charliep,
  308.         perk%YKTVMX.BITNET@berkeley,  perk.yktvmx.ibm@csnet-relay
  309.