diff options
Diffstat (limited to 'nx-X11/lib/psres/PSres.c')
-rw-r--r-- | nx-X11/lib/psres/PSres.c | 1661 |
1 files changed, 0 insertions, 1661 deletions
diff --git a/nx-X11/lib/psres/PSres.c b/nx-X11/lib/psres/PSres.c deleted file mode 100644 index b7fd4acba..000000000 --- a/nx-X11/lib/psres/PSres.c +++ /dev/null @@ -1,1661 +0,0 @@ -/* - * PSres.c - * - * (c) Copyright 1991-1994 Adobe Systems Incorporated. - * All rights reserved. - * - * Permission to use, copy, modify, distribute, and sublicense this software - * and its documentation for any purpose and without fee is hereby granted, - * provided that the above copyright notices appear in all copies and that - * both those copyright notices and this permission notice appear in - * supporting documentation and that the name of Adobe Systems Incorporated - * not be used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. No trademark license - * to use the Adobe trademarks is hereby granted. If the Adobe trademark - * "Display PostScript"(tm) is used to describe this software, its - * functionality or for any other purpose, such use shall be limited to a - * statement that this software works in conjunction with the Display - * PostScript system. Proper trademark attribution to reflect Adobe's - * ownership of the trademark shall be given whenever any such reference to - * the Display PostScript system is made. - * - * ADOBE MAKES NO REPRESENTATIONS ABOUT THE SUITABILITY OF THE SOFTWARE FOR - * ANY PURPOSE. IT IS PROVIDED "AS IS" WITHOUT EXPRESS OR IMPLIED WARRANTY. - * ADOBE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL - * IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND - * NON- INFRINGEMENT OF THIRD PARTY RIGHTS. IN NO EVENT SHALL ADOBE BE LIABLE - * TO YOU OR ANY OTHER PARTY FOR ANY SPECIAL, INDIRECT, OR CONSEQUENTIAL - * DAMAGES OR ANY DAMAGES WHATSOEVER WHETHER IN AN ACTION OF CONTRACT, - * NEGLIGENCE, STRICT LIABILITY OR ANY OTHER ACTION ARISING OUT OF OR IN - * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ADOBE WILL NOT - * PROVIDE ANY TRAINING OR OTHER SUPPORT FOR THE SOFTWARE. - * - * Adobe, PostScript, and Display PostScript are trademarks of Adobe Systems - * Incorporated which may be registered in certain jurisdictions - * - * Author: Adobe Systems Incorporated - */ -/* $XFree86: xc/lib/psres/PSres.c,v 1.4tsi Exp $ */ - -#include <stdio.h> -#include <stdlib.h> - -#ifdef XENVIRONMENT -#include <X11/Xos.h> -#else -#include <string.h> -#include <sys/types.h> -#endif - -#define USE_POSIX - -#ifdef NeXT -#undef USE_POSIX -#endif /* NeXT */ - -#ifdef USE_POSIX -#include <dirent.h> -#else -#include <sys/dir.h> -#endif - -#include <sys/stat.h> -#include <DPS/PSres.h> - -#ifndef PSRES_NAME -#define PSRES_NAME "PSres.upr" -#endif /* PSRES_NAME */ - -#ifndef PSRES_EXT -#define PSRES_EXT ".upr" -#endif /* PSRES_EXT */ - -#ifndef SEEK_SET -#define SEEK_SET 0 -#endif /* SEEK_SET */ - -/* MT is the right pointer type to pass to memcpy, MST the size type */ -#define MT void * -#define MST size_t - -#define MAXLEN 256 -typedef int (*ReadContentsFunction)(); - -char *PSResFontOutline = "FontOutline", - *PSResFontPrebuilt = "FontPrebuilt", - *PSResFontAFM = "FontAFM", - *PSResFontBDF = "FontBDF", - *PSResFontFamily = "FontFamily", - *PSResFontBDFSizes = "FontBDFSizes", - *PSResForm = "Form", - *PSResPattern = "Pattern", - *PSResEncoding = "Encoding", - *PSResProcSet = "ProcSet"; - -typedef struct _ResourceNameStruct { - char *name; - char *file; -} ResourceNameStruct, *ResourceName; - -typedef struct _ResourceTypeStruct { - char *type; - long fileOffset; /* -1 means not really in the file */ - ResourceName names; - int nameCount; - int filled; /* Whether has all names or just already found names */ - char *nameBuffer; - char **oldNameBuffers; - int oldNameCount; -} ResourceTypeStruct, *ResourceType; - -typedef struct _ResourceDirectoryStruct { - char *directory; - ResourceType types; - int typeCount; - char *typeNameBuffer; - char *filePrefix; - long endOfHeader; - int exclusive; - struct _ResourceDirectoryStruct *next; -} ResourceDirectoryStruct, *ResourceDirectory; - -typedef struct { - char *type; - char *name; -} TypeName; - -typedef struct { - PSResourceEnumerator func; - char *type; - char *name; - char *private; - int done; -} EnumeratorStruct; - -static ResourceDirectory resDir = NULL, lastResDir; -static char *savedPathOverride = NULL, *savedDefaultPath = NULL; -static PSResourceSavePolicy currentPolicy = PSSaveByType; -static char **currentResourceTypes = NULL; -static char *resourceTypeBuffer = NULL; -static time_t lastModifiedTime; -static char nullStr = '\0'; - -/* Wrappers */ - -static char *mymalloc(size) - int size; -{ - char *ret; - -#ifdef XENVIRONMENT -#ifdef MALLOC_0_RETURNS_NULL - if (size < 1) size = 1; -#endif -#else - if (size < 1) size = 1; /* Better safe than sorry */ -#endif - - ret = (char *) malloc((unsigned) size); - if (ret != NULL) return ret; - (void) fprintf(stderr, "malloc failed\n"); - exit(1); - return NULL; -} - -PSResMallocProc PSResMalloc = mymalloc; -#define MALLOC (*PSResMalloc) - -static char *myrealloc(ptr, size) - char *ptr; - int size; -{ - char *ret; - -#ifdef XENVIRONMENT -#ifdef MALLOC_0_RETURNS_NULL - if (size < 1) size = 1; -#endif -#else - if (size < 1) size = 1; /* Better safe than sorry */ -#endif - - if (ptr == NULL) return MALLOC(size); -#ifdef NO_VOID_STAR - ret = (char *) realloc(ptr, (unsigned) size); -#else - ret = (char *) realloc((void *) ptr, (unsigned) size); -#endif - if (ret != NULL) return ret; - (void) fprintf(stderr, "realloc failed\n"); - exit(1); - return NULL; -} - -PSResReallocProc PSResRealloc = myrealloc; -#define REALLOC (*PSResRealloc) - -static void myfree(ptr) - char *ptr; -{ -#ifdef NO_VOID_STAR - if (ptr != NULL) free(ptr); -#else - if (ptr != NULL) free((void *) ptr); -#endif -} - -PSResFreeProc PSResFree = myfree; -#define FREE (*PSResFree) - -#define NewString(str) ((char *) strcpy(MALLOC((int) (strlen(str)+1)),(str))) - -static void FileWarningHandler(file, extraInfo) - char *file; - char *extraInfo; -{ - fprintf(stderr, - "Syntax error found in PostScript resource file %s:\n %s\n", - file, extraInfo); -} - -PSResFileWarningHandlerProc PSResFileWarningHandler = FileWarningHandler; - -/* Just like fgets, but strips trailing newline, eliminates trailing comments, - skips trailing white space, skips blank lines, and chops lines longer - than size */ - -static char *myfgets(buf, size, f) - char *buf; - register int size; - FILE *f; -{ - register int ch; - register int count = 0; - -#define STRIP_BLANKS \ - while (--count >= 0 && (buf[count] == ' ' || buf[count] == '\t')) \ - buf[count] = '\0'; -#define RETURN_BUF \ - if (buf[0] != '\0') return buf; \ - else return myfgets(buf, size, f); - - if (size == 0) return buf; - size--; - - while (count < size) { - ch = getc(f); - if (ch == EOF) { - buf[count] = '\0'; - STRIP_BLANKS; - return NULL; - } - if (ch == '\n') { - buf[count] = '\0'; - STRIP_BLANKS; - RETURN_BUF; - } - if (ch == '%') { /* Comment */ - if (count == 0 || buf[count-1] != '\\') { - buf[count] = '\0'; - do { - ch = getc(f); - } while (ch != EOF && ch != '\n'); - STRIP_BLANKS; - if (ch == EOF) return NULL; - else RETURN_BUF; - } - } - - buf[count] = ch; - count++; - } - - /* Overflow, flush */ - buf[count] = '\0'; - do { - ch = getc(f); - } while (ch != EOF && ch != '\n'); - STRIP_BLANKS; - if (ch == EOF) return NULL; - else RETURN_BUF; -#undef RETURN_BUF -#undef STRIP_BLANKS -} - -static int Dequote(buf, dontDequote) - char *buf; - char dontDequote; -{ - char *dst = buf, *src = buf; - - while (*src != '\0') { - if (*src == '\\') { - src++; - if (*src == '\0') { - *dst = '\0'; - return 1; - } else if (*src == dontDequote) *dst++ = '\\'; - } - *dst++ = *src++; - } - *dst = '\0'; - return 0; -} - -/* Sep returns the first unquoted position of the break character. The - dontDequote character only applies after the break character. If the - separator character is doubled, doubleSep is set to 1 and only one - of the separators is installed */ - -static int DequoteAndBreak(buf, sep, bchar, dontDequote, doubleSep) - char *buf; - char **sep; - char bchar; - char dontDequote; - int *doubleSep; -{ - char *dst = buf, *src = buf; - - *doubleSep = 0; - *sep = NULL; - - while (*src != '\0') { - if (*src == '\\') { - src++; - if (*src == '\0') { - *dst = '\0'; - return 1; - } else if (*src == dontDequote && *sep != NULL) *dst++ = '\\'; - } else if (*sep == NULL && *src == bchar) { - *sep = dst; - if (*(src+1) == bchar) { - src++; - *doubleSep = 1; - } - } - *dst++ = *src++; - } - *dst = '\0'; - return 0; -} - -static float ParseVersion(f, excl) - FILE *f; - int *excl; -{ - char inBuf[MAXLEN]; - float version = 0.0; - int count; - - if (myfgets(inBuf, MAXLEN, f) == NULL) return 0.0; - - /* Compare against magic value */ - - count = sscanf(inBuf, "PS-Resources-Exclusive-%f", &version); - if (count == 1) { - *excl = 1; - return version; - } - count = sscanf(inBuf, "PS-Resources-%f", &version); - if (count == 1) { - *excl = 0; - return version; - } - return 0.0; -} - -static int ParseResourceTypes(f, dir) - FILE *f; - ResourceDirectory dir; -{ - char inBuf[MAXLEN]; - char typebuf[MAXLEN]; - char *types = typebuf; - int buflen = MAXLEN, typelen = 0, len; - int count, i; - int continued = 0, precontinued = 0; - - typebuf[0] = '\0'; - count = 0; - - while (1) { - if (myfgets(inBuf, MAXLEN, f) == NULL) { - if (types != typebuf) FREE((char *) types); - return 1; - } - if (strcmp(inBuf, ".") == 0) break; - precontinued = continued; - continued = Dequote(inBuf, '\0'); - - len = strlen(inBuf); - if (typelen + len + 1 > buflen) { - if (types == typebuf) { - types = (char *) MALLOC(2*MAXLEN); - (void) memcpy((MT) types, (MT) typebuf, (MST) typelen); - } else types = REALLOC(types, buflen+MAXLEN); - buflen += MAXLEN; - } - - if (precontinued) typelen--; /* Write over previous \0 */ - else count++; - (void) strncpy(&types[typelen], inBuf, len+1); - typelen += len+1; - } - - dir->typeCount = count; - if (count == 0) dir->types = NULL; - else { - dir->types = (ResourceType) - MALLOC((int) (count * sizeof(ResourceTypeStruct))); - dir->typeNameBuffer = (char *) MALLOC(typelen); - (void) memcpy((MT) dir->typeNameBuffer, (MT) types, (MST) typelen); - } - - len = 0; - for (i = 0; i < count; i++) { - dir->types[i].type = &(dir->typeNameBuffer[len]); - dir->types[i].fileOffset = 0; - dir->types[i].names = NULL; - dir->types[i].nameBuffer = NULL; - dir->types[i].filled = 0; - dir->types[i].oldNameBuffers = NULL; - dir->types[i].oldNameCount = 0; - dir->types[i].nameCount = 0; - len += strlen(dir->types[i].type) + 1; - } - - if (types != typebuf) FREE((char *) types); - return 0; -} - -static int ParseFilePrefix(f, dir, dirName) - FILE *f; - ResourceDirectory dir; - char *dirName; -{ - char inBuf[MAXLEN]; - int continued; - int len; - long savePos; - char *prefix; - - dir->filePrefix = NULL; - - savePos = ftell(f); - if (myfgets(inBuf, MAXLEN, f) == NULL) return 1; - - if (inBuf[0] != '/') { - if (fseek(f, savePos, SEEK_SET) == -1) return 1; - len = strlen(dirName); - dir->filePrefix = strcpy((char *) MALLOC(len+2), dirName); - dir->filePrefix[len] = '/'; - dir->filePrefix[len+1] = '\0'; - return 0; - } - - continued = Dequote(inBuf, '\0'); - prefix = inBuf+1; - len = strlen(prefix); - dir->filePrefix = (char *) strcpy((char *) MALLOC(len+2), prefix); - if (!continued) { - dir->filePrefix[len] = '/'; - dir->filePrefix[len+1] = '\0'; - return 0; - } - - while (1) { - if (myfgets(inBuf, MAXLEN, f) == NULL) return 1; - continued = Dequote(inBuf, '\0'); - len += strlen(inBuf); - dir->filePrefix = (char *) REALLOC(dir->filePrefix, len+2); - (void) strcat(dir->filePrefix, inBuf); - if (!continued) { - dir->filePrefix[len] = '/'; - dir->filePrefix[len+1] = '\0'; - return 0; - } - } -} - -static ResourceDirectory ParseHeader(f, dirName, fileName) - FILE *f; - char *dirName, *fileName; -{ - ResourceDirectory dir; - float version; - int exclusive; - - rewind(f); - - version = ParseVersion(f, &exclusive); - if (version < 1.0) return NULL; - - dir = (ResourceDirectory) MALLOC(sizeof(ResourceDirectoryStruct)); - dir->directory = (char *) NewString(fileName); - dir->exclusive = exclusive; - dir->next = NULL; - - if (ParseResourceTypes(f, dir)) { - FREE((char *) dir->directory); - FREE((char *) dir); - return NULL; - } - - if (ParseFilePrefix(f, dir, dirName)) dir->endOfHeader = 0; - else dir->endOfHeader = ftell(f); - - return dir; -} - -/* Store away old name buffer so pointers to it do not become invalid */ - -static void CacheOldNames(type) - ResourceType type; -{ - type->oldNameCount++; - type->oldNameBuffers = (char **) REALLOC((char *) type->oldNameBuffers, - type->oldNameCount); - type->oldNameBuffers[type->oldNameCount-1] = type->nameBuffer; - type->nameBuffer = NULL; -} - -/* Verify that the name matches the name in the file */ - -static int VerifyName(f, name) - FILE *f; - char *name; -{ - char inBuf[MAXLEN]; - int continued = 0; - int len; - int start = 0; - - while (1) { - if (myfgets(inBuf, MAXLEN, f) == NULL) return 1; - continued = Dequote(inBuf, '\0'); - if (continued) { - len = strlen(inBuf); - if (strncmp(inBuf, &name[start], len) != 0) return 1; - start += len; - } else { - if (strcmp(inBuf, &name[start]) != 0) return 1; - else break; - } - } - return 0; -} - -static int LookupResourceInList(type, name) - ResourceType type; - char *name; -{ - int i; - - for (i = 0; i < type->nameCount; i++) { - if (strcmp(name, type->names[i].name) == 0) return 1; - } - return 0; -} - -static int CheckInsertPrefix(type) - char *type; -{ - /* Insert the prefix unless one of these special values */ - - if (strcmp(type, PSResFontFamily) == 0 || - strcmp(type, PSResFontBDFSizes) == 0 || - strcmp(type, "FontAxes") == 0 || - strcmp(type, "FontBlendMap") == 0 || - strcmp(type, "FontBlendPositions") == 0 || - strcmp(type, "mkpsresPrivate") == 0) return 0; - return 1; -} - -/* Returns a line, including continuations. Memory must be copied before - calling this again. */ - -static int linebuflen = 0; -static char *inputline = NULL; - -static char *ReadFullLine(f) - FILE *f; -{ - char readbuf[MAXLEN]; - int start = 0; - int len; - - while (1) { - if (myfgets(readbuf, MAXLEN, f) == NULL) return NULL; - len = strlen(readbuf); - if (start + len + 1 > linebuflen) { - linebuflen += MAXLEN + 1; - inputline = REALLOC(inputline, linebuflen); - } - strncpy(inputline+start, readbuf, len+1); - - if (inputline[start+len-1] != '\\') break; - - start = start+len-1; - } - return inputline; -} - -static void FreeLineBuf() -{ - if (inputline != NULL) FREE(inputline); - inputline = NULL; - linebuflen = 0; -} - -/* Assumes being correctly positioned in the file */ - -static int ReadResourceSection(f, dir, type, name) - FILE *f; - ResourceDirectory dir; - ResourceType type; - char *name; /* If NULL, enumerate */ -{ -#define GROW 1000 - char *linein; - int start; - int len; - char namebuf[GROW]; - char *names = namebuf; - int buflen = GROW, namelen = 0; - int i, count = 0; - char *sep; - int prefixLen; - int insertPrefix; - char dontDequote; - int doubleEquals; - int addingPrefix; - int newsize; - - if (type->nameBuffer != NULL) CacheOldNames(type); - - insertPrefix = CheckInsertPrefix(type->type); - if (insertPrefix) { - prefixLen = strlen(dir->filePrefix); - dontDequote = '\0'; - } else { - prefixLen = 0; - dontDequote = ','; - } - - while (1) { - start = namelen; - - linein = ReadFullLine(f); - if (linein == NULL) { - if (names != namebuf) FREE((char *) names); - FreeLineBuf(); - return 1; - } - if (strcmp(linein, ".") == 0) break; - - sep = NULL; - (void) DequoteAndBreak(linein, &sep, '=', dontDequote, &doubleEquals); - - /* If no separator, a bogus line */ - if (sep == NULL) continue; - - /* Next line is UNIX specific! */ - addingPrefix = *(sep+1) != '/' && insertPrefix && !doubleEquals; - - len = strlen(linein) + 1 + (addingPrefix ? prefixLen : 0); - - if (namelen + len >= buflen) { - newsize = buflen + GROW; - if (namelen + len > newsize) newsize = namelen + len; - - if (names == namebuf) { - names = (char *) MALLOC(newsize); - (void) memcpy((MT) names, (MT) namebuf, (MST) namelen); - } else names = REALLOC(names, newsize); - buflen = newsize; - } - - *sep = '\0'; - len = strlen(linein); - (void) strncpy(&names[namelen], linein, len+1); - namelen += len+1; - - if (addingPrefix) { - (void) strncpy(&names[namelen], dir->filePrefix, prefixLen); - namelen += prefixLen; - } - - len = strlen(sep+1); - (void) strncpy(&names[namelen], sep+1, len+1); - namelen += len+1; - - if (name != NULL && strcmp(names, name) != 0) namelen = start; - else count++; - } - - type->nameCount = count; - if (count == 0) type->names = NULL; - else { - type->names = (ResourceName) - MALLOC((int) (count * sizeof(ResourceNameStruct))); - type->nameBuffer = (char *) MALLOC(namelen); - (void) memcpy((MT) type->nameBuffer, (MT) names, (MST) namelen); - } - - len = 0; - for (i = 0; i < count; i++) { - type->names[i].name = &(type->nameBuffer[len]); - len += strlen(type->names[i].name) + 1; - type->names[i].file = &(type->nameBuffer[len]); - len += strlen(type->names[i].file) + 1; - } - - if (names != namebuf) FREE((char *) names); - if (name == NULL) type->filled = 1; - FreeLineBuf(); - return 0; - -#undef GROW -} - -/* Assumes being correctly positioned in the file */ - -static int SkipResourceSection(f, dir, type, checkName) - FILE *f; - ResourceDirectory dir; - ResourceType type; - int checkName; -{ - char inBuf[MAXLEN]; - int i; - - /* If next type has offset, just go there */ - - for (i = 0; i < dir->typeCount && dir->types + i != type; i++) {} - - if (dir->types + i == type) { - for (i++; i < dir->typeCount; i++) { - if (dir->types[i].fileOffset == -1) continue; - if (dir->types[i].fileOffset > 0) { - if (fseek(f, dir->types[i].fileOffset, SEEK_SET) != -1) { - return 0; - } else break; - } - } - } - - if (checkName && VerifyName(f, type->type) != 0) return 1; - - while (1) { - if (myfgets(inBuf, MAXLEN, f) == NULL) return 1; - if (strcmp(inBuf, ".") == 0) return 0; - } -} - -/* Assumes being correctly positioned in the file */ - -static int ParseResourceSection(f, dir, type, name, checkName) - FILE *f; - ResourceDirectory dir; - ResourceType type; - char *name; /* If NULL, enumerate */ - int checkName; -{ - if (checkName && VerifyName(f, type->type) != 0) return 1; - - if (type->filled || (name != NULL && LookupResourceInList(type, name))) { - return SkipResourceSection(f, dir, type, 0); - } - - return ReadResourceSection(f, dir, type, name); -} - -void FreePSResourceStorage(everything) - int everything; -{ - ResourceDirectory d; - ResourceType t; - int i, j; - - if (resDir == NULL) return; - - for (d = resDir; d != NULL; d = d->next) { - for (i = 0; i < d->typeCount; i++) { - t = d->types + i; - FREE(t->nameBuffer); - FREE((char *) t->names); - t->nameCount = 0; - for (j = 0; j < t->oldNameCount; j++) FREE(t->oldNameBuffers[j]); - if (t->oldNameBuffers != NULL) FREE((char *) t->oldNameBuffers); - t->oldNameCount = 0; - t->nameCount = 0; - t->filled = 0; - } - } - - if (!everything) return; - - while (resDir != NULL) { - d = resDir->next; - FREE(resDir->directory); - FREE((char *) resDir->types); - FREE(resDir->typeNameBuffer); - FREE(resDir->filePrefix); - FREE((char *) resDir); - resDir = d; - } - lastResDir = NULL; - FREE(savedPathOverride); - savedPathOverride = NULL; - FREE(savedDefaultPath); - savedDefaultPath = NULL; -} - -static ResourceDirectory ReadAndStoreFile(dir, name, len, readFunc, data) - char *dir, *name; - int len; - ReadContentsFunction readFunc; - char *data; -{ - ResourceDirectory rd = NULL; - FILE *f; - char nameBuf[MAXLEN]; - char *fullName = nameBuf; - int fullLen; - - fullLen = len + strlen(name) + 1; - if (fullLen >= MAXLEN) fullName = MALLOC(fullLen+1); - (void) strcpy(fullName, dir); - fullName[len] = '/'; - (void) strcpy(fullName+len+1, name); - - f = fopen(fullName, "r"); - if (f != NULL) { - rd = ParseHeader(f, dir, fullName); - - if (rd != NULL) { - if (resDir == NULL) resDir = rd; - else lastResDir->next = rd; - lastResDir = rd; - if (readFunc != NULL) (*readFunc) (f, rd, data); - } else (*PSResFileWarningHandler)(fullName, "Malformed header"); - (void) fclose(f); - } - if (fullName != nameBuf) FREE(fullName); - return rd; -} - -static time_t ReadFilesInDirectory(dirName, readFunc, data) - char *dirName; - ReadContentsFunction readFunc; - char *data; -{ - DIR *dir; -#ifdef USE_POSIX - struct dirent *d; -#else - struct direct *d; -#endif - ResourceDirectory rd; - int len = strlen(dirName); - static int extensionLen = 0; - struct stat buf; - int namelen; - - if (extensionLen == 0) extensionLen = strlen(PSRES_EXT); - if (stat(dirName, &buf) != 0) buf.st_mtime = 0; - - rd = ReadAndStoreFile(dirName, PSRES_NAME, len, readFunc, data); - - if (rd != 0 && rd->exclusive) return buf.st_mtime; - - dir = opendir(dirName); - if (dir == NULL) return buf.st_mtime; - - while ((d = readdir(dir)) != NULL) { - namelen = strlen(d->d_name); - if (namelen < extensionLen) continue; - - if (strcmp(d->d_name + (namelen - extensionLen), PSRES_EXT) == 0 - && strcmp(d->d_name, PSRES_NAME) != 0) { - (void) ReadAndStoreFile(dirName, d->d_name, len, readFunc, data); - } - } - (void) closedir(dir); - return buf.st_mtime; -} - -/* Returns nonzero if current paths different from saved ones */ - -static int SetUpSavedPaths(pathOverride, defaultPath) - char *pathOverride; - char *defaultPath; -{ - if (pathOverride == NULL) pathOverride = &nullStr; - if (defaultPath == NULL) defaultPath = &nullStr; - - if (savedPathOverride == NULL || - strcmp(pathOverride, savedPathOverride) != 0 || - strcmp(defaultPath, savedDefaultPath) != 0) { - - FreePSResourceStorage(1); - - savedPathOverride = NewString(pathOverride); - savedDefaultPath = NewString(defaultPath); - - return 1; - } - return 0; -} - -/* Like SetUpSavedPaths, but never affects saved state */ - -static int CheckSavedPaths(pathOverride, defaultPath) - char *pathOverride; - char *defaultPath; -{ - if (pathOverride == NULL) pathOverride = &nullStr; - if (defaultPath == NULL) defaultPath = &nullStr; - - if (savedPathOverride == NULL || - strcmp(pathOverride, savedPathOverride) != 0 || - strcmp(defaultPath, savedDefaultPath) != 0) return 1; - else return 0; -} - -static time_t ReadFilesInPath(string, readFunc, data) - char *string; - ReadContentsFunction readFunc; - char *data; -{ - char *pathChar; - char pathBuf[MAXLEN]; - char *path; - register char *dir; - int len; - register char ch; - time_t newTime, latestTime = 0; - - pathChar = string; - - if (*pathChar == ':') pathChar++; - - len = strlen(pathChar); - if (len < MAXLEN) path = pathBuf; - else path = MALLOC(len+1); - - do { - dir = path; - do { - while (*pathChar == '\\') { - pathChar++; - if (*pathChar != '\0') *dir++ = *pathChar++; - } - - *dir++ = ch = *pathChar++; - } while (ch != '\0' && ch != ':'); - if (ch == ':') *(dir-1) = '\0'; - - if (*path == '\0') { - if (ch == ':' && string != savedDefaultPath) { - newTime = ReadFilesInPath(savedDefaultPath, readFunc, data); - if (newTime > latestTime) latestTime = newTime; - } - } else { - newTime = ReadFilesInDirectory(path, readFunc, data); - if (newTime > latestTime) latestTime = newTime; - } - } while (ch == ':'); - if (path != pathBuf) FREE(path); - return latestTime; -} - -static time_t MaxTimeInPath(string) - char *string; -{ - char *pathChar; - char pathBuf[MAXLEN]; - char *path; - register char *dir; - int len; - register char ch; - time_t latestTime = 0; - struct stat buf; - - pathChar = string; - - if (*pathChar == ':') pathChar++; - - len = strlen(pathChar); - if (len < MAXLEN) path = pathBuf; - else path = MALLOC(len+1); - - do { - dir = path; - do { - while (*pathChar == '\\') { - pathChar++; - if (*pathChar != '\0') *dir++ = *pathChar++; - } - - *dir++ = ch = *pathChar++; - } while (ch != '\0' && ch != ':'); - if (ch == ':') *(dir-1) = '\0'; - - if (*path == '\0') { - if (ch == ':' && string != savedDefaultPath) { - buf.st_mtime = MaxTimeInPath(savedDefaultPath); - if (buf.st_mtime > latestTime) latestTime = buf.st_mtime; - } - } else { - if (stat(path, &buf) != 0) buf.st_mtime = 0; - if (buf.st_mtime > latestTime) latestTime = buf.st_mtime; - } - } while (ch == ':'); - if (path != pathBuf) FREE(path); - return latestTime; -} - -static char *GetPath() -{ - static char defaultEnvironmentPath[] = "::"; - static char *environmentPath = NULL; - - if (savedPathOverride != NULL && *savedPathOverride != '\0') { - return savedPathOverride; - } - - if (environmentPath == NULL) { - environmentPath = getenv("PSRESOURCEPATH"); - if (environmentPath == NULL) environmentPath = defaultEnvironmentPath; - } - - return environmentPath; -} - -void SetPSResourcePolicy(policy, willList, resourceTypes) - PSResourceSavePolicy policy; - int willList; - char **resourceTypes; -{ - currentPolicy = policy; - - if (currentResourceTypes != NULL) FREE((char *) currentResourceTypes); - if (resourceTypeBuffer != NULL) FREE((char *) resourceTypeBuffer); - - if (resourceTypes == NULL) { - currentResourceTypes = NULL; - resourceTypeBuffer = NULL; - } else { - int i = 0, len = 0; - char **cp = resourceTypes; - - while (*cp != NULL) { - i++; - len += strlen(*cp) + 1; - cp++; - } - - currentResourceTypes = - (char **) MALLOC((int) ((i+1) * sizeof(char *))); - resourceTypeBuffer = MALLOC(len); - - len = 0; - i = 0; - cp = resourceTypes; - - while (*cp != NULL) { - (void) strcpy(resourceTypeBuffer+len, *cp); - currentResourceTypes[i++] = resourceTypeBuffer + len; - len += strlen(*cp) + 1; - cp++; - } - currentResourceTypes[i] = NULL; - } -} - -int InSavedList(type) - char *type; -{ - char **cp = currentResourceTypes;; - - if (cp == NULL) return 0; - - while (*cp != NULL) { - if (strcmp(*cp++, type) == 0) return 1; - } - return 0; -} - -/* ARGSUSED */ -static int ReadEverything(f, rd, data) - FILE *f; - ResourceDirectory rd; - char *data; -{ - int i; - ResourceType t; - long pos; - - /* We're at the start of the resource section; read all of them */ - - for (i = 0; i < rd->typeCount; i++) { - t = &rd->types[i]; - - if (t->fileOffset == -1) continue; /* Not really there */ - - if (t->fileOffset != 0 && fseek(f, t->fileOffset, SEEK_SET) != -1) { - if (!t->filled) { - if (ParseResourceSection(f, rd, t, (char *) NULL, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else { - if (SkipResourceSection(f, rd, t, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } - continue; - } - - pos = ftell(f); - if (VerifyName(f, t->type) == 0) { - t->fileOffset = pos; - if (ParseResourceSection(f, rd, t, (char *) NULL, 0)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else { - /* No resources of this type; try the next type */ - t->fileOffset = -1; - if (fseek(f, pos, SEEK_SET)) { - PSResFileWarningHandler(rd->directory, - "File changed during execution"); - return 1; - } - } - } - return 0; -} - -static int ReadType(f, rd, type) - FILE *f; - ResourceDirectory rd; - char *type; -{ - int i; - ResourceType t; - long pos; - - /* We're at the start of the resource section; read the sections that - are in the cached type list or are the passed in type */ - - for (i = 0; i < rd->typeCount; i++) { - t = &rd->types[i]; - - if (t->fileOffset == -1) continue; /* Not really there */ - if (t->fileOffset != 0 && fseek(f, t->fileOffset, SEEK_SET) != -1) { - if (!t->filled && - (strcmp(t->type, type) == 0 || InSavedList(t->type))) { - if (ParseResourceSection(f, rd, t, (char *) NULL, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else if (SkipResourceSection(f, rd, t, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - continue; - } - - pos = ftell(f); - if (VerifyName(f, t->type) == 0) { - t->fileOffset = pos; - if (strcmp(t->type, type) == 0 || InSavedList(t->type)) { - if (ParseResourceSection(f, rd, t, (char *) NULL, 0)){ - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else if (SkipResourceSection(f, rd, t, 0)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else { - /* No resources of this type; try the next type */ - t->fileOffset = -1; - if (fseek(f, pos, SEEK_SET) == -1) { - PSResFileWarningHandler(rd->directory, - "File changed during execution"); - return 1; - } - } - } - return 0; -} - -static int ReadName(f, rd, data) - FILE *f; - ResourceDirectory rd; - char *data; -{ - TypeName *tn = (TypeName *) data; - int i; - ResourceType t; - long pos; - - /* We're at the start of the resource section; read the name in the - section for the passed in type */ - - for (i = 0; i < rd->typeCount; i++) { - t = &rd->types[i]; - - if (t->fileOffset == -1) continue; /* Not really there */ - if (t->fileOffset != 0 && fseek(f, t->fileOffset, SEEK_SET)) { - if (strcmp(t->type, tn->type) == 0) { - if (ParseResourceSection(f, rd, t, tn->name, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else if (SkipResourceSection(f, rd, t, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - continue; - } - - pos = ftell(f); - if (VerifyName(f, t->type) == 0) { - t->fileOffset = pos; - if (fseek(f, pos, SEEK_SET) == -1) { - PSResFileWarningHandler(rd->directory, - "File changed during execution"); - return 1; - } - if (strcmp(t->type, tn->type) == 0) { - if (ParseResourceSection(f, rd, t, tn->name, 0)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else if (SkipResourceSection(f, rd, t, 0)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - } else { - /* No resources of this type; try the next type */ - t->fileOffset = -1; - if (fseek(f, pos, SEEK_SET) == -1) { - PSResFileWarningHandler(rd->directory, - "File changed during execution"); - return 1; - } - } - } - return 0; -} - -static void ReadHeadersAndData(resourceType, resourceName) - char *resourceType; - char *resourceName; -{ - TypeName t; - - switch (currentPolicy) { - case PSSaveEverything: - lastModifiedTime = - ReadFilesInPath(GetPath(), ReadEverything, (char *) NULL); - break; - case PSSaveByType: - lastModifiedTime = - ReadFilesInPath(GetPath(), ReadType, resourceType); - break; - case PSSaveReturnValues: - t.type = resourceType; - t.name = resourceName; - lastModifiedTime = - ReadFilesInPath(GetPath(), ReadName, (char *) &t); - break; - } -} - -static void UpdateData(resourceType, resourceName) - char *resourceType; - char *resourceName; -{ - ResourceDirectory rd; - ResourceType rt; - int i; - FILE *f; - TypeName tn; - - /* Make two passes; the first figures out if we're going to have to read - the file to service this request. If we are, open the file and read - in sections in the saved list (from SetPSResourcePolicy). If not - just saving return values, make sure we read in everything - in the section. */ - - for (rd = resDir; rd != NULL; rd = rd->next) { - f = NULL; - for (i = 0; i < rd->typeCount; i++) { - rt = rd->types + i; - if (rt->filled) continue; - if (strcmp(rt->type, resourceType) != 0) continue; - - if (resourceName != NULL && - LookupResourceInList(rt, resourceName)) continue; - - f = fopen(rd->directory, "r"); - break; - } - if (f == NULL) continue; - - /* Nuts, have to read the file */ - - if (fseek(f, rd->endOfHeader, SEEK_SET) != -1) { - switch (currentPolicy) { - case PSSaveEverything: - (void) ReadEverything(f, rd, (char *) NULL); - break; - case PSSaveByType: - (void) ReadType(f, rd, resourceType); - break; - case PSSaveReturnValues: - tn.type = resourceType; - tn.name = resourceName; - (void) ReadName(f, rd, (char *) &tn); - break; - } - } else (*PSResFileWarningHandler)(rd->directory, - "File changed during execution"); - (void) fclose(f); - } -} - -static int FindData(resourceType, resourceName, - resourceNamesReturn, resourceFilesReturn) - char *resourceType; - char *resourceName; - char ***resourceNamesReturn; - char ***resourceFilesReturn; -{ - ResourceDirectory rd; - ResourceType rt; - int i, j, k; - int nameCount = 0; - char **names, **files; - - /* Make two passes; first count, then set and return */ - - for (rd = resDir; rd != NULL; rd = rd->next) { - for (i = 0; i < rd->typeCount; i++) { - rt = rd->types + i; - if (strcmp(rt->type, resourceType) != 0) continue; - if (resourceName == NULL) nameCount += rt->nameCount; - else { - for (j = 0; j < rt->nameCount; j++) { - if (strcmp(rt->names[j].name, resourceName) == 0) { - nameCount++; - } - } - } - } - } - - if (nameCount == 0) return 0; - - names = (char **) MALLOC((int) (nameCount * sizeof(char *))); - files = (char **) MALLOC((int) (nameCount * sizeof(char *))); - k = 0; - - for (rd = resDir; rd != NULL; rd = rd->next) { - for (i = 0; i < rd->typeCount; i++) { - rt = rd->types + i; - if (strcmp(rt->type, resourceType) != 0) continue; - for (j = 0; j < rt->nameCount; j++) { - if (resourceName == NULL || - strcmp(rt->names[j].name, resourceName) == 0) { - names[k] = rt->names[j].name; - files[k++] = rt->names[j].file; - } - } - } - } - - *resourceNamesReturn = names; - *resourceFilesReturn = files; - return nameCount; -} - -extern int ListPSResourceFiles(psResourcePathOverride, defaultPath, - resourceType, resourceName, - resourceNamesReturn, resourceFilesReturn) - char *psResourcePathOverride; - char *defaultPath; - char *resourceType; - char *resourceName; - char ***resourceNamesReturn; - char ***resourceFilesReturn; -{ - if (SetUpSavedPaths(psResourcePathOverride, defaultPath)) { - ReadHeadersAndData(resourceType, resourceName); - } else UpdateData(resourceType, resourceName); - return FindData(resourceType, resourceName, - resourceNamesReturn, resourceFilesReturn); -} - -int ListPSResourceTypes(pathOverride, defaultPath, typesReturn) - char *pathOverride; - char *defaultPath; - char ***typesReturn; -{ -#define GROW 5 -#define START 15 - int typeCount = 0, i, j, typeBufSize = 0; - ResourceDirectory d; - register char **types = NULL; - int sig; - int *sigs = NULL; - char *ch; - - if (SetUpSavedPaths(pathOverride, defaultPath)) { - if (currentPolicy != PSSaveEverything) { - lastModifiedTime = - ReadFilesInPath(GetPath(), (ReadContentsFunction) NULL, - (char *) NULL); - } else lastModifiedTime = - ReadFilesInPath(GetPath(), ReadEverything, (char *) NULL); - } - - for (d = resDir; d != NULL; d = d->next) { - for (i = 0; i < d->typeCount; i++) { - for (sig = 0, ch = d->types[i].type; *ch != '\0'; sig += *ch++) {} - for (j = 0; j < typeCount; j++) { - if (sig == sigs[j] && - strcmp(types[j], d->types[i].type) == 0) break; - } - if (j >= typeCount) { /* Have to add */ - if (typeCount >= typeBufSize) { - if (typeCount == 0) typeBufSize = START; - else typeBufSize += GROW; - types = (char **) REALLOC((char *) types, - typeBufSize * sizeof(char *)); - sigs = (int *) REALLOC((char *) sigs, - typeBufSize * sizeof(int)); - } - types[typeCount] = d->types[i].type; - sigs[typeCount++] = sig; - } - } - } - - FREE((char *) sigs); - *typesReturn = types; - return typeCount; -#undef START -#undef GROW -} - -/* Assumes being correctly positioned in the file */ - -static int EnumerateResourceSection(f, dir, type, s, checkName) - FILE *f; - ResourceDirectory dir; - ResourceType type; - EnumeratorStruct *s; - int checkName; -{ -#define GROW 1000 - char *linein; - int len; - char namebuf[GROW]; - char *names = namebuf; - int buflen = GROW, namelen = 0; - char *sep; - int prefixLen; - int insertPrefix; - char *file; - char dontDequote; - int doubleEquals; - int addingPrefix; - - if (checkName && VerifyName(f, type->type) != 0) return 1; - - insertPrefix = CheckInsertPrefix(type->type); - if (insertPrefix) { - prefixLen = strlen(dir->filePrefix); - dontDequote = '\0'; - } else { - prefixLen = 0; - dontDequote = ','; - } - - while (1) { - linein = ReadFullLine(f); - if (linein == NULL) { - if (names != namebuf) FREE((char *) names); - FreeLineBuf(); - return 1; - } - - if (strcmp(linein, ".") == 0) { - if (names != namebuf) FREE((char *) names); - FreeLineBuf(); - return 0; - } - - sep = NULL; - (void) DequoteAndBreak(linein, &sep, '=', dontDequote, &doubleEquals); - - /* If no separator, a bogus line */ - if (sep == NULL) continue; - - /* Next line is UNIX specific! */ - addingPrefix = *(sep+1) != '/' && insertPrefix && !doubleEquals; - - len = strlen(linein) + (addingPrefix ? 0 : prefixLen) + 1; - if (len > buflen) { - if (names != namebuf) FREE((char *) names); - names = (char *) MALLOC(len); - } - - *sep = '\0'; - len = strlen(linein); - (void) strncpy(names, linein, len+1); - - namelen = len+1; - file = &names[namelen]; - - if (addingPrefix) { - (void) strncpy(&names[namelen], dir->filePrefix, prefixLen); - namelen += prefixLen; - } - - len = strlen(sep+1); - (void) strncpy(&names[namelen], sep+1, len+1); - - if (s->name == NULL || strcmp(names, s->name) == 0) { - s->done = (*s->func) (s->type, names, file, s->private); - if (s->done) { - if (names != namebuf) FREE((char *) names); - FreeLineBuf(); - return 0; - } - } - } -#undef GROW -} - -static int Enumerate(f, rd, data) - FILE *f; - ResourceDirectory rd; - char *data; -{ - EnumeratorStruct *s = (EnumeratorStruct *) data; - int i; - ResourceType t; - long pos; - - if (s->done) return 0; - - for (i = 0; i < rd->typeCount; i++) { - t = &rd->types[i]; - - if (t->fileOffset == -1) continue; /* Not really there */ - if (t->fileOffset != 0 && fseek(f, t->fileOffset, SEEK_SET) != -1) { - if (strcmp(t->type, s->type) == 0) { - if (EnumerateResourceSection(f, rd, t, s, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - if (s->done) return 0;; - } else if (SkipResourceSection(f, rd, t, 1)) { - char buf[256]; - sprintf(buf, "Trouble parsing resource type %s", t->type); - PSResFileWarningHandler(rd->directory, buf); - return 1; - } - continue; - } - - pos = ftell(f); - if (VerifyName(f, t->type) == 0) { - t->fileOffset = pos; - if (strcmp(t->type, s->type) == 0) { - if (EnumerateResourceSection(f, rd, t, s, 0)) return 1; - if (s->done) return 0; - } else if (SkipResourceSection(f, rd, t, 0)) return 1; - } else { - /* No resources of this type; try the next type */ - t->fileOffset = -1; - if (fseek(f, pos, SEEK_SET) == -1) return 1; - } - } - return 0; -} - -void EnumeratePSResourceFiles(pathOverride, defaultPath, resourceType, - resourceName, enumerator, private) - char *pathOverride; - char *defaultPath; - char *resourceType; - char *resourceName; - PSResourceEnumerator enumerator; - char *private; -{ - ResourceDirectory d; - FILE *f; - EnumeratorStruct s; - - s.func = enumerator; - s.type = resourceType; - s.name = resourceName; - s.private = private; - s.done = 0; - - if (SetUpSavedPaths(pathOverride, defaultPath)) { - lastModifiedTime = - ReadFilesInPath(GetPath(), Enumerate, (char *) &s); - return; - } - - for (d = resDir; d != NULL && !s.done; d = d->next) { - f = fopen(d->directory, "r"); - if (f == NULL) continue; - if (fseek(f, d->endOfHeader, SEEK_SET) != -1) { - (void) Enumerate(f, d, (char *) &s); - } - (void) fclose(f); - } -} - -int CheckPSResourceTime(pathOverride, defaultPath) - char *pathOverride; - char *defaultPath; -{ - if (CheckSavedPaths(pathOverride, defaultPath)) return 1; - return MaxTimeInPath(GetPath()) > lastModifiedTime; -} |