fmc@cnam.cnam.fr (Frederic Chauveau) (02/24/91)
Submitted-by: Frederic Chauveau <fmc@cnam.cnam.fr> Posting-number: Volume 17, Issue 15 Archive-name: news_split/part01 Supersedes: news_split1.6: Volume 17, Issue 1 This brings news_split to patch level 2. As the shar file is only 18k, I am submitting it full. [fmc] ---- Cut Here and unpack ---- #!/bin/sh # This is news_split, a shell archive (shar 3.32) # made 02/22/1991 15:23 UTC by fmc@cnam.cnam.fr # Source directory /users/labinf/fmc/tools/news_split # # existing files will NOT be overwritten # # This shar contains: # length mode name # ------ ---------- ------------------------------------------ # 8228 -rw-r--r-- news_split.c # 130 -rw-r--r-- patchlevel.h # 660 -rw-r--r-- Makefile # 3402 -rw-r--r-- README # 2256 -rw-r--r-- INSTALL # if touch 2>&1 | fgrep 'amc' > /dev/null then TOUCH=touch else TOUCH=true fi # ============= news_split.c ============== if test X"$1" != X"-c" -a -f 'news_split.c'; then echo "File already exists: skipping 'news_split.c'" else echo "x - extracting news_split.c (Text)" sed 's/^X//' << 'SHAR_EOF' > news_split.c && X X/* X * news_split [fmc] 21/02/91 Version 1.8 X * Browse a given NewsGroup (usualy comp.sources.??? X * and try to update/maintain a directory for the X * sources found in it. X * I use it to maintain the ~ftp/pub/comp.sources.??? X * from the equivalent News directories. X * X * Usage: news_split [-sn#a] [-l logdir] group ... group X * or news_split [-sn#a] [-l logdir] -f groupfile X * X * In the second case, groupfile is a file containing X * each group to be processed, one per line. X * X * CopyLeft and CopyWrong Frederic Chauveau [fmc@cnam.cnam.fr] X */ X X#include <stdio.h> X#ifdef NOUNISTD X#include <sys/file.h> X#else X#include <unistd.h> X#endif X#include <ctype.h> X#include <errno.h> X#include <sys/types.h> X#include <sys/dir.h> X#include "patchlevel.h" X X#ifndef NEWS_SPOOL X#define NEWS_SPOOL "/usr/spool/news" X#endif /* no NEWS_SPOOL */ X X#ifndef FTP_DIR X#define FTP_DIR "/local/ftp/pub" X#endif /* no FTP_DIR */ X X#ifndef LOGFILE X#define LOGFILE "%s/Index.ns" X#endif /* no LOGFILE */ X X#ifndef LOGDIR X#define LOGDIR FTP_DIR X#endif X XFILE *logfile; Xchar *logdir = LOGDIR; X Xchar logname[BUFSIZ]; Xchar Supercede_P = 1; Xchar force_number = 0; X X#ifndef DIRENT X#define DIRENT struct direct X#endif X X#ifdef NOSCANDIR X Xint scandir(DirName,NameList,Select,Sort) Xchar *DirName; XDIRENT *(*NameList[]); Xint (*Select)(), (*Sort)(); { X int c = 0; X DIRENT **tab, *entry; X DIR *dirp; X X dirp = opendir(DirName); X while (entry = readdir(dirp)) X c += (Select ? (*Select)(entry) : 1); X tab = (DIRENT **) malloc(c * sizeof(DIRENT *)); X rewinddir(dirp); c = 0; X while (entry = readdir(dirp)) X if (!Select || (*Select)(entry)) X tab[c++] = entry; X if (Sort) X qsort(tab,c,sizeof(DIRENT *),Sort); X *NameList = tab; X return c; X} X X#endif /* NOSCANDIR */ X XDirSelect(dp) XDIRENT *dp; { X return isdigit(dp->d_name[0]); X} X Xvoid CreateDirAndFile(dirname,infile) Xchar *dirname; XFILE *infile; { X FILE *outfile; X char *p = dirname; X char buf[BUFSIZ]; X X while (p = (char *) strchr(p+1,'/')) X { X *p = '\0'; X if (mkdir(dirname,0766) && (errno != EEXIST)) X { X FILE *foo = stderr; X *stderr = *logfile; X perror(dirname); X *stderr = *foo; X perror(dirname); X return; X } X *p = '/'; X } X if (!infile) X return; X#ifdef COMPRESS X strcat(dirname,".Z"); X#endif X if (access(dirname,F_OK) != -1) X { X fprintf(stderr," Warning: %s %s\n", X (Supercede_P ? "Superceding" : "Not Superceding"),dirname); X fprintf(logfile," Warning: %s %s\n", X (Supercede_P ? "Superceding" : "Not Superceding"),dirname); X if (!Supercede_P) X return; X } X#ifdef COMPRESS X sprintf(buf,"%s > %s",COMPRESS,dirname); /* .Z already tacked at the end */ X outfile = popen(buf,"w"); X#else X outfile = fopen(dirname,"w"); X#endif X if (!outfile) X { X FILE *foo = stderr; X *stderr = *logfile; X perror(dirname); X *stderr = *foo; X perror(dirname); X } X else X { X rewind(infile); X while (fgets(buf,BUFSIZ,infile)) X fputs(buf,outfile); X#ifdef COMPRESS X pclose(outfile); X#else X fclose(outfile); X#endif X } X} X Xvoid SaveIt(pnumb,aname,subj,anumb,infile,group) Xchar *pnumb, *aname, *group, *subj, *anumb; XFILE *infile; { X int vol, iss; X char dirname[BUFSIZ]; X X pnumb[strlen(pnumb)-1] = '\0'; X if (force_number) X { X fprintf(logfile,"Art #%s: %s",anumb,subj); X sprintf(dirname,"%s/%s/%s",FTP_DIR,group,anumb); X CreateDirAndFile(dirname,infile); X return; X } X if (sscanf(pnumb,"Posting-number: Volume %d, Info%*[^0-9] %d",&vol,&iss) != 2) X { X if (sscanf(pnumb,"Posting-number: Volume %d %*[^0-9] %d",&vol,&iss) != 2) X { X fprintf(stderr," Couldn't get volume for article [%s]\n",anumb); X fprintf(logfile," Couldn't get volume for article [%s]\n",anumb); X sprintf(dirname,"%s/%s/%s",FTP_DIR,group,anumb); X CreateDirAndFile(dirname,infile); X } X } X else X sprintf(aname,"Archive-name: Info%d\n",iss); X if (!aname[0]) X { X sprintf(dirname,"%s/%s/%s",FTP_DIR,group,subj); X CreateDirAndFile(dirname,infile); X } X else X { X aname += 14; aname[strlen(aname)-1] = '\0'; X sprintf(dirname,"%s/%s/volume%d/%s",FTP_DIR,group,vol,aname); X fprintf(logfile,"Volume %3d, Issue %3d :\t\t%s\n",vol,iss,aname); X CreateDirAndFile(dirname,infile); X } X} X Xvoid ProcArticle(art,group) Xchar *art, *group; { X FILE *inp; X char buf[BUFSIZ], postnum[BUFSIZ], archnam[BUFSIZ]; X char subject[BUFSIZ]; X int i = 0; X X if (!(inp = fopen(art,"r"))) X { X perror(art); X return; X } X *postnum = *archnam = *subject = '\0'; X while (fgets(buf,BUFSIZ,inp)) X { X if ((*postnum && *archnam && *subject) || X (*buf == '#') || (i > 30)) X { X SaveIt(postnum,archnam,subject,art,inp,group); X break; X } X if (!strncmp("Subject:",buf,8)) X { X if (force_number) X strcpy(subject,buf+8); X else X sscanf(buf,"Subject: %[^ :]",subject); X } X else if (!strncmp("Posting-number",buf,14)) X strcpy(postnum,buf); X else if (!strncmp("Archive-name",buf,12)) X strcpy(archnam,buf); X i++; X } X fclose(inp); X} X XGroupToDir(group,dirname) Xchar *group, *dirname; { X char *p; X strcpy(dirname,group); X X for (p = (char *) strchr(dirname,'.'); p; p = (char *) strchr(p,'.')) X *p++ = '/'; X} X Xvoid ProcGroup(group,first,last) Xint *first, *last; Xchar *group; { X register int i, art_num, max, nf = *first, nl = *last; X char dirname[BUFSIZ]; X DIRENT **namelist; X X chdir(NEWS_SPOOL); X GroupToDir(group,dirname); X chdir(dirname); X max = scandir(".",&namelist,DirSelect,NULL); X if (max == -1) X { X perror(dirname); X fprintf(stderr,"Cannot scan %s/%s\n",NEWS_SPOOL,group); X return; X } X for (i = 0; i < max; i++) X { X art_num = atoi(namelist[i]->d_name); X if (art_num < *first) X ProcArticle(namelist[i]->d_name,group); X else if (art_num > *last) X ProcArticle(namelist[i]->d_name,group); X if (art_num && art_num < nf) X nf = art_num; X if (art_num && art_num > nl) X nl = art_num; X } X *first = nf; X *last = nl; X} X XFILE *OpenLog(group_name) Xchar *group_name; { X char tmp[BUFSIZ], ln[BUFSIZ]; X FILE *logfile; X X sprintf(tmp,LOGFILE,group_name); X sprintf(ln,"%s/%s",logdir,tmp); X CreateDirAndFile(ln,NULL); X if (!(logfile = fopen(ln,"w"))) X { X perror(ln); X logfile = stderr; X } X return logfile; X} X Xvoid ProcName(group_name, backtodir) Xchar *group_name, *backtodir; { X FILE *tmp; X int first, last; X long now; X X now = time((long *) 0); X logfile = OpenLog(group_name); X tmp = fopen(group_name,"r"); X if (!tmp) X { X first = 9999; X last = 0; X } X else X { X fscanf(tmp,"%d %d",&first,&last); X fclose(tmp); X } X fprintf(logfile," -- Processing group %s (%d %d) at %s",group_name,first, X last,ctime(&now)); X fprintf(stderr,"Processing group %s (%d %d)\n",group_name,first,last); X ProcGroup(group_name,&first,&last); X chdir(backtodir); X tmp = fopen(group_name,"w"); X fprintf(tmp,"%d %d\n",first,last); X fclose(tmp); X if (logfile != stderr) X fclose(logfile); X fprintf(stderr,"Processed group %s (%d %d)\n",group_name,first,last); X} X X Xvoid Usage(s,pn) Xchar *s, *pn; { X fprintf(stderr,"Unknown option %s\n",s); X fprintf(stderr,"Usage: %s [-sn] [-l logdir] [-f group_file | group1 .. groupn]\n",pn); X exit(1); X} X Xmain(argc,argv) Xchar **argv; { X FILE *from_file = NULL; X char cwd[BUFSIZ], *pname = *argv; X X getcwd(cwd,BUFSIZ); X while (++argv, --argc) X { X if (**argv == '-') X { X switch (argv[0][1]) X { X case 's' : case 'S' : Supercede_P = 1; break; X case 'n' : case 'N' : Supercede_P = 0; break; X case 'l' : case 'L' : logdir = argv[1]; argv++; argc--; break; X case '#' : force_number = 1; break; X case 'a' : force_number = 0; break; X case 'f' : case 'F' : X from_file = fopen(argv[1],"r"); X if (!from_file) X { X perror(argv[1]); X argv++; argc--; X } X break; X default: Usage(*argv,pname); X } X continue; X } X if (from_file) X { X char gname[BUFSIZ]; X X while (fgets(gname,BUFSIZ,from_file)) X { X gname[strlen(gname)-1] = '\0'; X ProcName(gname,cwd); X } X fclose(from_file); X from_file = NULL; X } X else X ProcName(*argv,cwd); X } X} X X SHAR_EOF $TOUCH -am 0222162391 news_split.c && chmod 0644 news_split.c || echo "restore of news_split.c failed" set `wc -c news_split.c`;Wc_c=$1 if test "$Wc_c" != "8228"; then echo original size 8228, current size $Wc_c fi fi # ============= patchlevel.h ============== if test X"$1" != X"-c" -a -f 'patchlevel.h'; then echo "File already exists: skipping 'patchlevel.h'" else echo "x - extracting patchlevel.h (Text)" sed 's/^X//' << 'SHAR_EOF' > patchlevel.h && X/* X * patchlevel.hfor news_split. X * First patch updates from v1.6 to v1.7 X * there was NO PATCHLEVEL 1 X */ X X#define PATCHLEVEL 2 SHAR_EOF $TOUCH -am 0222111391 patchlevel.h && chmod 0644 patchlevel.h || echo "restore of patchlevel.h failed" set `wc -c patchlevel.h`;Wc_c=$1 if test "$Wc_c" != "130"; then echo original size 130, current size $Wc_c fi fi # ============= Makefile ============== if test X"$1" != X"-c" -a -f 'Makefile'; then echo "File already exists: skipping 'Makefile'" else echo "x - extracting Makefile (Text)" sed 's/^X//' << 'SHAR_EOF' > Makefile && XALLFILES = news_split.c patchlevel.h Makefile README INSTALL X X# for system with no scandir function add -DNOSCANDIR to CFLAGS X# for system with no <unistd.h> file, add -dNOUNISTD to CFLAGS X# if you want to save in compressed format add X# -DCOMPRESS=\"compress\" to CFLAGS X XCFLAGS = -O -DCOMPRESS=\"compress\i exit 0 # Just in case... -- Kent Landfield INTERNET: kent@sparky.IMD.Sterling.COM Sterling Software, IMD UUCP: uunet!sparky!kent Phone: (402) 291-8300 FAX: (402) 291-4362 Please send comp.sources.misc-related mail to kent@uunet.uu.net.