|
|
1.1 ! root 1: /* ! 2: * File: fifo.c ! 3: * ! 4: * Purpose: allow kernel to fetch data from real-mode bootstrap data area ! 5: * ! 6: * $Log: fifo.c,v $ ! 7: * Revision 1.2 93/04/12 13:54:26 bin ! 8: * vlad: mods supplied with 386 semaphores ! 9: * ! 10: * Revision 1.1 92/10/05 13:10:43 bin ! 11: * Initial revision ! 12: * ! 13: * Revision 1.5 92/09/18 09:42:03 bin ! 14: * version 210 fom piggy ! 15: * ! 16: * Revision 1.2 92/01/06 11:59:11 hal ! 17: * Compile with cc.mwc. ! 18: * ! 19: */ ! 20: ! 21: /* ! 22: * Includes. ! 23: */ ! 24: #define KERNEL ! 25: #include <sys/typed.h> ! 26: ! 27: #ifndef T_NULL ! 28: #define T_NULL ((char *)0) ! 29: #endif ! 30: ! 31: /* ! 32: * Definitions. ! 33: * Constants. ! 34: * Macros with argument lists. ! 35: * Typedefs. ! 36: * Enums. ! 37: */ ! 38: ! 39: typedef unsigned char uchar; ! 40: typedef unsigned int uint; ! 41: typedef unsigned long ulong; ! 42: ! 43: /* ! 44: * Functions. ! 45: * Import Functions. ! 46: * Export Functions. ! 47: * Local Functions. ! 48: */ ! 49: FIFO * fifo_open(); ! 50: int fifo_close(); ! 51: typed_space * fifo_read(); ! 52: ! 53: /* ! 54: * Global Data. ! 55: * Import Variables. ! 56: * Export Variables. ! 57: * Local Variables. ! 58: * ! 59: * Arguments are passed into the kernel through boot_gift. ! 60: * If you start getting "Not enough room for all arguments." messages ! 61: * at boot time, just increase the BG_LEN to whatever you need. ! 62: * This structure is EXACTLY BG_LEN bytes long. ! 63: */ ! 64: TYPED_SPACE(boot_gift, BG_LEN, T_FIFO_SIC); ! 65: ! 66: /* ! 67: * fifo_open() ! 68: * ! 69: * Open a typed space as a fifo. ! 70: * ! 71: * Takes a typed_space that is already allocated, and a mode. The type of ! 72: * the typed space must be a FIFO. Only T_FIFO_SIC has been implimented ! 73: * (static, in-core fifo). ! 74: * ! 75: * The mode indicates whether to open for reading or writing. ! 76: * mode == 0 means read only. ! 77: * mode == 1 means write only. ! 78: * Other values are illegal. ! 79: * ! 80: * Returns a pointer to an initialized FIFO structure. FIFO structures are ! 81: * allocated from a pre-allocated array. Returns F_NULL if it can't open ! 82: * the fifo. ! 83: */ ! 84: FIFO * ! 85: fifo_open(fifo_space, mode) ! 86: typed_space *fifo_space; ! 87: int mode; ! 88: { ! 89: /* ff_table is a table of FIFO structures which can be allocated on ! 90: * demand. It is functionally similiar to the file descritor table ! 91: * in the kernel. ! 92: */ ! 93: static FIFO ff_table[NFIFOS]; ! 94: static int inited = (1==2); /* Has ff_table been initialized? */ ! 95: ! 96: int i; /* A handy counter. */ ! 97: FIFO *the_fifo; /* The fifo we are going to allocate. */ ! 98: ! 99: /* Initilize ff_table the first time we get called. */ ! 100: if (!inited) { ! 101: for (i = 0; i < NFIFOS; ++i) { ! 102: ff_table[i].f_space = F_NULL; ! 103: ff_table[i].f_flags = 0; ! 104: } ! 105: inited = 1; ! 106: } ! 107: ! 108: /* Check the type of the space we were passed. */ ! 109: switch (fifo_space->ts_type) { ! 110: case T_FIFO: /* Overly general type, assuming SIC. */ ! 111: fifo_space->ts_type = T_FIFO_SIC; ! 112: break; ! 113: case T_FIFO_SIC: /* Static In-core Fifo. */ ! 114: break; ! 115: case T_FIFO_DIC: /* Dynamic In-core Fifo (can grow). */ ! 116: return(F_NULL); /* Unimplimented. */ ! 117: case T_FIFO_SP: /* Static Permanent Fifo (fixed size file). */ ! 118: return(F_NULL); /* Unimplimented. */ ! 119: case T_FIFO_DP: /* Dynamic Permanent Fifo (ordinary file). */ ! 120: return(F_NULL); /* Unimplimented. */ ! 121: default: ! 122: return(F_NULL); /* Illegal type encountered. */ ! 123: } ! 124: ! 125: /* ASSERTION: fifo_space is a valid and implimented FIFO. */ ! 126: ! 127: /* Find the first free FIFO structure. */ ! 128: ! 129: /* This should be re-implimented using a malloc-based scheme. ! 130: * At the moment, the tertiary boot libraries do not include a ! 131: * malloc. ! 132: */ ! 133: for (i = 0; (i < NFIFOS) && (0 != ff_table[i].f_flags); ++i) { ! 134: /* Do nothing else. */ ! 135: } ! 136: ! 137: if (NFIFOS == i) { ! 138: return(F_NULL); /* No more free fifo structs. */ ! 139: } ! 140: ! 141: the_fifo = &(ff_table[i]); ! 142: ! 143: /* ASSERTION: the_fifo points at a FIFO we can take. */ ! 144: ! 145: /* Initialize the FIFO struct. */ ! 146: the_fifo->f_space = fifo_space; ! 147: the_fifo->f_offset = fifo_space->ts_data; ! 148: ! 149: /* Initilize the flags. */ ! 150: switch(mode) { ! 151: case 0: /* read */ ! 152: the_fifo->f_flags |= F_READ; ! 153: break; ! 154: case 1: /* write */ ! 155: the_fifo->f_flags |= F_WRITE; ! 156: break; ! 157: default: ! 158: return(F_NULL); /* Illegal mode flag. */ ! 159: } ! 160: ! 161: return(the_fifo); ! 162: } /* fifo_open() */ ! 163: ! 164: /* ! 165: * fifo_close() ! 166: * ! 167: * Finish with using a typed space as a fifo. ! 168: * Free up FIFO structure associated with a typed space. ! 169: * Returns 0 if ffp was not open, 1 otherwise. ! 170: */ ! 171: int ! 172: fifo_close(ffp) ! 173: FIFO *ffp; ! 174: { ! 175: if (0 == ffp->f_flags) { ! 176: return(0); /* This ffp is not open. */ ! 177: } ! 178: ffp->f_space = F_NULL; ! 179: ffp->f_offset = T_NULL; ! 180: ffp->f_flags = 0; ! 181: ! 182: return(1); ! 183: } /* fifo_close() */ ! 184: ! 185: /* ! 186: * fifo_read() ! 187: * ! 188: * Read a typed space from a fifo. ! 189: * Return a pointer to the next typed space in the fifo ffp. Returns ! 190: * NULL on end of fifo. ! 191: * ! 192: * This read assumes that ffp->f_space has type T_FIFO_SIC. ! 193: */ ! 194: typed_space * ! 195: fifo_read(ffp) ! 196: register FIFO *ffp; ! 197: { ! 198: typed_space *retval; ! 199: ! 200: /* Read MUST be set. */ ! 201: if (F_READ != F_READ & ffp->f_flags ) { ! 202: return(T_NULL); /* This ffp is not open for reading. */ ! 203: } ! 204: ! 205: /* From here to the end of fifo_read is really fifo_read_sic(). */ ! 206: ! 207: ! 208: /* Space of size 0 marks EOFIFO. */ ! 209: if ((long)0 == ffp->f_offset->ts_size) { ! 210: retval = T_NULL; ! 211: } else { ! 212: /* Return the next space. */ ! 213: retval = ffp->f_offset; ! 214: /* Advance to the next space. */ ! 215: (char *) ffp->f_offset += ffp->f_offset->ts_size; ! 216: } ! 217: ! 218: return(retval); ! 219: } /* fifo_read() */ ! 220: ! 221: #ifdef TEST ! 222: #include <stdio.h> ! 223: ! 224: /* This is the typed space we will use for our FIFO operations. */ ! 225: TYPED_SPACE(global_space, 128, T_FIFO_SIC); /* Static In-Core Fifo. */ ! 226: ! 227: int ! 228: main() ! 229: { ! 230: FIFO *ffp; /* Fifo pointer for a handle. */ ! 231: char line[1024]; /* Place to put input lines. */ ! 232: long size; /* Length for line. (Sizes are all long.) */ ! 233: int i; ! 234: ! 235: typed_space *local_space; ! 236: ! 237: /* Open the fifo for writing. */ ! 238: if (F_NULL == (ffp = fifo_open(&global_space, 1))) { ! 239: fprintf(stderr, "Can't open global_space for writing.\n"); ! 240: exit(1); ! 241: } ! 242: ! 243: do { ! 244: printf("Feed me: "); ! 245: gets(line); ! 246: size = (long) (strlen(line) + 1); ! 247: } while (T_NULL != fifo_write_untyped(ffp, line, size, T_STR_STR)); ! 248: ! 249: if (0 == fifo_close(ffp)) { ! 250: fprintf(stderr, "Failed to close global_space.\n"); ! 251: exit(1); ! 252: } ! 253: ! 254: printf("OK, global_space is now full.\n"); ! 255: /* ASSERTION: We've filled global_space with strings. */ ! 256: ! 257: /* Open the fifo for reading. */ ! 258: if (F_NULL == (ffp = fifo_open(&global_space, 0))) { ! 259: fprintf(stderr, "Can't open global_space for reading.\n"); ! 260: exit(1); ! 261: } ! 262: ! 263: /* Dump the contents of this FIFO. */ ! 264: for (i = 1; T_NULL != (local_space = fifo_read(ffp)); ++i) { ! 265: printf("%d: size: %ld: type: 0x%x\n", i, ! 266: local_space->ts_size, ! 267: local_space->ts_type); ! 268: ! 269: /* Assume everything is a NUL terminated string. */ ! 270: printf("datum: %s\n\n", local_space->ts_data); ! 271: printf("Hit <RETURN>"); ! 272: gets(line); ! 273: } ! 274: ! 275: ! 276: /* Rewind the file, and dump it out again. */ ! 277: printf("Rewinding.\n"); ! 278: if (0 == fifo_rewind(ffp)) { ! 279: fprintf("Can't rewind global_space.\n"); ! 280: exit(1); ! 281: } ! 282: ! 283: for (i = 1; T_NULL != (local_space = fifo_read(ffp)); ++i) { ! 284: printf("%d: size: %ld: type: 0x%x\n", i, ! 285: local_space->ts_size, ! 286: local_space->ts_type); ! 287: ! 288: /* Assume everything is a NUL terminated string. */ ! 289: printf("datum: %s\n\n", local_space->ts_data); ! 290: } ! 291: ! 292: if (0 == fifo_close(ffp)) { ! 293: fprintf(stderr, "Failed to close global_space.\n"); ! 294: exit(1); ! 295: } ! 296: ! 297: exit(0); ! 298: } /* main() */ ! 299: ! 300: #endif /* TEST */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.