123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656 |
- /*
- THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
- SOFTWARE CORPORATION ("PARALLAX"). PARALLAX, IN DISTRIBUTING THE CODE TO
- END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
- ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
- IN USING, DISPLAYING, AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
- SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
- FREE PURPOSES. IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
- CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES. THE END-USER UNDERSTANDS
- AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.
- COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
- */
- /*
- * $Source: f:/miner/source/pslib/rcs/library.c $
- * $Revision: 1.30 $
- * $Author: matt $
- * $Date: 1994/03/23 13:55:30 $
- *
- * Sample setup for RCS header
- *
- * $Log: library.c $
- * Revision 1.30 1994/03/23 13:55:30 matt
- * Set others_use in library get info routine
- *
- * Revision 1.29 1994/02/15 12:53:25 john
- * Made numfiles stored in library be a short instead of char.
- *
- * Revision 1.28 1994/02/14 20:11:38 john
- * First version working with new cfile stuff.
- *
- * Revision 1.27 1994/01/17 11:01:23 john
- * Made cfopen return NULL when file not found instead
- * of doing an Error inside ReadFile.
- *
- * Revision 1.26 1994/01/07 12:02:41 yuan
- * fixed problem with checkfile.
- * CheckFile now checks the directory first, rather
- * than the library
- *
- * Revision 1.25 1994/01/07 11:45:24 yuan
- * cleaned up some code.
- *
- * Revision 1.24 1994/01/07 10:24:29 yuan
- * Makes it so ReadFile reads from directory before
- * it checks the library file.
- *
- * Revision 1.23 1993/12/15 11:18:45 yuan
- * Fixed calloc in lib_init... Changed it to MALLOC
- *
- * Revision 1.22 1993/12/10 19:26:13 matt
- * Made more functions call Error() instead of returning error codes
- *
- * Revision 1.21 1993/12/08 17:06:47 yuan
- * Added CheckFile();
- *
- * Revision 1.20 1993/12/08 16:07:05 yuan
- * Changed MAX_FILES for FileList[]
- *
- * Revision 1.19 1993/10/28 14:40:55 yuan
- * cfread changed to cfreadfile.
- *
- * Revision 1.18 1993/10/27 12:42:29 yuan
- * Added ReadFileBuf to read into a buffer (compressed)
- *
- * Revision 1.17 1993/10/19 14:11:09 yuan
- * Fixed uncompress reading/writing problem
- *
- * Revision 1.16 1993/10/19 13:55:44 matt
- * Made ReadFile() call Error() on file error
- *
- * Revision 1.15 1993/10/19 12:38:53 matt
- * Cleaned up error handling in lib_init() a little
- *
- * Revision 1.14 1993/10/19 11:33:33 yuan
- * Fixed cfread free problem.
- *
- * Revision 1.13 1993/10/18 18:00:27 yuan
- * Fixed memory alloc errors.
- *
- * Revision 1.12 1993/10/17 18:01:48 yuan
- * Fixed the first file counting problem.
- *
- * Revision 1.11 1993/09/29 17:52:59 yuan
- * *** empty log message ***
- *
- * Revision 1.10 1993/09/29 17:46:54 yuan
- * ReadFile, etc. I/O functions moved back into library.c
- * ReadFile was renamed to ReadFileRaw which just reads
- * a file into a buffer... LibReadFile was renamed to
- * ReadFile, and it reads from either a library or a buffer
- * depending on lib_init and if the file is found in the
- * library.
- *
- * Also, printfs and exits for errors were removed.
- *
- * In this version, ReadFile should be completely transparent
- * to the user.
- *
- * Revision 1.9 1993/09/27 17:13:20 yuan
- * LibReadFile, lib_init, and lib_close functions added.
- * Documented in library.h.
- *
- * Revision 1.8 1993/09/21 17:22:26 yuan
- * *** empty log message ***
- *
- * Revision 1.7 1993/09/21 17:16:37 yuan
- * cleaning up
- *
- * Revision 1.6 1993/09/21 17:06:14 yuan
- * broken and then unbroken version.
- * need to restart the cflib_init stuff from scratch.
- *
- * Revision 1.5 1993/09/14 13:14:23 yuan
- * additional change which was made in 1.4:
- * If lzw_compress returns a size overflow (*size = -1) then it
- * means that the compression ratio is negative, thus we will
- * store the file rather than compress it.
- *
- * Revision 1.4 1993/09/14 13:06:41 yuan
- * Major changes made.
- * 1) cfread and cfwrite have been changed into lzw_expand and lzw_compress.
- * these functions now manipulate buffers rather than files.
- * 2) cfread, cfwrite, cfr_test, and cfw_test have been added.
- * cfread takes a file and returns a buffer.
- * cfwrite takes a buffer and writes to a file.
- * cfr_test and cfw_test are test programs for the previous two
- * programs and read and write files.
- * 3) extract now returns a buffer rather than passing a buffer as a
- * parameter.
- * 4) switches are allowed anywhere on the command line now.
- * 5) -a switch added in order to add files to a library.
- * 6) Help message lists available options.
- * 7) Date & Time added to library file headers.
- *
- * Revision 1.3 1993/09/09 17:42:21 yuan
- * parsarg running off of library
- * parsarg passes full path, so filename is extracted from path
- * for library.
- * checks to make sure library is not added to itself.
- * checks to make sure '-l' is not called in the middle of a build.
- *
- * Revision 1.2 1993/09/09 12:38:48 yuan
- * WriteFile and AppendFile fixed.
- *
- * Revision 1.1 1993/09/08 16:14:46 yuan
- * Initial revision
- *
- *
- */
- #pragma off (unreferenced)
- static char rcsid[] = "$Id: library.c 1.30 1994/03/23 13:55:30 matt Exp $";
- #pragma on (unreferenced)
- #include <time.h>
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <ctype.h>
- #include <stdarg.h>
- #include <conio.h>
- #include <dos.h>
- #include <fcntl.h>
- #include <io.h>
- #include <sys\types.h>
- #include <sys\stat.h>
- #include <errno.h>
- #include <string.h>
- #include "library.h"
- #include "mem.h"
- #include "error.h"
- int lib_flag; // library flag
- int l_flag; // listing flag
- int b_flag; // building flag;
- int c_flag; // compression flag
- FILE *InputLibFile; // file to read from
- FILE *OutputLibFile; // file to write to
- char *lib_name; // name of the library
- int file_count; // number of files processed
- int headers; // number of header spaces allocated
- char *FileList[MAX_FILES]; // Contains the list of files being processed
- file_header Header; // Holds header info of file being processed
- file_header *LibHeaderList;
- FILE *InputLibInitFile; // file to read from
- short init_numfiles; // number of files in the library
- int ReadFileBufRaw( char *filename, ubyte *buf, int bufsize )
- {
- int length;
- int handle;
- handle = open( filename, O_RDONLY | O_BINARY );
- if (handle == -1 )
- Error("File %s, %s ",filename,strerror(errno));
- if (length = read( handle, buf, bufsize ) != bufsize )
- {
- close( handle );
- Error("File %s, %s ",filename,strerror(errno));
- }
- close( handle );
- return length;
- }
- ubyte *ReadFileRaw( char *filename, int *length )
- {
- void *FileData;
- int handle;
- handle = open( filename, O_RDONLY | O_BINARY );
- if (handle == -1 )
- return NULL;
- // Error("File %s, %s ",filename,strerror(errno));
- *length = filelength( handle );
- // MALLOC( FileData, ubyte, *length );//Compile hack again -KRB
- FileData = (ubyte *)malloc(*length*sizeof(ubyte));
- if (FileData == NULL ) {
- close( handle );
- Error("File %s, cannot malloc memory",filename);
- }
- if (read( handle, FileData, *length ) != *length ) {
- free( FileData );
- close( handle );
- Error("File %s, %s ",filename,strerror(errno));
- }
- close( handle );
- return FileData;
- }
- int AppendFile( char *filename, void *data, int length )
- {
- int handle;
- handle = open( filename, O_WRONLY | O_CREAT | O_APPEND | O_BINARY , S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP );
- if (handle == -1 ) {
- // return ERROR_OPENING_FILE;
- Error("File %s, %s ",filename,strerror(errno));
- }
- if (write( handle, data, length )!=length) {
- close( handle );
- // return ERROR_WRITING_FILE;
- Error("File %s, %s ",filename,strerror(errno));
- }
- close( handle );
- return 0;
- }
- int WriteFile( char *filename, void *data, int length )
- {
- int handle;
- handle = open( filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP );
- if (handle == -1 ) {
- // return ERROR_OPENING_FILE;
- Error("File %s, %s ",filename,strerror(errno));
- }
- if (write( handle, data, length )!=length) {
- close( handle );
- // return ERROR_WRITING_FILE;
- Error("File %s, %s ",filename,strerror(errno));
- }
- close( handle );
- return 0;
- }
- int cfwritefile( char *filename, ubyte *buffer, int length ) {
- FILE *output;
- ubyte *compressed;
- int size;
- output = fopen( filename, "wb");
- putc( 'C', output );
- putc( 'F', output );
- fwrite( &length, sizeof(length), 1, output);
- compressed = lzw_compress( buffer, NULL, length, &size);
- if (size < 0) {
- printf(" WARNING! : Compressed size larger than original\n");
- printf(" Not storing.\n");
- }
- else {
- fwrite( compressed, sizeof(ubyte), size, output);
- fclose( output );
- free( compressed );
- return LF_LZW;
- }
- return 0;
- }
- ubyte *cfreadfile( char *filename, int *size ) {
- FILE *input;
- ubyte *tempbuf;
- ubyte *buf;
- char header[3];
- int length, i;
- input = fopen( filename, "rb" );
- for (i=0;i<3;i++) header[i]=0;
- for (i=0;i<2;i++)
- header[i] = (char) getc( input );
- if (strcmp( header, "CF" )) {
- return NULL;
- }
- fread( size, sizeof(int), 1, input);
- length = file_size( filename ) - 6;
- //MALLOC( tempbuf, ubyte, length );//Compile hack again -KRB
- tempbuf=(ubyte *)malloc(length*sizeof(ubyte));
- fread( tempbuf, sizeof(ubyte), length, input );
- buf = lzw_expand( tempbuf, NULL, *size );
- return buf;
- }
- ubyte *extract( char *library, char *filename ) {
- int i;
- ubyte *buf_ptr;
- ubyte *buf;
- ubyte *tempbuf;
- char header_buf[5];
- short numfiles;
- strupr( filename );
- InputLibFile = fopen( library, "rb" );
- for (i=0;i<5;i++) header_buf[i]=0;
- for (i=0;i<4;i++)
- header_buf[i] = (char) getc( InputLibFile );
- if (strcmp(header_buf, "PSLB")) {
- fclose( InputLibFile );
- return NULL;
- }
- else {
- //numfiles = (short) getc( InputLibFile );
- fread( &numfiles, sizeof(short), 1, InputLibFile );
- for (i=0; i<numfiles; i++) {
- read_data( InputLibFile, &Header );
- if (!strcmp(Header.name, filename)) {
- fseek( InputLibFile, Header.offset, SEEK_SET );
- //MALLOC(buf, ubyte, Header.original_size);//Compile hack again -KRB
- buf=(ubyte *)malloc(Header.original_size*sizeof(ubyte));
- buf_ptr = buf;
- if ( Header.compression == 0 ) {
- fread( buf, sizeof(ubyte), Header.original_size, InputLibFile );
- }
- else if ( Header.compression == LF_LZW ) {
- //MALLOC(tempbuf, ubyte, Header.length);//Compile hack again -KRB
- tempbuf=(ubyte*)malloc(Header.length*sizeof(ubyte));
- fread( tempbuf, sizeof(ubyte), Header.length, InputLibFile );
- lzw_expand( tempbuf, buf, Header.original_size );
- }
- break;
- }
- }
- if ( i >= numfiles ) return NULL;
- fclose( InputLibFile );
- return buf_ptr;
- }
- }
- int read_data( FILE *fp, struct file_header *p )
- {
- return( fread( p, sizeof(*p), 1, fp ) );
- }
- int file_size( char *name ) {
- long eof_ftell;
- FILE *file;
- file = fopen( name, "r" );
- if ( file == NULL )
- return( 0L );
- fseek( file, 0L, SEEK_END );
- eof_ftell = ftell( file );
- fclose( file );
- return( eof_ftell );
- }
- int ReadFileBuf( char *filename, ubyte *buf, int bufsize ) {
- int i;
- int length;
- ubyte *tempbuf;
- strupr( filename );
- length = -1;
- if (CheckFile( filename )==1)
- return ReadFileBufRaw( filename, buf, bufsize );
- if (lib_flag == 1)
- for ( i=0; i < init_numfiles; i++ ) {
- if (!strcmp(LibHeaderList[i].name, filename)) {
- fseek( InputLibInitFile, LibHeaderList[i].offset, SEEK_SET );
- length = LibHeaderList[i].original_size;
-
- if ( length == bufsize )
- if ( LibHeaderList[i].compression == 0 ) {
- //printf("Reading buf size = %d\n", LibHeaderList[i].original_size);
- fread( buf, sizeof(ubyte), LibHeaderList[i].original_size, InputLibInitFile );
- }
- else if ( LibHeaderList[i].compression == LF_LZW ) {
- //MALLOC(tempbuf, ubyte, LibHeaderList[i].length);//Compile hack again -KRB
- tempbuf=(ubyte *)malloc( LibHeaderList[i].length*sizeof(ubyte));
- fread( tempbuf, sizeof(ubyte), LibHeaderList[i].length, InputLibInitFile );
- lzw_expand( tempbuf, buf, LibHeaderList[i].original_size );
- }
-
- break;
- }
- }
- // else
- // return ReadFileBufRaw( filename, buf, bufsize );
- if ( i >= init_numfiles )
- return ReadFileBufRaw( filename, buf, bufsize );
-
- return length; //buf_ptr;
- }
- ubyte *ReadFile( char *filename, int *length ) {
- int i;
- ubyte *buf_ptr;
- ubyte *buf;
- ubyte *tempbuf;
- strupr( filename );
- *length = -1;
- if (CheckFile( filename )==1)
- return ReadFileRaw( filename, length );
- if (lib_flag == 1)
- for ( i=0; i < init_numfiles; i++ ) {
- if (!strcmp(LibHeaderList[i].name, filename)) {
- fseek( InputLibInitFile, LibHeaderList[i].offset, SEEK_SET );
- //MALLOC(buf, ubyte, LibHeaderList[i].original_size);//Compile hack again -KRB
- buf=(ubyte *)malloc(LibHeaderList[i].original_size*sizeof(ubyte));
- buf_ptr = buf;
- *length = LibHeaderList[i].original_size;
-
- if ( LibHeaderList[i].compression == 0 ) {
- //printf("Reading buf size = %d\n", LibHeaderList[i].original_size);
- fread( buf, sizeof(ubyte), LibHeaderList[i].original_size, InputLibInitFile );
- }
-
- else if ( LibHeaderList[i].compression == LF_LZW ) {
- //MALLOC(tempbuf, ubyte, LibHeaderList[i].length);//Compile hack again -KRB
- tempbuf=(ubyte *)malloc(LibHeaderList[i].length*sizeof(ubyte));
- fread( tempbuf, sizeof(ubyte), LibHeaderList[i].length, InputLibInitFile );
- lzw_expand( tempbuf, buf, LibHeaderList[i].original_size );
- }
-
- break;
- }
- }
- //else
- //return ReadFileRaw( filename, length );
- if ( i >= init_numfiles )
- return ReadFileRaw( filename, length );
- return buf_ptr;
- }
- //returns error codes listed in cflib.h
- int lib_init( char *init_lib_name ) {
- char header_buf[5];
- int i;
- short temp;
- InputLibInitFile = fopen( init_lib_name, "rb" );
- if (! InputLibInitFile) return LI_NO_FILE;
- for (i=0;i<5;i++) header_buf[i]=0;
- for (i=0;i<4;i++)
- header_buf[i] = (char) getc( InputLibInitFile );
- if (strcmp(header_buf, "PSLB")) {
- fclose( InputLibInitFile );
- return LI_NOT_PSLIB;
- }
- //init_numfiles = (short) getc( InputLibInitFile );
- fread( &temp, sizeof(short), 1, InputLibInitFile );
- init_numfiles = temp;
- // MALLOC ( LibHeaderList, file_header, init_numfiles );//Compile hack again -KRB
- LibHeaderList=(file_header *)malloc(init_numfiles*sizeof(file_header));
- if (! LibHeaderList) {
- fclose(InputLibInitFile);
- return LI_NO_MEM;
- }
- fread( LibHeaderList, sizeof( *LibHeaderList ), init_numfiles, InputLibInitFile );
- atexit(lib_close);
- lib_flag = 1; //everything is ok, so mark as open
- return LI_NO_ERROR;
- }
- void lib_close() {
- fclose( InputLibInitFile );
- free (LibHeaderList);
- lib_flag = 0;
- }
- void init_library( char *filename, int numfiles ) {
- lib_header Lib_Header;
- int i;
- ubyte nul;
- short temp;
-
- OutputLibFile = fopen( filename, "wb");
- strcpy( Lib_Header.id, "PSLB" );
- Lib_Header.nfiles = numfiles;
- for ( i=0; i<4 ; i++ ) putc( Lib_Header.id[i], OutputLibFile );
- temp = Lib_Header.nfiles;
- //putc( Lib_Header.nfiles, OutputLibFile );
- temp = Lib_Header.nfiles;
- fwrite( &temp, sizeof(short), 1, OutputLibFile );
- nul = 0;
- for ( i=0; i<numfiles; i++ ) fwrite( &nul, sizeof(nul), 32, OutputLibFile );
- fclose( OutputLibFile );
- }
- void write_file_header( char *filename, file_header Header ) {
- OutputLibFile = fopen( filename, "rb+" );
- fseek( OutputLibFile, 4+sizeof(short)+32*(file_count-1), SEEK_SET );
- fwrite( &Header, sizeof(file_header), 1, OutputLibFile );
- fclose( OutputLibFile );
- }
- int CheckFile( char *filename ) {
- int i;
- int handle;
- strupr( filename );
- handle = open( filename, O_RDONLY | O_BINARY );
- if (handle != -1)
- {
- close( handle );
- return 1;
- }
- close(handle);
-
- if (lib_flag == 1)
- for ( i=0; i < init_numfiles; i++ )
- if (!strcmp(LibHeaderList[i].name, filename))
- return 2;
-
- return 0;
-
- }
- FILE * LibraryGetFileInfo( char *filename, int * others_use, int * lib_offset, int * file_size, int * org_size, int * compressed, char * buffer ) {
- int i;
- FILE * lib_file;
- char signature[3];
- strupr( filename );
- lib_file = fopen( filename, "rb" );
- if (lib_file) {
- if (buffer)
- setvbuf( lib_file, buffer, _IOFBF, 4096*2 );
- *file_size = filelength( fileno( lib_file ));
- fread( signature, 2, sizeof(char), lib_file );
- signature[2] = '\0';
- if (!strcmp( signature, "CF" )) {
- fread( org_size, 1, sizeof(int), lib_file );
- *lib_offset = 6L; // Offset is CF+Length into file
- *compressed = 1;
- } else {
- *org_size = *file_size;
- *lib_offset = 0;
- fseek( lib_file, 0L, SEEK_SET );
- *compressed = 0;
- }
- *others_use = 0;
- return lib_file;
- }
- if (lib_flag == 1)
- for ( i=0; i < init_numfiles; i++ ) {
- if (!strcmp(LibHeaderList[i].name, filename)) {
- lib_file = InputLibInitFile;
- *lib_offset = LibHeaderList[i].offset;
- *org_size = LibHeaderList[i].original_size;
- *file_size = LibHeaderList[i].length;
- *compressed = (LibHeaderList[i].compression == LF_LZW );
- *others_use = 1;
- return lib_file;
- }
- }
- lib_file = NULL;
- *others_use = 0;
- *lib_offset = 0;
- *org_size = 0;
- *file_size = 0;
- *compressed=0;
- return lib_file;
- }
|