/* $Id: webstr.c,v 1.10 2005/03/11 15:58:58 starfish Exp $ */ #include "webstr.h" #include #include #include /*********************************************************************/ void web_ReplaceOutput(char *string, char escape, struct web_replace_t *table, unsigned int tableSize, void (*write)(const char *str, size_t size, void *file), void *file, void *userdata) { unsigned int lastptr, strptr, varptr; struct web_replace_t *item; char buf[32]; if (string == NULL) return; /* loop for the input string */ for (lastptr=strptr=0; string[strptr]!='\0'; ++strptr) { /* check whether it is a variable to replace */ while (string[strptr] == escape) { ++strptr; if (string[strptr] != '\0') { /* linear search the variable in the table */ for (varptr=0; ; ++varptr) { if (varptr >= tableSize) { /* exit the loop if variable is not defined */ /* write the string before the variable */ if (strptr > lastptr+1) { write(string+lastptr, strptr-lastptr-1, file); } /* write the unmatched character */ write(string+strptr, 1, file); /* set pointers for next scan */ ++strptr; lastptr = strptr; break; } item = table + varptr; if (item->variable == string[strptr]) { /* write the string before the variable */ if (strptr > lastptr+1) { write(string+lastptr, strptr-lastptr-1, file); } /* output the value of the variable */ switch (item->type) { case web_replace_STRING: write(item->value_ptr, strlen(item->value_ptr), file); break; case web_replace_UINT: snprintf(buf, sizeof buf, "%u", *(unsigned int *)item->value_ptr); write(buf, strlen(buf), file); break; case web_replace_SINT: snprintf(buf, sizeof buf, "%i", *(unsigned int *)item->value_ptr); write(buf, strlen(buf), file); break; case web_replace_FUNCTION: ((void (*)(void *, void *))item->value_ptr)( file, userdata); break; } ++strptr; lastptr = strptr; break; } } } } } /* output the remaining string */ if (strptr != lastptr) { write(string+lastptr, strptr-lastptr, file); } } /*********************************************************************/ /* Read a line of string from a file. The string returned from this function should be deallocated by free(). */ static char * readline(FILE *fd) { const unsigned int d_len = 128; unsigned int len; char *buf, *buf2; buf = NULL; len = 0; do { buf2 = realloc(buf, len + d_len + 1); if (buf2 == NULL) { free(buf); return NULL; } buf = buf2; buf[len+d_len-1] = '\n'; /* for condition of the do-while loop */ if (fgets(buf+len, d_len+1, fd) == NULL) { buf[len] = 0; return buf; } len += d_len; } while (buf[len] == '\0' && buf[len-1] != '\n'); /* remove the newline character at the tail */ buf2 = buf+len-d_len + strlen(buf+len-d_len) - 1; if (*buf2 == '\n') *buf2 = '\0'; return buf; } /* Read lines of string from a file, until a empty line is read. The string returned from this function should be deallocated by free(). */ static char * readblock(FILE *fd) { const unsigned int d_len = 256; unsigned int len; char *buf, *buf2; buf = NULL; len = 0; for (;;) { buf2 = realloc(buf, len + d_len + 1); if (buf2 == NULL) { free(buf); return NULL; } buf = buf2; if (fgets(buf+len, d_len+1, fd) == NULL) { buf[len] = 0; return buf; } if (buf[len] == '\n') { /* an empty is read */ break; } len += strlen(buf+len); } return buf; } int web_readfile(char const *filename, void *dest, struct web_strfile_t const *items, size_t numItems) { FILE *fd; char *name, *block; int i; fd = fopen(filename, "r"); if (fd == NULL) { /* cannot open the file */ return 1; } while (!feof(fd)) { name = readline(fd); if (name == NULL) return 2; block = readblock(fd); if (block == NULL) { free(name); return 3; } for (i=0; i