* This software is Copyright (c) 1985 by Rick Adams.
* Permission is hereby granted to copy, reproduce, redistribute or
* otherwise use this software as long as: there is no monetary
* profit gained specifically from the use or reproduction or this
* software, it is not sold, rented, traded or otherwise marketed, and
* this copyright notice is included prominently in any copy
* The author make no claims as to the fitness or correctness of
* this software for any use whatsoever, and it is provided as is.
* Any use of this software is at the user's own risk.
* Batch: program to batch a list of news articles into an unbatch script.
* Usage: /usr/lib/news/batch listfile [bytecount]
* where listfile is a file containing a list, one per line, of full
* path names of files containing articles, e.g. as produced by the F
* transmission option in the sys file.
* bytecount is the maximum number of bytes to output before exiting
* Output is placed on standard output.
* With the shellfile "sendbatch", with machine names as arguments:
* sendbatch rlgvax seismo
* This would be invoked every hour or two from crontab.
static char *SccsId
= "@(#)batch.c 1.19 10/7/87";
#if defined(USG) || defined(BSD4_2)
extern char *sys_errlist
[];
fprintf(stderr
, "Usage: batch listfile [bytecount]\n");
* Rename real file to a work name to avoid race conditions.
* If workfile exists skip the rename in order
* to recover from a crash w/o losing anything.
(void) strcpy(workfile
, argv
[1]);
(void) strcat(workfile
, ".work");
if (access(workfile
, 0) < 0) {
if (access(argv
[1], 0) < 0 && errno
== ENOENT
)
if (rename(argv
[1], workfile
) < 0) {
logerror("rename(%s,%s) %s", argv
[1], workfile
,
fd
= fopen(workfile
, "r");
logerror("fopen(%s,r) %s", workfile
, sys_errlist
[errno
]);
maxbytes
= atol(argv
[2]);
maxbytes
= 100000000L; /* backwards compatible */
while ((fdstatus
= fgets(fname
, sizeof fname
, fd
)) != NULL
) {
(void) fstat(fileno(nfd
), &sbuf
);
if (nbytes
> maxbytes
&& nbytes
!= sbuf
.st_size
)
printf("#! rnews %ld\n", (long)sbuf
.st_size
);
/* guess length of #! rnews string */
while (c
= fread(cbuf
, 1, sizeof cbuf
, nfd
)) {
fwrite(cbuf
, 1, c
, stdout
);
logerror("stdout write %s", sys_errlist
[errno
]);
if (n
!= sbuf
.st_size
) { /* paranoia */
logerror("%s, expected %ld bytes, got %ld", fname
,
/* breaking out of this early will end up resyncing
the batch files (isn't serendipity wonderful?) */
if (fdstatus
!= NULL
) { /* exceeded maxbytes */
(void) strcpy(tmpfile
, argv
[1]);
(void) strcat(tmpfile
, ".tmp");
nfd
= fopen(tmpfile
, "w");
logerror("fopen(%s,w) %s", tmpfile
, sys_errlist
[errno
]);
} while (fgets(fname
, sizeof fname
, fd
) != NULL
);
logerror("write(%s) %s", tmpfile
, sys_errlist
[errno
]);
/* will pick it up next time thru */
if (rename(tmpfile
, workfile
) < 0) {
logerror("rename(%s,%s) %s", tmpfile
, workfile
,
* Log the given message, with printf strings and parameters allowed,
* on the log file, if it can be written.
logerror(fmt
, a1
, a2
, a3
, a4
, a5
, a6
, a7
, a8
, a9
)
long a1
, a2
, a3
, a4
, a5
, a6
, a7
, a8
, a9
;
char lfname
[BUFLEN
]; /* the log file */
#if defined(LOGDIR) || defined(HOME)
(void) sprintf(lfname
, "%s/%s/errlog", logdir(HOME
), LIBDIR
);
(void) sprintf(lfname
, "%s/errlog", LIBDIR
);
(void) sprintf(bfr
, fmt
, a1
, a2
, a3
, a4
, a5
, a6
, a7
, a8
, a9
);
if (access(lfname
, 0) == 0 && (logfile
= fopen(lfname
, "a")) != NULL
) {
#if defined(USG) || defined(BSD4_2)
flags
= fcntl(fileno(logfile
), F_GETFL
, 0);
(void) fcntl(fileno(logfile
), F_SETFL
, flags
|O_APPEND
);
(void) lseek(fileno(logfile
), 0L, 2);
fprintf(logfile
, "%s\tbatch\t%s\n", logtime
, bfr
);
register char *from
, *to
;