Relay-Version: version B 2.10 5/3/83; site utzoo.UUCP Posting-Version: version B 2.10.2 9/18/84 +MULTI+2.11; site stc.UUCP Path: utzoo!linus!philabs!cmcl2!seismo!mcvax!ukc!stc!shimell From: shimell@stc.UUCP (Dave Shimell) Newsgroups: net.sources Subject: Re: A batch system for 4.2 (2 of 2) Message-ID: <227@stc-a.stc.UUCP> Date: Sat, 27-Apr-85 00:40:23 EDT Article-I.D.: stc-a.227 Posted: Sat Apr 27 00:40:23 1985 Date-Received: Sun, 28-Apr-85 07:48:56 EDT References: <226@stc-a.stc.UUCP> Reply-To: ollie@stc.UUCP (Bruce Ollie Munro) Distribution: net Organization: STC Telecomms. London. Lines: 687 Keywords: batch Xpath: stc stc-a Here are the routines required for the local library. These routines are required for the batch program in the previous posting. Note, these routines were originally built for portability + convenience. The Makefile will build a library for BSD4.2 by default. Regards, Dave Shimell. {root44, ukc, idec, stl, creed}!stc!shimell -=-=-=-=-=-=--=-=-=-=-=-=-=-=--=-=-=-=-=-=-=-=--=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- # To unbundle, csh this file echo Makefile cat >Makefile <<'End of Makefile' # Makefile for local libraries # %W% # SCCS = . BIN = /usr/local/lib LIB = liblocal.a CFLAGS = -O #------------------------------------------------------------------------------- all: $(LIB) @echo programs are up to date .DEFAULT: $(GET) $(GFLAGS) $(SCCS)/s.$< rm clean tidy: cp install: $(LIB) -rm -f $(BIN)/$(LIB) cp $(LIB) $(BIN)/$(LIB) ranlib $(BIN)/$(LIB) # The following is a list of files for BDS4.2. $(LIB): \ $(LIB)(curdir.o)\ $(LIB)(dname.o)\ $(LIB)(fswitch.o)\ $(LIB)(getopt.o)\ $(LIB)(sname.o)\ $(LIB)(error.o)\ $(LIB)(quit.o)\ $(LIB)(warning.o)\ $(LIB)(salloc.o)\ $(LIB)(ename.o) # The following is a complete list of files. # This will need editing for your system and # moved above. #$(LIB): # # $(LIB)(curdir.o)\ # $(LIB)(dname.o)\ # $(LIB)(fswitch.o)\ # $(LIB)(getopt.o)\ # $(LIB)(rename.o)\ # $(LIB)(sname.o)\ # $(LIB)(umask.o)\ # $(LIB)(ndir.h)\ # $(LIB)(opendir.o)\ # $(LIB)(closedir.o)\ # $(LIB)(readdir.o)\ # $(LIB)(seekdir.o)\ # $(LIB)(telldir.o)\ # \ # $(LIB)(error.o)\ # $(LIB)(quit.o)\ # $(LIB)(warning.o)\ # $(LIB)(salloc.o)\ # $(LIB)(ename.o)\ 'End of Makefile' echo closedir.c cat >closedir.c <<'End of closedir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include /* * close a directory. */ void closedir(dirp) register DIR *dirp; { close(dirp->dd_fd); dirp->dd_fd = -1; dirp->dd_loc = 0; free(dirp); } 'End of closedir.c' echo curdir.c cat >curdir.c <<'End of curdir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include extern FILE *popen(); curdir(pwd) char *pwd; /* Fill this in with the current directory */ { register FILE *fp; int reply = -1; if ((fp = popen("pwd", "r")) != NULL) { reply = 0; fscanf(fp, " %s ", pwd); pclose(fp); } return(reply); } 'End of curdir.c' echo dname.c cat >dname.c <<'End of dname.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif char * dname(nam) char *nam; { register char *slash; register char *cp; /* * Find last slash in nam. */ for (slash = cp = nam; *cp != '\0'; cp++) if (*cp == '/') slash = cp; if (slash == nam) nam = (*slash == '/' ? "/" : "."); else *slash = '\0'; return(nam); } 'End of dname.c' echo ename.c cat >ename.c <<'End of ename.c' #include extern char *sname(); #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif /* * Returns a pointer to the file type (file * extension) or NULL if one cannot be found. * Eg. * /usr.xyz/file.plm returns ".plm" * /usr.xyz/file returns NULL */ char * ename(file) register char *file; { register char *dot = NULL; for (file = sname(file); *file; file++) if (*file == '.') dot = file; return(dot); } 'End of ename.c' echo error.c cat >error.c <<'End of error.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include extern char *program; unsigned ecount; /* VARARGS1 */ error(s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10) char *s; { ecount++; fflush(stdout); fprintf(stderr, "%s: error, ", program); fprintf(stderr, s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); fprintf(stderr, "\n"); } 'End of error.c' echo fswitch.c cat >fswitch.c <<'End of fswitch.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include #ifndef TRUE # define TRUE 1 # define FALSE 0 #endif fswitch() { assert(FALSE); } 'End of fswitch.c' echo getopt.c cat >getopt.c <<'End of getopt.c' #include #define ERR(S, A) if (opterr) error((S), (A)); else int opterr = 1; int optind = 1; int optopt; char *optarg; char *program; extern char *sname(); extern char *index(); #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif int getopt(argc, argv, opts) char **argv, *opts; { static int sp = 1; register c; register char *cp; if (program == NULL) program = sname(argv[0]); if (sp == 1) { if (optind >= argc || argv[optind][0] != '-' || argv[optind][1] == '\0') return(EOF); else if (strcmp(argv[optind], "--") == NULL) { optind++; return(EOF); } } optopt = c = argv[optind][sp]; if (c == ':' || (cp = index(opts, c)) == NULL) { ERR("illegal option -%c", c); if (argv[optind][++sp] == '\0') { optind++; sp = 1; } return('?'); } if (*++cp == ':') { if (argv[optind][sp + 1] != '\0') optarg = &argv[optind++][sp + 1]; else if (++optind >= argc) { ERR("option -%c requires an argument", c); sp = 1; return('?'); } else optarg = argv[optind++]; sp = 1; } else { if (argv[optind][++sp] == '\0') { sp = 1; optind++; } optarg = NULL; } return(c); } 'End of getopt.c' echo ndir.h cat >ndir.h <<'End of ndir.h' static char ndir[] = "%W%"; /* * Change notice (rti!trt): To be compatible with non-bsd systems: * #defines for u_short, u_long, and void added. */ #define u_short unsigned short #define u_long long #define void /* * A directory consists of some number of blocks of DIRBLKSIZ * bytes, where DIRBLKSIZ is chosen such that it can be transferred * to disk in a single atomic operation (e.g. 512 bytes on most machines). * * Each DIRBLKSIZ byte block contains some number of directory entry * structures, which are of variable length. Each directory entry has * a struct direct at the front of it, containing its inode number, * the length of the entry, and the length of the name contained in * the entry. These are followed by the name padded to a 4 byte boundary * with null bytes. All names are guaranteed null terminated. * The maximum length of a name in a directory is MAXNAMLEN. * * The macro DIRSIZ(dp) gives the amount of space required to represent * a directory entry. Free space in a directory is represented by * entries which have dp->d_reclen >= DIRSIZ(dp). All DIRBLKSIZ bytes * in a directory block are claimed by the directory entries. This * usually results in the last entry in a directory having a large * dp->d_reclen. When entries are deleted from a directory, the * space is returned to the previous entry in the same directory * block by increasing its dp->d_reclen. If the first entry of * a directory block is free, then its dp->d_ino is set to 0. * Entries other than the first in a directory do not normally have * dp->d_ino set to 0. */ #define DIRBLKSIZ 512 #define MAXNAMLEN 255 struct direct { u_long d_ino; /* inode number of entry */ u_short d_reclen; /* length of this record */ u_short d_namlen; /* length of string in d_name */ char d_name[MAXNAMLEN + 1]; /* name must be no longer than this */ }; /* * The DIRSIZ macro gives the minimum record length which will hold * the directory entry. This requires the amount of space in struct direct * without the d_name field, plus enough space for the name with a terminating * null byte (dp->d_namlen+1), rounded up to a 4 byte boundary. */ #undef DIRSIZ #define DIRSIZ(dp) \ ((sizeof (struct direct) - (MAXNAMLEN+1)) + (((dp)->d_namlen+1 + 3) &~ 3)) #ifndef KERNEL /* * Definitions for library routines operating on directories. */ typedef struct _dirdesc { int dd_fd; long dd_loc; long dd_size; char dd_buf[DIRBLKSIZ]; } DIR; #ifndef NULL #define NULL 0 #endif extern DIR *opendir(); extern struct direct *readdir(); extern long telldir(); extern void seekdir(); #define rewinddir(dirp) seekdir((dirp), (long)0) extern void closedir(); #endif KERNEL 'End of ndir.h' echo opendir.c cat >opendir.c <<'End of opendir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include #include /* * open a directory. */ DIR * opendir(name) char *name; { register DIR *dirp; register int fd; struct stat sbuf; if ((fd = open(name, 0)) == -1) return NULL; fstat(fd, &sbuf); if (((sbuf.st_mode & S_IFDIR) == 0) || ((dirp = (DIR *)malloc(sizeof(DIR))) == NULL)) { close (fd); return NULL; } dirp->dd_fd = fd; dirp->dd_loc = 0; return dirp; } 'End of opendir.c' echo quit.c cat >quit.c <<'End of quit.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif int fail_status = 1; /* Exit status on error */ #include extern char *program; /* VARARGS1 */ quit(s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10) char *s; { fflush(stdout); fprintf(stderr, "%s: fatal, ", program); fprintf(stderr, s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); fprintf(stderr, "\n"); exit(fail_status); } 'End of quit.c' echo readdir.c cat >readdir.c <<'End of readdir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include /* * read an old stlye directory entry and present it as a new one */ #define ODIRSIZ 14 struct olddirect { ino_t od_ino; char od_name[ODIRSIZ]; }; /* * get next entry in a directory. */ struct direct * readdir(dirp) register DIR *dirp; { register struct olddirect *dp; static struct direct dir; for (;;) { if (dirp->dd_loc == 0) { dirp->dd_size = read(dirp->dd_fd, dirp->dd_buf, DIRBLKSIZ); if (dirp->dd_size <= 0) return NULL; } if (dirp->dd_loc >= dirp->dd_size) { dirp->dd_loc = 0; continue; } dp = (struct olddirect *)(dirp->dd_buf + dirp->dd_loc); dirp->dd_loc += sizeof(struct olddirect); if (dp->od_ino == 0) continue; dir.d_ino = dp->od_ino; strncpy(dir.d_name, dp->od_name, ODIRSIZ); dir.d_name[ODIRSIZ] = '\0'; /* insure null termination */ dir.d_namlen = strlen(dir.d_name); dir.d_reclen = DIRBLKSIZ; return (&dir); } } 'End of readdir.c' echo rename.c cat >rename.c <<'End of rename.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif rename(from, to) char *from; /* Old name */ char *to; /* New name */ { register status = -1; if (link(from, to) != -1 && unlink(from) != -1) status = 0; return(status); } 'End of rename.c' echo salloc.c cat >salloc.c <<'End of salloc.c' #include #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif extern char *malloc(); extern char *strcpy(); /* * Allocate and copy a string * into dynamic memory. */ char * salloc(nam) char *nam; { register char *p; if ((p = malloc((unsigned)strlen(nam) + 1)) == NULL) quit("dynamic memory exhausted"); return(strcpy(p, nam)); } 'End of salloc.c' echo seekdir.c cat >seekdir.c <<'End of seekdir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include /* * seek to an entry in a directory. * Only values returned by "telldir" should be passed to seekdir. */ void seekdir(dirp, loc) register DIR *dirp; long loc; { long base, offset; struct direct *dp; /* rti!trt: Always seek. Slower, but safer. This may even fix a bug. if (loc == telldir(dirp)) return; */ base = loc & ~(DIRBLKSIZ - 1); offset = loc & (DIRBLKSIZ - 1); lseek(dirp->dd_fd, base, 0); dirp->dd_loc = 0; while (dirp->dd_loc < offset) { dp = readdir(dirp); if (dp == NULL) return; } } 'End of seekdir.c' echo sname.c cat >sname.c <<'End of sname.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif char * sname(nam) register char *nam; { register char *slash; slash = nam; while (*nam != '\0') { if (*nam++ == '/') slash = nam; } return(slash); } 'End of sname.c' echo telldir.c cat >telldir.c <<'End of telldir.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include #include extern long lseek(); /* needed for pdp 11s -- ikonas!mcm */ /* * return a pointer into a directory */ long telldir(dirp) DIR *dirp; { return (lseek(dirp->dd_fd, 0L, 1) - dirp->dd_size + dirp->dd_loc); } 'End of telldir.c' echo umask.c cat >umask.c <<'End of umask.c' /* * Some systems do not have this * system call. * * DB Shimell September 1984 */ #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif umask(numask) { return(0); } 'End of umask.c' echo warning.c cat >warning.c <<'End of warning.c' #ifndef lint #ifndef NSCCS static char sccsid[] = "%W%"; #endif #endif #include extern char *program; unsigned wcount; /* VARARGS1 */ warning(s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10) char *s; { wcount++; fflush(stdout); fprintf(stderr, "%s: warning, ", program); fprintf(stderr, s, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10); fprintf(stderr, "\n"); } 'End of warning.c' exit 0 -- Regards, Dave Shimell. {root44, ukc, idec, stl, creed}!stc!shimell