|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1983, 1985 Regents of the University of California. ! 3: * All rights reserved. The Berkeley software License Agreement ! 4: * specifies the terms and conditions for redistribution. ! 5: */ ! 6: ! 7: #if defined(LIBC_SCCS) && !defined(lint) ! 8: static char sccsid[] = "@(#)findiop.c 5.6 (Berkeley) 3/9/86"; ! 9: #endif LIBC_SCCS and not lint ! 10: ! 11: #include <stdio.h> ! 12: #include <errno.h> ! 13: ! 14: extern int errno; ! 15: ! 16: #define active(iop) ((iop)->_flag & (_IOREAD|_IOWRT|_IORW)) ! 17: ! 18: #define NSTATIC 20 /* stdin + stdout + stderr + the usual */ ! 19: ! 20: FILE _iob[NSTATIC] = { ! 21: { 0, NULL, NULL, 0, _IOREAD, 0 }, /* stdin */ ! 22: { 0, NULL, NULL, 0, _IOWRT, 1 }, /* stdout */ ! 23: { 0, NULL, NULL, 0, _IOWRT|_IONBF, 2 }, /* stderr */ ! 24: }; ! 25: ! 26: extern char *calloc(); ! 27: ! 28: static char sbuf[NSTATIC]; ! 29: char *_smallbuf = sbuf; ! 30: static FILE **iobglue; ! 31: static FILE **endglue; ! 32: ! 33: /* ! 34: * Find a free FILE for fopen et al. ! 35: * We have a fixed static array of entries, and in addition ! 36: * may allocate additional entries dynamically, up to the kernel ! 37: * limit on the number of open files. ! 38: * At first just check for a free slot in the fixed static array. ! 39: * If none are available, then we allocate a structure to glue together ! 40: * the old and new FILE entries, which are then no longer contiguous. ! 41: */ ! 42: FILE * ! 43: _findiop() ! 44: { ! 45: register FILE **iov, *iop; ! 46: register FILE *fp; ! 47: ! 48: if (iobglue == 0) { ! 49: for (iop = _iob; iop < _iob + NSTATIC; iop++) ! 50: if (!active(iop)) ! 51: return (iop); ! 52: ! 53: if (_f_morefiles() == 0) { ! 54: errno = ENOMEM; ! 55: return (NULL); ! 56: } ! 57: } ! 58: ! 59: iov = iobglue; ! 60: while (*iov != NULL && active(*iov)) ! 61: if (++iov >= endglue) { ! 62: errno = EMFILE; ! 63: return (NULL); ! 64: } ! 65: ! 66: if (*iov == NULL) ! 67: *iov = (FILE *)calloc(1, sizeof **iov); ! 68: ! 69: return (*iov); ! 70: } ! 71: ! 72: _f_morefiles() ! 73: { ! 74: register FILE **iov; ! 75: register FILE *fp; ! 76: register char *cp; ! 77: int nfiles; ! 78: ! 79: nfiles = getdtablesize(); ! 80: ! 81: iobglue = (FILE **)calloc(nfiles, sizeof *iobglue); ! 82: if (iobglue == NULL) ! 83: return (0); ! 84: ! 85: endglue = iobglue + nfiles; ! 86: ! 87: for (fp = _iob, iov = iobglue; fp < &_iob[NSTATIC]; /* void */) ! 88: *iov++ = fp++; ! 89: ! 90: _smallbuf = calloc(nfiles, sizeof(*_smallbuf)); ! 91: return (1); ! 92: } ! 93: ! 94: f_prealloc() ! 95: { ! 96: register FILE **iov; ! 97: register FILE *fp; ! 98: ! 99: if (iobglue == NULL && _f_morefiles() == 0) ! 100: return; ! 101: ! 102: for (iov = iobglue; iov < endglue; iov++) ! 103: if (*iov == NULL) ! 104: *iov = (FILE *)calloc(1, sizeof **iov); ! 105: } ! 106: ! 107: _fwalk(function) ! 108: register int (*function)(); ! 109: { ! 110: register FILE **iov; ! 111: register FILE *fp; ! 112: ! 113: if (iobglue == NULL) { ! 114: for (fp = _iob; fp < &_iob[NSTATIC]; fp++) ! 115: if (active(fp)) ! 116: (*function)(fp); ! 117: } else { ! 118: for (iov = iobglue; iov < endglue; iov++) ! 119: if (*iov && active(*iov)) ! 120: (*function)(*iov); ! 121: } ! 122: } ! 123: ! 124: _cleanup() ! 125: { ! 126: extern int fclose(); ! 127: ! 128: _fwalk(fclose); ! 129: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.