|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T U
Length: 58859 (0xe5eb) Types: TextFile Notes: Uncompressed file
└─⟦9ae75bfbd⟧ Bits:30007242 EUUGD3: Starter Kit └─⟦ba1215703⟧ »EurOpenD3/news/cnews/10-Jan-1990.Z« └─⟦this⟧
To: utai!uunet!source-patches Subject: C News patch of 10-Jan-1990 This one introduces one major change: relaynews now completely implements the silly "Supersedes" header. We still think that most current uses of Supersedes do not justify it, but Brad Templeton (always the nuisance :-)) has found a real use for it, and there may be more. Actually, to head off yet more silly new headers, we implement an "Also-Control" header that lets any control-message function be piggybacked on a normal article, and do "Supersedes" by s/Supersedes:/Also-Control: cancel/. We've trying to clear our fairly lengthy low-priority-to-be-looked-at lists, some of it long overdue. A spacefor variant for Xenix and Microport Unixes. Revision of expire and mkdbm to invoke dbmclose(), in preparation for dbz, and a fake dbmclose() for systems that have dbm but not dbmclose(). Expire's reporting of bad expiry dates is now optional, invoked by -g. Everything has been checked over to be sure that files under $NEWSARTS with dots in their names are always ignored, so people who want to annotate the tree can do so. Memory leak in histinfo fixed. Upact and updatemin use a more sensible name for their temporary file, and are a bit more paranoid about it. Spurious system noises in error messages removed. More fixes for rsh misbehavior. expire -t output format documented. Reporting of articles arriving in newsgroups you don't subscribe to. Beginnings of a new document, notebook/problems, discussing common porting problems. And the usual bunch of minor cleanups. start of patch 10-Jan-1990 (suggested archive name: `pch10Jan90.Z') this should be run with patch -p0 <thisfile The following is a complete list of patches to date. Prereq: 23-Jun-1989 Prereq: 7-Jul-1989 Prereq: 23-Jul-1989 Prereq: 22-Aug-1989 Prereq: 24-Aug-1989 Prereq: 14-Sep-1989 Prereq: 13-Nov-1989 *** PATCHDATES.old Wed Jan 10 17:56:27 1990 --- PATCHDATES Wed Jan 10 17:56:27 1990 *************** *** 1,7 **** --- 1,8 ---- 23-Jun-1989 7-Jul-1989 23-Jul-1989 22-Aug-1989 24-Aug-1989 14-Sep-1989 13-Nov-1989 + 10-Jan-1990 Changed files, if any: *** cnpatch/old/COPYRIGHT Tue Jun 20 18:55:22 1989 --- COPYRIGHT Sat Dec 30 23:11:40 1989 *************** *** 1,4 **** /* ! * Copyright (c) University of Toronto 1985, 1986, 1987, 1988, 1989. * All rights reserved. * Written mostly by Geoffrey Collyer and Henry Spencer. --- 1,4 ---- /* ! * Copyright (c) University of Toronto 1985, 1986, 1987, 1988, 1989, 1990. * All rights reserved. * Written mostly by Geoffrey Collyer and Henry Spencer. *** cnpatch/old/ROADMAP Tue Jun 20 18:55:27 1989 --- ROADMAP Sat Dec 30 23:11:26 1989 *************** *** 6,10 **** an official part of C News. doc User documentation, including "install" which discusses how to ! install C News. expire Expire and friends, including history rebuilding and active-file updating (neither of which is done by expire in C News). Ought --- 6,14 ---- an official part of C News. doc User documentation, including "install" which discusses how to ! install C News. Although the documentation is supplied as troff ! sources, no complex formatting is used and it should be quite ! readable even if you don't have a troff to format it. We supply ! preformatted output for doc/install, as doc/install.out, just ! as a precaution. expire Expire and friends, including history rebuilding and active-file updating (neither of which is done by expire in C News). Ought *** cnpatch/old/batch/Makefile Mon Nov 13 17:39:42 1989 --- batch/Makefile Sat Dec 30 02:13:07 1989 *************** *** 44,47 **** --- 44,50 ---- for f in $(PGMS) ; do cmp $(PGMDIR)/$$f $$f ; done + check: $(PGMS) + for f in $(PGMS) ; do cmp $(PGMDIR)/$$f $$f || true ; done + newsinstall: batchparms -if test ! -d $(OUTGOING) ; then mkdir $(OUTGOING) ; fi *** cnpatch/old/conf/Makefile Thu Aug 24 16:39:47 1989 --- conf/Makefile Sun Dec 31 01:07:31 1989 *************** *** 16,19 **** --- 16,20 ---- DIRS = batch conf expire h hfake input $(LIBDIRS) misc relay rna CMPDIRS = batch conf expire input man misc relay rna + RDIRS = batch expire input relay SHS = doit.root doit.bin doit.news again.root *************** *** 46,51 **** ./subst -f substitutions `sed 's;^;../;' subst.hs subst.gc` - spacefors: spacefor.sysv spacefor.v7 spacefor.sgi spacefor.bsd spacefor.ultrix spacefor.null - spacefor.bsd: spacefor.proto Makefile cp spacefor.proto $@ --- 47,50 ---- *************** *** 57,60 **** --- 56,62 ---- sed '/dfunit=/s/1024/512/;/awk/s~|~| sed "s/.*:/: :/" |~;/nf = 4/s//nf = 3/;/stupid/s/4BSD/System V/' spacefor.proto >$@ + spacefor.xenix: spacefor.proto Makefile + sed '/dfunit=/s/1024/512/;/awk/s~|~| sed "s/.*:/: :/" |~;/nr = 2/s//nr = 1/;/nf = 4/s//nf = 3/;/stupid/s/4BSD/Xenix/' spacefor.proto >$@ + spacefor.sgi: spacefor.proto Makefile sed '/dfunit=/s/1024/512/;/nf = 4/s//nf = 5/;/stupid/s/4BSD/SGI/' spacefor.proto >$@ *************** *** 86,90 **** clean: rm -f spacefor.sysv spacefor.v7 spacefor.null queuelen.null ! rm -f spacefor.sgi rm -f config mailname organization server whoami hostname errlog rm -f substitutions history history.pag history.dir active localgroups --- 88,92 ---- clean: rm -f spacefor.sysv spacefor.v7 spacefor.null queuelen.null ! rm -f spacefor.sgi spacefor.xenix rm -f config mailname organization server whoami hostname errlog rm -f substitutions history history.pag history.dir active localgroups *************** *** 108,111 **** --- 110,116 ---- cmps: for d in $(CMPDIRS) ; do cd ../$$d ; make cmp RBIN=/usr/lib/uucp/bin ; done + + rs: + for d in $(RDIRS) ; do cd ../$$d ; make r ; done save: $(SHS) *** cnpatch/old/conf/build Mon Nov 13 17:39:43 1989 --- conf/build Mon Jan 1 00:25:38 1990 *************** *** 377,382 **** esac dbm="DBM=$answer" ;; ! *) fake="$fake dbm.o" dbm='DBM=' echo "Okay, we'll fake it for you. You might want to look at" --- 377,387 ---- esac dbm="DBM=$answer" + ./query 'Does your dbm have a dbmclose() function [no]? ' + read answer + case "$answer" in + n*|N*|'') fake="$fake dbmclose.o" ;; + esac ;; ! *) fake="$fake dbm.o dbmclose.o" dbm='DBM=' echo "Okay, we'll fake it for you. You might want to look at" *************** *** 392,398 **** echo 'are faster than those in any stdio we know; they are compatible with' echo 'most AT&T-derived stdios. If they work on your system, they are a' ! echo 'major performance win for C News. There is a simple compatibility' ! echo 'check run after the library is built. The only system we know of' ! echo 'where the test works but the functions do not is SunOS 4.0.' ./query 'Do you want to use our fast stdio library [yes]? ' read libstdio --- 397,403 ---- echo 'are faster than those in any stdio we know; they are compatible with' echo 'most AT&T-derived stdios. If they work on your system, they are a' ! echo 'major performance win for C News. There is a fairly thorough' ! echo 'compatibility check run after the library is built; as far as we' ! echo 'know, if the test works, the functions do (even on SunOS 4.0).' ./query 'Do you want to use our fast stdio library [yes]? ' read libstdio *************** *** 602,605 **** --- 607,611 ---- echo ' sgi Silicon Graphics Iris systems' echo ' ultrix DEC Ultrix 3.0 (and later) (and earlier??)' + echo ' xenix some (all?) Xenixes, notably SCO' echo ' v7 plain old style: no headers or fluff, just name and number' echo " null don't know or don't care how much space is available" *************** *** 610,614 **** case "$dftype" in '') dftype=bsd ;; ! sysv) echo 'Beware -- test "spacefor" to make sure it works.' echo 'System V "df" formats vary widely, indeed wildly.' echo '"Consider it standard". Sure.' --- 616,621 ---- case "$dftype" in '') dftype=bsd ;; ! sysv|xenix) ! echo 'Beware -- test "spacefor" to make sure it works.' echo 'System V "df" formats vary widely, indeed wildly.' echo '"Consider it standard". Sure.' *************** *** 616,620 **** esac case "$dftype" in ! bsd|sysv|sgi|ultrix|v7|null) break ;; esac echo 'Sorry, no such choice is available.' --- 623,627 ---- esac case "$dftype" in ! bsd|sysv|sgi|ultrix|xenix|v7|null) break ;; esac echo 'Sorry, no such choice is available.' *** cnpatch/old/conf/spacefor.proto Thu Sep 14 16:03:27 1989 --- conf/spacefor.proto Thu Nov 16 17:07:30 1989 *************** *** 22,26 **** if test " $server" != " $me" then ! exec rsh $server /bin/sh -c "'PATH=$PATH `basename $0` $*'" # does not return fi --- 22,26 ---- if test " $server" != " $me" then ! exec rsh $server -n /bin/sh -c "'PATH=$PATH `basename $0` $*'" # does not return fi *************** *** 33,37 **** # argument to df, df units, and free space desired (in df units) ! dfunit=1024 # default unit (bytes) case "$2" in incoming) arg="$NEWSARTS/in.coming" ; desire=5000 ;; --- 33,37 ---- # argument to df, df units, and free space desired (in df units) ! dfunit=1024 # default df unit (bytes) case "$2" in incoming) arg="$NEWSARTS/in.coming" ; desire=5000 ;; *************** *** 43,46 **** --- 43,53 ---- exit 2 ;; esac + + # In the following, the initialization of nf determines which field the + # block count comes from, and the one for nr determines which line. For + # System V, the Makefile edits in a sed which tries to strip silliness + # off in a reasonably System-V-variant-indepedent way. Expr would be + # faster than awk, but on a 16-bit machine, expr does 16-bit arithmetic, + # which isn't enough. # this is set up for the stupid 4BSD df *** cnpatch/old/conf/sys.proto Thu Sep 14 16:03:28 1989 --- conf/sys.proto Wed Jan 3 15:11:50 1990 *************** *** 1,6 **** # line indicating what we are willing to receive; note local groups on end ME:comp,news,sci,rec,misc,soc,talk,to,can,ont,tor,ut ! # sample insignificant feed not using batching huey:news.config,to.huey/all::uux - -r -gd huey!rnews --- 1,10 ---- + # Only the ME line is mandatory; the others are just samples of how to do + # things. Virtually everything will need modifying for your local feeds + # and newsgroups. + # line indicating what we are willing to receive; note local groups on end ME:comp,news,sci,rec,misc,soc,talk,to,can,ont,tor,ut ! # sample insignificant feed not using batching (for special situations only) huey:news.config,to.huey/all::uux - -r -gd huey!rnews *************** *** 20,24 **** # Send ihave telling louie what we have -- batcher turns the batch into a # giant control message and posts it to "to.louie". (#1) ! louie:rec.music.synth,!to/all,!sendme,!ihave:I:louie.ihave/togo # Send sendme in response to ihave from louie -- again, turned by batcher # into giant control message posted to "to.louie". (#3) --- 24,28 ---- # Send ihave telling louie what we have -- batcher turns the batch into a # giant control message and posts it to "to.louie". (#1) ! louie:comp,news,sci,rec,misc,soc,talk,!to/all,!sendme,!ihave:I:louie.ihave/togo # Send sendme in response to ihave from louie -- again, turned by batcher # into giant control message posted to "to.louie". (#3) *************** *** 29,32 **** louie-real:to.louie/sendme:f:louie/togo # Actually the last two could be combined. ! # and send local postings to louie without waiting (beware ihave/sendme) louie-local:comp,news,sci,rec,misc,soc,talk/all,!sendme,!ihave:L: --- 33,38 ---- louie-real:to.louie/sendme:f:louie/togo # Actually the last two could be combined. ! ! # also, since ihave/sendme is slow, send local postings to louie without ! # waiting (beware ihave/sendme) louie-local:comp,news,sci,rec,misc,soc,talk/all,!sendme,!ihave:L: *** cnpatch/old/doc/interface Tue Aug 22 14:47:44 1989 --- doc/interface Wed Jan 3 14:06:13 1990 *************** *** 1,3 **** ! .DA "19 Aug 1989" .TL The Interface Between C News And The Outside World --- 1,3 ---- ! .DA "3 Jan 1990" .TL The Interface Between C News And The Outside World *************** *** 332,349 **** such an update. It should be run as \fInews\fR. ! .PP ! \fIRelay/relaynews\fR ! does not implement the ``Supersedes:'' header, which we loathe ! as a crude solution to the wrong problem. ! Alas, the network-map distribution in ! \fIcomp.mail.maps\fR relies heavily on it. ! Our preferred approach is to process map articles as they arrive and ! then expire them normally (using \fIexpire\fR's expiry-date-override ! features to insist that they expire promptly). ! However, for those who don't do this, and don't want to have megabytes ! of obsolete map data piling up, ! \fIexpire/superkludge\fR will remove superseded files in specified ! newsgroups. ! It should be run as \fInews\fR by \fIcron\fR, perhaps nightly. .SH Reboots and Administration --- 332,337 ---- such an update. It should be run as \fInews\fR. ! A much faster, but somewhat less portable, C implementation is ! supplied as \fIexpire/updatemin\fR. .SH Reboots and Administration *** cnpatch/old/expire/Makefile Thu Sep 14 16:03:29 1989 --- expire/Makefile Wed Jan 3 14:03:47 1990 *************** *** 7,11 **** LIBS= ../libcnews.a THEM = expire histdups histinfo histslash mkdbm mkhistory \ ! superkludge upact doexpire mkadir recovact DTR = README Makefile dircheck doexpire expire.c histdups histinfo.c \ histslash.c mkdbm.c mkhistory pgood superkludge tgood upact \ --- 7,11 ---- LIBS= ../libcnews.a THEM = expire histdups histinfo histslash mkdbm mkhistory \ ! upact doexpire mkadir recovact DTR = README Makefile dircheck doexpire expire.c histdups histinfo.c \ histslash.c mkdbm.c mkhistory pgood superkludge tgood upact \ *************** *** 31,34 **** --- 31,37 ---- for f in $(THEM) ; do cmp $(NEWSBIN)/expire/$$f $$f ; done + check: $(THEM) + for f in $(THEM) ; do cmp $(NEWSBIN)/expire/$$f $$f || true ; done + newsinstall: explist.proto -if test ! -r $(NEWSCTL)/explist ; then cp explist.proto $(NEWSCTL)/explist ; fi *************** *** 187,191 **** # the regression test proper ! r: $(THEM) $(UPACT) dircheck setup tgood pgood chmod +x dircheck $(THEM) $(RUN) -c explist --- 190,194 ---- # the regression test proper ! r: $(THEM) $(UPACT) dircheck setup tgood pgood superkludge chmod +x dircheck $(THEM) $(RUN) -c explist *** cnpatch/old/expire/README Tue Aug 22 14:47:45 1989 --- expire/README Wed Jan 3 14:02:58 1990 *************** *** 30,31 **** --- 30,33 ---- pgood and tgood are regression-test output-should-look-like-this files. mkadir is what expire invokes to create archiving subdirectories. + superkludge is an old implementation of the Supersedes header, now + superseded :-) by the full implementation in relaynews. *** cnpatch/old/expire/expire.c Mon Nov 13 17:39:44 1989 --- expire/expire.c Sun Dec 31 01:39:56 1989 *************** *** 78,81 **** --- 78,82 ---- int rebuild = 1; /* rebuild history files */ int violate = 0; /* non-rfc822 case-sensitive messageIDs */ + int getdgrump = 0; /* report un-getdate()able expiry dates */ long nkept = 0; /* count of articles not expired */ *************** *** 168,172 **** ftime(&ftnow); ! while ((c = getopt(argc, argv, "pa:sF:cn:tlvrVd")) != EOF) switch (c) { case 'p': /* print info line for archived articles */ --- 169,173 ---- ftime(&ftnow); ! while ((c = getopt(argc, argv, "pa:sF:cn:tlvrVgd")) != EOF) switch (c) { case 'p': /* print info line for archived articles */ *************** *** 203,206 **** --- 204,210 ---- violate = 1; break; + case 'g': /* report getdate() failures on expiry dates */ + getdgrump = 1; + break; case 'd': /* debug */ expdebug = 1; *************** *** 491,496 **** (void) close(old); ! if (rebuild) eufclose(new, "history.n"); if (testing) --- 495,502 ---- (void) close(old); ! if (rebuild) { eufclose(new, "history.n"); + dbmclose(); + } if (testing) *************** *** 565,569 **** else { expdate = readdate(subfield[1]); ! if (expdate == NODATE) { errno = 0; warning("bad expiry date in `%.40s...',", line); --- 571,575 ---- else { expdate = readdate(subfield[1]); ! if (expdate == NODATE && getdgrump) { errno = 0; warning("bad expiry date in `%.40s...',", line); *** cnpatch/old/expire/histinfo.c Thu Sep 14 16:03:31 1989 --- expire/histinfo.c Sat Dec 30 01:52:05 1989 *************** *** 6,9 **** --- 6,10 ---- #include <sys/types.h> #include <sys/stat.h> /* for modified time (date received) */ + #include <string.h> #include "config.h" #include "fgetmfs.h" *************** *** 55,61 **** while ((inname = fgetms(stdin)) != NULL) { inname[strlen(inname)-1] = '\0'; /* kill newline */ ! in = efopen(inname, "r"); ! process(in, inname); ! (void) fclose(in); free(inname); } --- 56,64 ---- while ((inname = fgetms(stdin)) != NULL) { inname[strlen(inname)-1] = '\0'; /* kill newline */ ! if (strchr(inname, '.') == NULL) { /* skip dot names */ ! in = efopen(inname, "r"); ! process(in, inname); ! (void) fclose(in); ! } free(inname); } *************** *** 79,83 **** static char expnm[] = "Expires: "; register char *p; - extern char *strchr(); expiry = strsave("-"); --- 82,85 ---- *************** *** 97,100 **** --- 99,104 ---- free(line); } + if (line != NULL) + free(line); /* generate the file name */ *** cnpatch/old/expire/mkdbm.c Thu Sep 14 16:03:31 1989 --- expire/mkdbm.c Tue Nov 28 19:24:46 1989 *************** *** 1,10 **** /* * mkdbm - rebuild dbm file for a history file - * - * History file on standard input; the dbm database is generated as - * hist.dir and hist.pag. */ #include <stdio.h> #include <string.h> #include "fgetmfs.h" #include "case.h" --- 1,8 ---- /* * mkdbm - rebuild dbm file for a history file */ #include <stdio.h> #include <string.h> + #include "alloc.h" #include "fgetmfs.h" #include "case.h" *************** *** 14,18 **** typedef struct { char *dptr; int dsize; } datum; ! main() { register char *scan; --- 12,18 ---- typedef struct { char *dptr; int dsize; } datum; ! main(argc, argv) ! int argc; ! char *argv[]; { register char *scan; *************** *** 21,33 **** datum rhs; register char *line; ! (void) close(creat("hist.dir", 0666)); ! (void) close(creat("hist.pag", 0666)); ! if (dbminit("hist") < 0) ! error("unable to do dbminit(\"hist\")", ""); for (;;) { ! place = ftell(stdin); ! line = fgetms(stdin); if (line == NULL) break; --- 21,40 ---- datum rhs; register char *line; + FILE *f; + extern FILE *efopen(); ! if (argc < 2) { ! fprintf(stderr, "Usage: mkdbm historyfile\n"); ! exit(2); ! } ! f = efopen(argv[1], "r"); ! (void) close(creat(str3save(argv[1], ".", "dir"), 0666)); ! (void) close(creat(str3save(argv[1], ".", "pag"), 0666)); ! if (dbminit(argv[1]) < 0) ! error("unable to do dbminit(`%s')", argv[1]); for (;;) { ! place = ftell(f); ! line = fgetms(f); if (line == NULL) break; *************** *** 49,52 **** --- 56,71 ---- free(line); } + + dbmclose(); exit(0); + } + + /* + - unprivileged - needed due to library interdependencies + */ + /* ARGSUSED */ + void + unprivileged(reason) + char *reason; + { } *** cnpatch/old/expire/mkhistory Thu Sep 14 16:03:32 1989 --- expire/mkhistory Sun Nov 26 01:32:54 1989 *************** *** 32,36 **** echo "$0: (grep history file for '@trash' to see them)" >&2 fi ! mkdbm <history.n mv history history.o && # install new ASCII history file mv history.n history && --- 32,36 ---- echo "$0: (grep history file for '@trash' to see them)" >&2 fi ! mkdbm history.n mv history history.o && # install new ASCII history file mv history.n history && *************** *** 37,39 **** rm -f history.pag && # and related dbm files rm -f history.dir && ! mv hist.pag history.pag && mv hist.dir history.dir --- 37,39 ---- rm -f history.pag && # and related dbm files rm -f history.dir && ! mv history.n.pag history.pag && mv history.n.dir history.dir *** cnpatch/old/expire/upact Tue Aug 22 14:47:46 1989 --- expire/upact Wed Dec 20 16:03:32 1989 *************** *** 18,21 **** --- 18,28 ---- esac + rm -f active.tmp + if test -f active.tmp + then + echo "$0: active.tmp exists and can't be removed; aborting" >&2 + exit 1 + fi + # lock news system lock="$NEWSCTL/LOCK" *************** *** 50,54 **** echo $group $max $min $fourth ! done <active >active.new # replace active, carefully --- 57,61 ---- echo $group $max $min $fourth ! done <active >active.tmp # replace active, carefully *************** *** 55,59 **** rm -f active.old ln active active.old ! mv active.new active exit 0 --- 62,66 ---- rm -f active.old ln active active.old ! mv active.tmp active exit 0 *** cnpatch/old/expire/updatemin.c Thu Sep 14 16:03:33 1989 --- expire/updatemin.c Wed Dec 20 16:04:50 1989 *************** *** 24,28 **** long lowest(); ! char newname[] = "active.new"; char *progname; --- 24,28 ---- long lowest(); ! char newname[] = "active.tmp"; char *progname; *** cnpatch/old/hfake/Makefile Tue Jun 20 18:58:03 1989 --- hfake/Makefile Wed Jan 10 17:12:27 1990 *************** *** 2,6 **** # beware -- build knows about NEEDED ! NEEDED = ../include/stdlib.h all: $(NEEDED) --- 2,6 ---- # beware -- build knows about NEEDED ! NEEDED = ../include/stdlib.h ../include/string.h all: $(NEEDED) *** cnpatch/old/input/Makefile Thu Aug 24 16:39:52 1989 --- input/Makefile Sat Dec 30 02:14:57 1989 *************** *** 41,44 **** --- 41,50 ---- ls -lg $(NEWSBIN)/input/newsspool | egrep -s '^-rwsrwsr-x 1 news news' + check: $(THEM) + for f in $(THEM) ; do cmp $(NEWSBIN)/input/$$f $$f || true ; done + cmp rnews $(RBIN)/rnews || true + cmp rnews $(RBIN)/cunbatch || true + ls -lg $(NEWSBIN)/input/newsspool | egrep -s '^-rwsrwsr-x 1 news news' + newsinstall: : nothing *** cnpatch/old/input/newsrun Tue Aug 22 14:47:46 1989 --- input/newsrun Wed Nov 15 15:14:08 1989 *************** *** 116,120 **** else # N.B.: rsh always returns exit status 0! ! rsh $server "PATH=$PATH relaynews -r -n" <$text fi st=$? --- 116,120 ---- else # N.B.: rsh always returns exit status 0! ! rsh $server /bin/sh -c "PATH=$PATH relaynews -r -n" <$text fi st=$? *** cnpatch/old/libc/warning.c Tue Jun 20 18:58:41 1989 --- libc/warning.c Sat Dec 30 01:46:05 1989 *************** *** 11,14 **** --- 11,15 ---- { char *cmdname; + int saverrno; extern int errno, sys_nerr; extern char *sys_errlist[]; *************** *** 16,19 **** --- 17,21 ---- extern char *getenv(); + saverrno = errno; /* so isatty(3) won't clobber it */ (void) fflush(stdout); /* hack */ cmdname = getenv("CMDNAME"); *************** *** 23,28 **** fprintf(stderr, "%s: ", progname); fprintf(stderr, s1, s2); ! if (errno > 0 && errno < sys_nerr) ! fprintf(stderr, " (%s)", sys_errlist[errno]); fprintf(stderr, "\n"); errno = 0; --- 25,30 ---- fprintf(stderr, "%s: ", progname); fprintf(stderr, s1, s2); ! if (saverrno > 0 && saverrno < sys_nerr) ! fprintf(stderr, " (%s)", sys_errlist[saverrno]); fprintf(stderr, "\n"); errno = 0; *** cnpatch/old/libfake/Makefile Thu Aug 24 16:39:55 1989 --- libfake/Makefile Wed Jan 10 17:15:59 1990 *************** *** 7,11 **** ALL = dbm.o fsync.o getopt.o ldiv.o memchr.o memcmp.o memcpy.o \ memset.o mkdir.o putenv.o strchr.o strcspn.o strpbrk.o strrchr.o \ ! strspn.o strtok.o symlink.o # beware -- build knows about NEEDED --- 7,11 ---- ALL = dbm.o fsync.o getopt.o ldiv.o memchr.o memcmp.o memcpy.o \ memset.o mkdir.o putenv.o strchr.o strcspn.o strpbrk.o strrchr.o \ ! strspn.o strtok.o symlink.o dbmclose.o # beware -- build knows about NEEDED *** cnpatch/old/man/expire.8 Thu Sep 14 16:03:40 1989 --- man/expire.8 Wed Jan 3 14:01:37 1990 *************** *** 7,11 **** .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH EXPIRE 8 "13 Sept 1989" "C News" .SH NAME expire, doexpire \- expire old news --- 7,11 ---- .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH EXPIRE 8 "3 Jan 1990" "C News" .SH NAME expire, doexpire \- expire old news *************** *** 16,21 **** .br recovact \- partially recover news active file - .br - superkludge \- implement stupid Supersedes header in news .SH SYNOPSIS .B \*b/expire/expire --- 16,19 ---- *************** *** 45,48 **** --- 43,48 ---- ] [ .B \-r + ] [ + .B \-g ] [ controlfile ] *************** *** 56,65 **** .br .B \*b/expire/recovact - .br - .B \*b/expire/superkludge - [ - .B \-v - ] - newsgroup ... .SH DESCRIPTION .I Expire --- 56,59 ---- *************** *** 182,185 **** --- 176,188 ---- print (on standard error) a shell-script-like description of what would be done, but don't do it. + In the absence of archiving, all output lines will be of the form + ``\fBremove\fR\ \fIname\fR'', where \fIname\fR is a pathname relative + to \fI\*a\fR. + If an article is to be archived, this will be preceded (on the same + line) by ``\fBcopy\fR\ \fIname\fR\ \fIdir\fR\ \fB;\fR\ '', where \fIname\fR + is as in \fBremove\fR and \fIdir\fR is an archiving directory + (including any `=' prefix) + as specified by the control file + or the \fB\-a\fR option. .TP .BR \-l *************** *** 199,202 **** --- 202,211 ---- report some statistics after termination. .TP + .BR \-g + report expiry dates that \fIgetdate\fR(3) does not like. + .I Expire + ignores such dates, treating the article as if it had no explicit + expiry date. + .TP .BR \-d turn on (voluminous and cryptic) debugging output. *************** *** 236,247 **** These programs are all fairly slow and they all lock the whole news system for the duration of the run, so they should not be run casually. - .PP - .I Superkludge - inspects the files in \fI\*a\fR for the \fInewsgroup\fR(s) - given, and removes any that have been superseded, according to the - `Supersedes' header, by newer ones. - The \fIhistory\fR file is not altered; it's not worth the trouble. - The \fB\-v\fR option produces a report of how many articles have been - superseded in each \fInewsgroup\fR. .SH FILES .ta 6c --- 245,248 ---- *************** *** 270,282 **** although such lines are rare. .PP ! \fIUpact\fR and \fIsuperkludge\fR are distasteful kludges, ! but then, so are the third field of the \fIactive\fR file and the ! `Supersedes' header. .PP - .I Superkludge - does not understand RFC822's complex case-sensitivity rules for message-IDs, - and insists on an exact case-sensitive match. - .PP One cannot put more than one newsgroup into a single archiving directory with the `=' feature, since the article numbers will collide with each other and expire doesn't do anything about this. --- 271,284 ---- although such lines are rare. .PP ! \fIUpact\fR is a distasteful kludge, ! but then, so is the third field of the \fIactive\fR file. .PP One cannot put more than one newsgroup into a single archiving directory with the `=' feature, since the article numbers will collide with each other and expire doesn't do anything about this. + .PP + .I Mkhistory + is inherently incapable of reconstructing history-file lines corresponding + to expired articles. + Protection against old articles reappearing is thus somewhat limited for + a while after the history file is rebuilt. *** cnpatch/old/man/newsaux.8 Mon Nov 13 17:39:47 1989 --- man/newsaux.8 Sun Dec 31 01:34:07 1989 *************** *** 7,11 **** .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH NEWSAUX 8 "15 Sept 1989" "C News" .SH NAME spacefor \- check available space for news --- 7,11 ---- .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH NEWSAUX 8 "30 Dec 1989" "C News" .SH NAME spacefor \- check available space for news *************** *** 263,264 **** --- 263,268 ---- \fIDelgroup\fR does not remove files or directories from \*a, although it prints a reminder to do so. + .PP + Various nuisances can result if the maintenance utilities are run as + \fIroot\fR rather than as the owner of the news database. + It's difficult to defend against this. *** cnpatch/old/man/relaynews.8 Fri Jul 7 15:40:08 1989 --- man/relaynews.8 Wed Jan 3 14:07:31 1990 *************** *** 7,11 **** .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH RELAYNEWS 8 "4 July 1989" "C News" .SH NAME relaynews \- store and forward netnews articles --- 7,11 ---- .\" =()<.ds m @<NEWSMASTER>@>()= .ds m usenet ! .TH RELAYNEWS 8 "2 January 1990" "C News" .SH NAME relaynews \- store and forward netnews articles *************** *** 98,101 **** --- 98,120 ---- is not a real newsgroup. .PP + An article which contains an + .B Also-Control: + header is treated normally + except that the contents of the header + are executed as if they were the contents of a + .B Control: + header. + Such an article is a form of + .I "hybrid message" + since it functions as an ordinary article + yet also causes control functions to be executed. + The + .B Supersedes: + header is a special case + and is rewritten internally + .I only + to + .BR "Also-Control: cancel" . + .PP Articles which contain no locally-known (to the *************** *** 222,228 **** (e.g. something like Eunice but on a PDP-11) will be filed incorrectly: ! any symbolic links under \*a will point at a non-existent ! filename. ! .br A control message which cannot be filed in the .B control --- 241,248 ---- (e.g. something like Eunice but on a PDP-11) will be filed incorrectly: ! any symbolic links under ! .B \*a ! will point at a non-existent filename. ! .PP A control message which cannot be filed in the .B control *************** *** 241,245 **** .B control pseudo-group. ! .br .I Relaynews could run faster in some circumstances --- 261,265 ---- .B control pseudo-group. ! .PP .I Relaynews could run faster in some circumstances *************** *** 246,253 **** and would be simpler if ! .I Control: were required to be the first header, if present, and if ! .I Newsgroups: were required to be the next. --- 266,285 ---- and would be simpler if ! .B Control: were required to be the first header, if present, and if ! .B Newsgroups: were required to be the next. + .PP + The whole control message and hybrid message situation + is a festering bug. + Either control messages should be eliminated, + or all forms of backward compatibility should be dropped + (including + .B Control: + and + .BR Supersedes: ) + and only + .B Also-Control: + should be supported. *** cnpatch/old/misc/Makefile Thu Sep 14 16:03:43 1989 --- misc/Makefile Sat Dec 30 02:17:11 1989 *************** *** 31,34 **** --- 31,38 ---- for f in $(UTILS) ; do cmp $(NEWSBIN)/$$f $$f ; done + check: $(THEM) + for f in $(MAINT) ; do cmp $(NEWSBIN)/maint/$$f $$f || true ; done + for f in $(UTILS) ; do cmp $(NEWSBIN)/$$f $$f || true ; done + newsinstall: : nothing *************** *** 50,54 **** NHCFLAGS = -I$(RN) $(CFLAGS) ! RNEWSOBJS = $(RN)/history.o $(RN)/article.o $(RN)/hdrcommon.o \ $(RN)/io.o $(RN)/msgs.o NHLIBS = $(LIBS) $(DBM) --- 54,58 ---- NHCFLAGS = -I$(RN) $(CFLAGS) ! RNEWSOBJS = $(RN)/history.o $(RN)/article.o $(RN)/hdrdefs.o \ $(RN)/io.o $(RN)/msgs.o NHLIBS = $(LIBS) $(DBM) *** cnpatch/old/misc/newsdaily Mon Nov 13 17:39:49 1989 --- misc/newsdaily Tue Dec 19 18:52:41 1989 *************** *** 116,119 **** --- 116,129 ---- ) >>$gripes fi + egrep '`' log.o | egrep 'no subscribed' | sed 's/.*`\(.*\)'"'"'.*/\1/' | sort | + uniq -c | sort -nr | sed 5q >$tmp + if test -s $tmp + then + ( + echo 'leading five unsubscribed newsgroups:' + cat $tmp + echo + ) >>$gripes + fi # and send it *** cnpatch/old/misc/newshist.c Tue Jun 20 19:00:05 1989 --- misc/newshist.c Mon Nov 27 19:45:35 1989 *************** *** 11,15 **** static char *histfile; /* unused */ int remote; /* to satisfy rnews code */ - int headdebug = 0; /* no debugging */ /* --- 11,14 ---- *** cnpatch/old/notebook/bdiffs Tue Jun 20 18:56:13 1989 --- notebook/bdiffs Tue Jan 2 19:03:00 1990 *************** *** 39,43 **** .I rnews by linking to the name ! .I /usr/lib/news/LOCK and repeating until successful; there is no time-out --- 39,43 ---- .I rnews by linking to the name ! .B /usr/lib/news/LOCK and repeating until successful; there is no time-out *************** *** 157,163 **** (e.g. .B usenet ). ! The superfluous .I Supersedes: ! header is not honoured. .PP .I "Newsgroup aliases." --- 157,167 ---- (e.g. .B usenet ). ! C news ! adds an ! .I Also-Control: ! header, ! of which .I Supersedes: ! is a special case. .PP .I "Newsgroup aliases." *** cnpatch/old/notebook/ctlmsg Tue Jun 20 18:56:24 1989 --- notebook/ctlmsg Tue Jan 2 19:03:31 1990 *************** *** 62,66 **** .I relaynews by executing the command following ! .B Control: , with a search path of .I $NEWSCTL/bin:$NEWSBIN/ctl --- 62,66 ---- .I relaynews by executing the command following ! .B Control: with a search path of .I $NEWSCTL/bin:$NEWSBIN/ctl *************** *** 68,71 **** --- 68,73 ---- the control message article. The command inherits + the standard news search path + and .I relaynews 's user and group ids, *** cnpatch/old/notebook/log Sun Jul 23 00:48:12 1989 --- notebook/log Sun Dec 31 01:30:54 1989 *************** *** 85,86 **** --- 85,92 ---- s generated in response to a \fIsendme\fR control message list of sites to which this article was relayed .TE + .PP + Beware that control-message handlers inherit + .I relaynew 's + standard output, so if any of them natters on standard output + (we believe none of ours does), the nattering will appear in + .B log . *** cnpatch/old/notebook/rfcerrata Mon Nov 13 17:39:49 1989 --- notebook/rfcerrata Tue Jan 2 19:04:10 1990 *************** *** 77,81 **** B 2.11 interprets absence of the target article as ``unable to cancel''. It would improve the efficacy and reliability of ! .IR cancel s to propagate them anyway, given that feed anomalies are widespread. There have been verified instances in which cancellations did not achieve --- 77,81 ---- B 2.11 interprets absence of the target article as ``unable to cancel''. It would improve the efficacy and reliability of ! \fIcancel\fRs to propagate them anyway, given that feed anomalies are widespread. There have been verified instances in which cancellations did not achieve *************** *** 84,88 **** C News interprets absence of the target article as deferred cancellation rather than failure to cancel, and propagates the ! .IR cancel . .SH ihave/sendme not documented --- 84,88 ---- C News interprets absence of the target article as deferred cancellation rather than failure to cancel, and propagates the ! \fIcancel\fR. .SH ihave/sendme not documented *************** *** 105,109 **** .I remotesys . .SH ! case-sensitivity in message-ids .PP RFC 1036 says nothing about whether message-ids are case-sensitive or not, --- 105,109 ---- .I remotesys . .SH ! Case-sensitivity in message-ids .PP RFC 1036 says nothing about whether message-ids are case-sensitive or not, *************** *** 118,119 **** --- 118,129 ---- matters appear to be extremely rare.) Simplification appears necessary. + .SH + New headers + .PP + The B news + .B Supersedes: + header needs to be documented in the next revision of the RFC, + as does the C news generalisation, + .B Also-Control: + (see + .I relaynews (8)). *** cnpatch/old/relay/control.c Thu Aug 24 16:39:59 1989 --- relay/control.c Mon Nov 27 19:47:53 1989 *************** *** 22,26 **** --- 22,28 ---- #include "libc.h" #include "news.h" + #include "case.h" #include "config.h" + #include "control.h" #include "headers.h" #include "article.h" *************** *** 30,33 **** --- 32,39 ---- #define NO_FILES "" #define SUBDIR binfile("ctl") /* holds shell scripts */ + #ifdef SLOWCTLMATCH + #define OLDCNTRL "all.all.ctl" + #endif + #define SFXOLDCNTRL ".ctl" /* *************** *** 58,66 **** void ctlmsg(art) ! struct article *art; { int pid, deadpid; int wstatus; - char *inname = art->a_tmpf, *ctlcmd = art->h.h_ctlcmd; static char nmcancel[] = "cancel "; static char nmihave[] = "ihave "; --- 64,72 ---- void ctlmsg(art) ! register struct article *art; { + register char *inname = art->a_tmpf, *ctlcmd = art->h.h_ctlcmd; int pid, deadpid; int wstatus; static char nmcancel[] = "cancel "; static char nmihave[] = "ihave "; *************** *** 67,70 **** --- 73,80 ---- static char nmsendme[] = "sendme "; + if (ctlcmd == NULL) + ctlcmd = art->h.h_etctlcmd; + if (ctlcmd == NULL) + return; if (STREQN(ctlcmd, nmcancel, STRLEN(nmcancel))) { art->a_status |= cancelart(ctlcmd + STRLEN(nmcancel)); *************** *** 102,106 **** STATIC boolean safecmd(cmd) /* true if it's safe to system(3) cmd */ ! char *cmd; { register char *s; --- 112,116 ---- STATIC boolean safecmd(cmd) /* true if it's safe to system(3) cmd */ ! register char *cmd; { register char *s; *************** *** 245,247 **** --- 255,300 ---- free(mailcmd); _exit(1); + } + + STATIC boolean + oldctl(hdrs) /* true iff ngs match OLDCNTRL */ + register struct headers *hdrs; + { + #ifdef SLOWCTLMATCH + return ngmatch(OLDCNTRL, hdrs->h_ngs); + #else + register int ngslen = strlen(hdrs->h_ngs); + + if (ngslen < STRLEN(SFXOLDCNTRL)) /* ngs too short */ + return NO; + else /* check for .ctl suffix */ + /* + * This is more general than RFC 850 specifies, but this + * generality seems harmless. This doesn't work for e.g. + * x.y.ctl,z.q, which is a darn shame, but that's a violation + * of common sense. + */ + return STREQ(&hdrs->h_ngs[ngslen-STRLEN(SFXOLDCNTRL)], + SFXOLDCNTRL); + #endif /* SLOWCTLMATCH */ + } + + hackoldctl(hdrs) /* Handle the all.all.ctl hack. */ + register struct headers *hdrs; + { + if (hdrs->h_ctlcmd == NULL && oldctl(hdrs)) + hdrs->h_ctlcmd = strsave(hdrs->h_subj); + } + + char * + hackhybrid(line) + register char *line; + { + static char stupersedes[] = "Supersedes:"; + static char alsocan[] = "Also-Control: cancel "; + + if (CISTREQN(line, stupersedes, STRLEN(stupersedes))) + return str3save(alsocan, "", &line[STRLEN(stupersedes)]); + else + return strsave(line); } *** cnpatch/old/relay/control.h Tue Jun 20 19:01:03 1989 --- relay/control.h Mon Nov 27 19:47:53 1989 *************** *** 1,2 **** --- 1,5 ---- /* imports from control.c */ extern void ctlmsg(); + extern char *hackhybrid(); + + #define CONTROL "control" /* control message pseudo-ng. */ *** cnpatch/old/relay/fileart.c Thu Aug 24 16:39:59 1989 --- relay/fileart.c Mon Nov 27 19:47:53 1989 *************** *** 25,29 **** --- 25,31 ---- #include "news.h" #include "config.h" + #include "control.h" #include "active.h" + #include "fileart.h" #include "mkdirs.h" #include "headers.h" *************** *** 32,38 **** #include "system.h" - #define JUNK "junk" /* lost+found pseudo-ng. */ - #define CONTROL "control" /* control message pseudo-ng. */ - static long artnum; /* asgnartnum sets artnum */ static int goodngs; /* asgnartnum reads goodngs */ --- 34,37 ---- *************** *** 98,102 **** register char *comma; ! ngs = (art->h.h_ctlcmd != NULL? CONTROL: art->h.h_ngs); if (art->a_status&ST_REFUSED) (void) fprintf(stderr, --- 97,101 ---- register char *comma; ! ngs = (art->h.h_ctlcmd != NULL? CONTROL: art->h.h_ngs); /* NCMP */ if (art->a_status&ST_REFUSED) (void) fprintf(stderr, *** cnpatch/old/relay/fileart.h Tue Jun 20 19:01:12 1989 --- relay/fileart.h Mon Nov 27 19:47:53 1989 *************** *** 2,3 **** --- 2,5 ---- extern void filedebug(); extern void fileart(); + + #define JUNK "junk" /* lost+found pseudo-ng. */ *** cnpatch/old/relay/hdrdefs.c Tue Jun 20 19:01:16 1989 --- relay/hdrdefs.c Mon Nov 27 19:47:53 1989 *************** *** 13,16 **** --- 13,17 ---- #include <stdlib.h> #endif /* REALSTDC */ + #include "libc.h" #include "news.h" #include "headers.h" *************** *** 29,33 **** /* optional headers */ static const char appnm[] = "Approved:"; /* for mod. groups */ ! static const char ctlnm[] = "Control:"; /* ctl. msg. */ static const char expnm[] = "Expires:"; /* for history */ static const char distrnm[] = "Distribution:"; /* for transmission */ --- 30,35 ---- /* optional headers */ static const char appnm[] = "Approved:"; /* for mod. groups */ ! static const char ctlnm[] = "Control:"; /* ctl. msg.; NCMP */ ! static const char etctlnm[] = "Also-Control:"; /* hybrid ctl. msg.; NCMP */ static const char expnm[] = "Expires:"; /* for history */ static const char distrnm[] = "Distribution:"; /* for transmission */ *************** *** 57,62 **** static const struct hdrdef apphdr = { appnm, STRLEN(appnm), offsetof(struct headers, h_approved) }; ! static const struct hdrdef ctlhdr = { ! ctlnm, STRLEN(ctlnm), offsetof(struct headers, h_ctlcmd) }; static const struct hdrdef exphdr = { expnm, STRLEN(expnm), offsetof(struct headers, h_expiry) }; --- 59,66 ---- static const struct hdrdef apphdr = { appnm, STRLEN(appnm), offsetof(struct headers, h_approved) }; ! static const struct hdrdef ctlhdr = { /* NCMP */ ! ctlnm, STRLEN(ctlnm), offsetof(struct headers, h_ctlcmd) }; /* NCMP */ ! static const struct hdrdef etctlhdr = { /* NCMP */ ! etctlnm, STRLEN(etctlnm), offsetof(struct headers, h_etctlcmd) }; /* NCMP */ static const struct hdrdef exphdr = { expnm, STRLEN(expnm), offsetof(struct headers, h_expiry) }; *************** *** 85,89 **** /* start optional headers */ &apphdr, ! &ctlhdr, &distrhdr, &exphdr, --- 89,94 ---- /* start optional headers */ &apphdr, ! &ctlhdr, /* NCMP */ ! &etctlhdr, /* NCMP */ &distrhdr, &exphdr, *************** *** 109,110 **** --- 114,156 ---- boolean headdebug = NO; + + void + hdrdebug(state) + int state; + { + headdebug = state; + } + + void + hdrinit(hdrs) /* zero all elements of hdrs */ + register struct headers *hdrs; + { + hdrs->h_subj = NULL; + hdrs->h_ngs = NULL; + hdrs->h_distr = NULL; + hdrs->h_ctlcmd = NULL; /* NCMP */ + hdrs->h_etctlcmd = NULL; /* NCMP */ + hdrs->h_approved = NULL; + hdrs->h_msgid = NULL; + hdrs->h_artid = NULL; + hdrs->h_expiry = NULL; + hdrs->h_path = NULL; + hdrs->h_sender = NULL; + } + + void + freeheaders(hdrs) /* free (assumed) malloced storage */ + register struct headers *hdrs; + { + nnfree(&hdrs->h_subj); + nnfree(&hdrs->h_ngs); + nnfree(&hdrs->h_distr); + nnfree(&hdrs->h_ctlcmd); /* NCMP */ + nnfree(&hdrs->h_etctlcmd); /* NCMP */ + nnfree(&hdrs->h_approved); + nnfree(&hdrs->h_msgid); + nnfree(&hdrs->h_artid); + nnfree(&hdrs->h_expiry); + nnfree(&hdrs->h_path); + nnfree(&hdrs->h_sender); + } *** cnpatch/old/relay/hdrint.h Thu Aug 24 16:39:59 1989 --- relay/hdrint.h Mon Nov 27 19:47:53 1989 *************** *** 22,33 **** #define DEFMSGID "" /* must be empty string or contain whitespace */ - #define JUNK "junk" - #define ALL "all" - - #ifdef SLOWCTLMATCH - #define OLDCNTRL "all.all.ctl" - #endif - #define SFXOLDCNTRL ".ctl" - struct hdrdef { const char *hdrnm; /* ascii name */ --- 22,25 ---- *** cnpatch/old/relay/hdrparse.c Mon Nov 13 17:39:50 1989 --- relay/hdrparse.c Mon Nov 27 19:47:53 1989 *************** *** 7,11 **** --- 7,13 ---- #include "libc.h" #include "news.h" + #include "control.h" #include "case.h" + #include "fileart.h" #include "headers.h" #include "hdrint.h" *************** *** 12,25 **** /* - * Reset internal state of header parser. - * (Empty the stomach of partially-digested headers.) - */ - void - hdrwretch() - { - /* historical stub */ - } - - /* * Parse (assumed) RFC822/850/1036 header in "line" (ishdr(line) can * verify this) into "hdrs" using hdrlst set of keywords by retaining the --- 14,17 ---- *************** *** 32,39 **** hdrparse(hdrs, line, hdrlst) register struct headers *hdrs; ! register char *line; hdrlist hdrlst; /* headers of positive utility */ { register struct hdrdef **hpp; for (hpp = hdrlst; *hpp != NULL; hpp++) { --- 24,32 ---- hdrparse(hdrs, line, hdrlst) register struct headers *hdrs; ! char *line; hdrlist hdrlst; /* headers of positive utility */ { register struct hdrdef **hpp; + register char *hackline = hackhybrid(line); for (hpp = hdrlst; *hpp != NULL; hpp++) { *************** *** 40,44 **** register char *hdrnm = (*hpp)->hdrnm; ! if (CISTREQN(line, hdrnm, (int)(*hpp)->hdrlen) && (*hpp)->hdroff >= 0) /* paranoia */ break; --- 33,37 ---- register char *hdrnm = (*hpp)->hdrnm; ! if (CISTREQN(hackline, hdrnm, (int)(*hpp)->hdrlen) && (*hpp)->hdroff >= 0) /* paranoia */ break; *************** *** 48,55 **** nnfree(ptrp); /* free prev. value in this article */ ! *ptrp = strsave(skipsp(&line[(*hpp)->hdrlen])); if (*ptrp != NULL) trim(*ptrp); /* cut trailing \n */ } } --- 41,49 ---- nnfree(ptrp); /* free prev. value in this article */ ! *ptrp = strsave(skipsp(&hackline[(*hpp)->hdrlen])); if (*ptrp != NULL) trim(*ptrp); /* cut trailing \n */ } + free(hackline); } *************** *** 90,94 **** if (hdrs->h_subj == NULL) hdrs->h_subj = strsave(""); ! if (hdrs->h_ctlcmd == NULL && oldctl(hdrs)) ! hdrs->h_ctlcmd = strsave(hdrs->h_subj); } --- 84,87 ---- if (hdrs->h_subj == NULL) hdrs->h_subj = strsave(""); ! hackoldctl(hdrs); /* NCMP */ } *** cnpatch/old/relay/headers.h Tue Jun 20 19:01:19 1989 --- relay/headers.h Mon Nov 27 19:47:54 1989 *************** *** 19,23 **** char *h_ngs; /* newsgroups: used in filing, sys matching & all.all.ctl matching */ char *h_distr; /* distribution for transmit */ ! char *h_ctlcmd; /* control command */ char *h_approved; /* needed for acceptance in moderated groups */ char *h_msgid; /* needed for history & rejection */ --- 19,24 ---- char *h_ngs; /* newsgroups: used in filing, sys matching & all.all.ctl matching */ char *h_distr; /* distribution for transmit */ ! char *h_ctlcmd; /* control command (NCMP) */ ! char *h_etctlcmd; /* also-control command (NCMP) */ char *h_approved; /* needed for acceptance in moderated groups */ char *h_msgid; /* needed for history & rejection */ *************** *** 36,39 **** /* parse */ ! extern void hdrwretch(), hdrparse(), hdrdeflt(); extern boolean ishdr(), contin(); --- 37,40 ---- /* parse */ ! extern void hdrparse(), hdrdeflt(); extern boolean ishdr(), contin(); *** cnpatch/old/relay/makefile Mon Nov 13 17:39:53 1989 --- relay/makefile Sat Dec 30 02:20:17 1989 *************** *** 33,41 **** LIBOBJS=../libcnews.a SRC=relaynews.c active.c article.c caches.c mkdirs.c control.c fileart.c \ ! hdrdefs.c hdrcommon.c hdrparse.c hdrmunge.c \ history.c io.c msgs.c procart.c \ sys.c transmit.c trbatch.c ihave.c $(LIBSRCS) OBJ=relaynews.o active.o article.o caches.o mkdirs.o control.o fileart.o \ ! hdrdefs.o hdrcommon.o hdrparse.o hdrmunge.o \ history.o io.o msgs.o procart.o \ sys.o transmit.o trbatch.o ihave.o --- 33,41 ---- LIBOBJS=../libcnews.a SRC=relaynews.c active.c article.c caches.c mkdirs.c control.c fileart.c \ ! hdrdefs.c hdrparse.c hdrmunge.c \ history.c io.c msgs.c procart.c \ sys.c transmit.c trbatch.c ihave.c $(LIBSRCS) OBJ=relaynews.o active.o article.o caches.o mkdirs.o control.o fileart.o \ ! hdrdefs.o hdrparse.o hdrmunge.o \ history.o io.o msgs.o procart.o \ sys.o transmit.o trbatch.o ihave.o *************** *** 80,84 **** cmp: relaynews cmp $(NEWSBIN)/relay/relaynews relaynews - ls -lg $(NEWSBIN)/relay/relaynews | egrep -s '^-rwsrwsr-x 1 news news' for f in `ls sh` ; do cmp $(NEWSBIN)/inject/$$f sh/$$f ; done for f in `ls ctl` ; do cmp $(NEWSBIN)/ctl/$$f ctl/$$f ; done --- 80,83 ---- *************** *** 85,89 **** --- 84,97 ---- for f in `ls aux` ; do cmp $(NEWSBIN)/relay/$$f aux/$$f ; done cmp $(BIN)/inews sh/inews + ls -lg $(NEWSBIN)/relay/relaynews | egrep -s '^-rwsrwsr-x 1 news news' + check: relaynews + cmp $(NEWSBIN)/relay/relaynews relaynews || true + for f in `ls sh` ; do cmp $(NEWSBIN)/inject/$$f sh/$$f || true ; done + for f in `ls ctl` ; do cmp $(NEWSBIN)/ctl/$$f ctl/$$f || true ; done + for f in `ls aux` ; do cmp $(NEWSBIN)/relay/$$f aux/$$f || true ; done + cmp $(BIN)/inews sh/inews || true + ls -lg $(NEWSBIN)/relay/relaynews | egrep -s '^-rwsrwsr-x 1 news news' + TODO.grep: TODO -egrep TODO ../include/*.h *.h *.c sh/* | tr -s " \11" " " >$@ *************** *** 124,128 **** fileart.o: ../include/libc.h ../include/news.h ../include/config.h fileart.o: active.h mkdirs.h headers.h article.h history.h system.h - hdrcommon.o: ../include/news.h headers.h hdrint.h hdrdefs.o: ../include/news.h headers.h hdrint.h hdrmunge.o: ../include/libc.h ../include/news.h fileart.h headers.h --- 132,135 ---- *** cnpatch/old/relay/procart.c Mon Nov 13 17:39:53 1989 --- relay/procart.c Mon Nov 27 19:47:54 1989 *************** *** 136,144 **** { register char *hdr = NULL; ! long limit; int is_hdr = NO; - hdrwretch(); /* reset the header parser */ - limit = (art->a_blvmax? art->a_unread+1: art->a_unread); /* 1 for NUL */ /* 1 is again for NUL */ while (limit > 1 && (hdr = gethdr(in, &limit, &is_hdr)) != NULL && is_hdr) { --- 136,142 ---- { register char *hdr = NULL; ! long limit = (art->a_blvmax? art->a_unread+1: art->a_unread); /* 1 for NUL */ int is_hdr = NO; /* 1 is again for NUL */ while (limit > 1 && (hdr = gethdr(in, &limit, &is_hdr)) != NULL && is_hdr) { *************** *** 274,279 **** transmit(art, exclude); /* writes systems on stdout */ (void) putchar('\n'); /* ends the log line */ ! if (art->h.h_ctlcmd != NULL) ! ctlmsg(art); #ifdef notdef /* it's only a log file! */ (void) fflush(stdout); /* crash-proofness */ --- 272,276 ---- transmit(art, exclude); /* writes systems on stdout */ (void) putchar('\n'); /* ends the log line */ ! ctlmsg(art); #ifdef notdef /* it's only a log file! */ (void) fflush(stdout); /* crash-proofness */ *** cnpatch/old/relay/transmit.c Thu Aug 24 16:40:07 1989 --- relay/transmit.c Tue Dec 19 16:07:22 1989 *************** *** 178,182 **** STRLEN(":") + strlen(bincmd) + STRLEN(":") + strlen(newspath()) + STRLEN(";<") + strlen(filename) + STRLEN(" (") + ! strlen(syscmd) + strlen(filename) + STRLEN(")") + 1)); (void) strcpy(cmd, "PATH="); (void) strcat(cmd, ctlcmd); --- 178,182 ---- STRLEN(":") + strlen(bincmd) + STRLEN(":") + strlen(newspath()) + STRLEN(";<") + strlen(filename) + STRLEN(" (") + ! strlen(syscmd) + strlen(filename) + STRLEN(")") + SIZENUL)); (void) strcpy(cmd, "PATH="); (void) strcat(cmd, ctlcmd); *************** *** 199,207 **** art->a_status |= ST_DROPPED; (void) fprintf(stderr, "%s: `%s' contains two %%'s\n", ! progname, cmd); } else if (*percent != 's' && *percent != '%') { art->a_status |= ST_DROPPED; (void) fprintf(stderr, "%s: `%s' contains %%%c, not %%s\n", ! progname, cmd, *percent); } else (void) sprintf(cmd+strlen(cmd), syscmd, filename); --- 199,207 ---- art->a_status |= ST_DROPPED; (void) fprintf(stderr, "%s: `%s' contains two %%'s\n", ! progname, syscmd); } else if (*percent != 's' && *percent != '%') { art->a_status |= ST_DROPPED; (void) fprintf(stderr, "%s: `%s' contains %%%c, not %%s\n", ! progname, syscmd, *percent); } else (void) sprintf(cmd+strlen(cmd), syscmd, filename); *************** *** 211,216 **** if (exitstat != 0) { art->a_status |= ST_DROPPED; ! (void) fprintf(stderr, "%s: `%s' returned exit status 0%o\n", ! progname, cmd, exitstat); } free(cmd); --- 211,217 ---- if (exitstat != 0) { art->a_status |= ST_DROPPED; ! (void) fprintf(stderr, "%s: `", progname); ! (void) fputs(cmd, stderr); ! (void) fprintf(stderr, "' returned exit status 0%o\n", exitstat); } free(cmd); Files that are new: new libfake/dbmclose.c (patch can't create, so diff against null): Index: libfake/dbmclose.c *** cnpatch/old/libfake/dbmclose.c Wed Jan 10 18:03:50 1990 --- libfake/dbmclose.c Tue Nov 28 19:20:22 1989 *************** *** 0 **** --- 1 ---- + dbmclose(){} new notebook/problems (patch can't create, so diff against null): Index: notebook/problems *** cnpatch/old/notebook/problems Wed Jan 10 18:03:51 1990 --- notebook/problems Wed Jan 10 17:54:42 1990 *************** *** 0 **** --- 1,145 ---- + .DA "31 Dec 1989" + .TL + Known Porting Problems With C News + .AU + Henry Spencer + .AI + Dept. of Zoology + University of Toronto + .SH + Intro + .PP + C News in general is pretty portable. + People have got it to run on a very wide range of systems with little + trouble. + Difficulties are usually problems in the system, not C News. + Some of them, however, are widespread enough to be worth comment, for + the guidance of people having problems. + If you run into a novel problem, + we are always interested in hearing about such things. + .SH + Unix Dependencies + .PP + The biggest portability glitch in C News is that it depends a lot on Unix + utilities. + The extensive use of complex shell files, \fIsed\fR and \fIawk\fR programs, + and a wide range of lesser Unix utilities would make it quite difficult + to move C News to a system that is seriously non-Unix-like. + The actual C programs seldom depend on Unix in major ways. + (An exception is the use + of \fIread\fR system calls in \fIexpire\fR, to avoid difficulties with + stdio end-of-file behavior; + we now know how to avoid this but haven't implemented the fixes yet.) + .PP + We know that \fIawk\fR and the colon (:) operator of \fIexpr\fR are + problem areas under Minix. + .SH + Shell Problems + .PP + C News seriously stress-tests shells. + The current Minix shell is not robust enough + in the face of complex inputs, botches some constructs entirely, + and can run out of memory on the complex shell files. + Any shell that is too old to implement comments begun + by ``#'' is big trouble, since we use such comments everywhere. + .PP + Any system/shell combination that thinks that a shell script starting + with ``#!\ /bin/sh'' should be run by the C Shell (because it starts + with `#') is also big trouble: + you will have to change that line to ``:\ use\ /bin/sh'' everywhere. + We know that at least some releases of Xenix have this problem. + It is not necessary that your kernel understand the ``#!'' feature\(emwe + believe that nothing in C News relies on it\(embut it is essential that + it not cause invocation of the C Shell. + .PP + We know that some Hewlett-Packard Unixes have broken shells, probably + the result of mistakes in + HP's efforts to make + the shell 8-bit-clean; the symptom is + that something like: + .DS + x=y + if test " $x" != " y" + then + echo oops + fi + .DE + prints ``oops''. + This is, again, big trouble, because we do that a lot. + .PP + Many people using 3B1s, aka UNIX PCs, + run the Korn shell as their \fI/bin/sh\fR. + Some other folks may do this too. + Beware that \fIksh\fR was not fully \fIsh\fR-compatible for a + long time, with some subtle differences in the + ill-documented behavior of backquotes and backslashes. + Some of the C News shell scripts, + notably \fIinews\fR, + are known to hit these bugs. + We are \fItold\fR that current \fIksh\fRs have fixed them. + .SH + Make vs. Test + .PP + There is a persistent problem on 3B2s with implementations of \fImake\fR + that violate the SVID in a subtle way. + They attempt to execute makefile commands directly, rather than via the + shell, if the commands do not contain metacharacters. + This means that if\(emas on many 3B2s\(em\fItest\fR is a shell builtin + \fIand there is no /bin/test program\fR, the makefile line + ``test\ \-s\ file'' will cause \fImake\fR to complain about an unknown + command. + (The SVID says that makefile commands must be executed as if by + the shell, and the shell will execute this line correctly.) + We've added `;' on the ends of such lines, which suffices to convince + \fImake\fR to run a shell on the systems we've encountered, but AT&T + is good at finding ways to break such workarounds. + This problem is also known to occur in A/UX. + .SH + Offsetof + .PP + ANSI C requires C compilers to supply a macro \fIoffsetof\fR, which can + be used to find the offset of a structure member within the structure. + \fIRelaynews\fR's header-parsing code uses it, + defining it if the system has not supplied it. + Unfortunately, it is really hard to write a portable version of this. + The implementation we currently use is: + .DS + #define offsetof(type, mem) ((char *)&((type *)NULL)\->mem \- (char *)NULL) + .DE + The table in \fIrelay/hdrdefs.c\fR + puts invocations of \fIoffsetof\fR in initializers. + This turns out to be a severe stress test for C compilers. + A compilation error in \fIhdrdefs.c\fR is almost certain + to be problems with this macro. + Some compilers, + notably the one in Microport System V Release 2.3, + reject it. + We have heard a report that System V Release 2 on the VAX silently + miscompiles it! + If you have trouble with \fIoffsetof\fR, you might try this version instead: + .DS + #define offsetof(type, mem) ((int)&((type *)NULL)\->mem) + .DE + .SH + Fast Stdio Routines + .PP + We supply a set of fast standard-I/O routines that are compatible with + most AT&T-derived implementations of \fIstdio\fR. + They speed up C News quite a bit. + However, they don't work on all Unixes. + The tester program we supply, which the library-build procedure runs, + is thought to diagnose such problems 100% of the time. + It has been reported in the past that A/UX and Microport 386 stdios + flunk the test. + SunOS 4.0 used to pass the test falsely, but improvements in both + the test and the routines + seem to have cured the problems: + 4.0.3 passes the test and + as far as we can tell, + the routines run correctly under it. + .PP + In any case, if you are feeling nervous or are having mysterious problems, + telling \fIbuild\fR that you don't want to use the fast-stdio stuff is + always safe. + .PP + xxx more to come... end of patch 10-Jan-1990