G:/ScriptBasic/source/variations/winisapi/winisapi.c

Go to the documentation of this file.
00001 #include <stdio.h>
00002 #include <stdlib.h>
00003 #include <string.h>
00004 #include <windows.h>
00005 #include <time.h>
00006 #include <httpext.h>
00007 #include <process.h>
00008 
00009 #include "../../report.h"
00010 #include "../../lexer.h"
00011 #include "../../sym.h"
00012 #include "../../expression.h"
00013 #include "../../syntax.h"
00014 #include "../../reader.h"
00015 #include "../../myalloc.h"
00016 #include "../../builder.h"
00017 #include "../../memory.h"
00018 #include "../../execute.h"
00019 #include "../../buildnum.h"
00020 #include "../../conftree.h"
00021 #include "../../filesys.h"
00022 #include "../../errcodes.h"
00023 #include "../../epreproc.h"
00024 #include "../../uniqfnam.h"
00025 
00026 /*
00027 ScriptBasic execution may have pointers to the standard input and
00028 standard output functions. The print command uses the standard
00029 output function pointer unless it is NUL. Here we implement a very
00030 simple function that can be used as standard output function when
00031 running under ISAPI. This function uses the ISAPI interface function
00032 WriteClient in a very inefficient mode sending characters by character,
00033 but the output is buffered anyway.
00034 
00035 The function has two arguments. The first is the character to send to
00036 the standard output. The second argument is the embedder pointer. This
00037 pointer in this case is the ISAPI extension control block pointer.
00038 */
00039 static void IsapiStdOutFunction(char Character, LPEXTENSION_CONTROL_BLOCK lpECB){
00040   static DWORD dwBytes = 1;
00041   lpECB->WriteClient(lpECB->ConnID,&Character,&dwBytes,HSE_IO_SYNC);
00042   }
00043 
00044 /*
00045  Configuration data is read only once, when the first basic program is executed.
00046  This makes execution faster. You have to restart the web server for any
00047  configuration change.
00048 */
00049 static tConfigTree MyCONF;
00050 static char *szCache;
00051 static char *szReportFile;
00052 static FILE *ReportFile;
00053 CRITICAL_SECTION csReport;
00054 static char *szErrorMessage;
00055 
00056 static int DoMemoryCache; /* we can switch it off while developing */
00057 CRITICAL_SECTION csCacheWrite;
00058 static SymbolTable ProgramCache;
00059 static void *pCacheMemorySegment;
00060 typedef struct _CacheItem {
00061   BuildObject *pMyBUILD;
00062   CRITICAL_SECTION csCompile;
00063   }CacheItem,*pCacheItem;
00064 
00065 static void IsapiErrorScreen(LPEXTENSION_CONTROL_BLOCK lpECB){
00066   DWORD dwBytes;
00067   static char *szDefaultErrorMessage =
00068 "</PRE></FONT>\n</BODY>\n</HTML>\n";
00069 
00070   if( szErrorMessage == NULL )szErrorMessage = szDefaultErrorMessage;
00071 
00072   dwBytes = strlen(szErrorMessage);
00073   lpECB->WriteClient(lpECB->ConnID,szErrorMessage,&dwBytes,HSE_IO_SYNC);
00074 
00075   }
00076 
00077 int GetC(void *f){ return getc((FILE *)f); }
00078 
00079 void isapi_report(void *vlpECB,
00080                   char *FileName,
00081                   long LineNumber,
00082                   unsigned int iErrorCode,
00083                   int iErrorSeverity,
00084                   int *piErrorCounter,
00085                   char *szErrorString,
00086                   unsigned long *fFlags
00087   ){
00088   char timebuf[9],datebuf[9];
00089   LPEXTENSION_CONTROL_BLOCK lpECB=vlpECB;
00090   char ErrMes[256];
00091   DWORD dwBytes;
00092   static char *szErrorHeader =
00093 "HTTP/1.0 200 OK\nContent-Type: text/html\n\n"
00094 "<HTML>\n<HEAD>\n<TITLE>ScriptBasic Program Error</TITLE>\n</HEAD>\n<BODY BGCOLOR=\"WHITE\">\n"
00095 "<FONT FACE=\"VERDANA\" SIZE=\"2\">\n"
00096 "<H1>ScriptBasic Program Error</H1>\n"
00097 "An error happened while executing the program.<P>\n<FONT SIZE=\"3\"><TT>";
00098 
00099 #define EMIT  dwBytes = strlen(ErrMes);lpECB->WriteClient(lpECB->ConnID,ErrMes,&dwBytes,HSE_IO_SYNC)
00100 
00101   if(  !((*fFlags) & REPORT_F_FRST) ){
00102     dwBytes = strlen(szErrorHeader);
00103     lpECB->WriteClient(lpECB->ConnID,szErrorHeader,&dwBytes,HSE_IO_SYNC);
00104     }
00105 
00106   if( szReportFile == NULL )return;
00107   EnterCriticalSection(&csReport);
00108   ReportFile = fopen(szReportFile,"a");
00109   if( ReportFile == NULL )
00110     LeaveCriticalSection(&csReport);
00111 
00112   _strtime( timebuf );
00113   _strdate( datebuf );
00114   if( szErrorString && strlen(szErrorString) > 80 )szErrorString[79] = (char)0;
00115 
00116   if( iErrorSeverity >= REPORT_ERROR && piErrorCounter )(*piErrorCounter)++;
00117 
00118   if( ReportFile )fprintf(ReportFile,"%s %s:",datebuf,timebuf);
00119   sprintf(ErrMes,"%s %s:",datebuf,timebuf);
00120   EMIT;
00121   if( FileName && ReportFile )fprintf(ReportFile,"%s(%ld):",FileName,LineNumber);
00122   if( FileName ){
00123     sprintf(ErrMes,"%s(%ld):",FileName,LineNumber);
00124     EMIT;
00125     }
00126   if( ReportFile )
00127     fprintf(ReportFile,(iErrorCode < MAX_ERROR_CODE ? " error &H%x:" : " error 0x%08x:"),iErrorCode);
00128   sprintf(ErrMes,(iErrorCode < MAX_ERROR_CODE ? " error &H%x:" : " error 0x%08x:"),iErrorCode);
00129   EMIT;
00130   if( iErrorCode >= MAX_ERROR_CODE )iErrorCode = COMMAND_ERROR_EXTENSION_SPECIFIC;
00131   if( szErrorString ){
00132     fprintf(ReportFile,en_error_messages[iErrorCode],szErrorString);
00133     fprintf(ReportFile,"\n");
00134     }else
00135     fprintf(ReportFile,"%s\n",en_error_messages[iErrorCode]);
00136 
00137   if( szErrorString ){
00138     sprintf(ErrMes,en_error_messages[iErrorCode],szErrorString);
00139     EMIT;
00140     sprintf(ErrMes,"<P>\n");
00141     EMIT;
00142     }else{
00143     sprintf(ErrMes,"%s<P>\n",en_error_messages[iErrorCode]);
00144     EMIT;
00145     }
00146   *fFlags |= REPORT_F_FRST;
00147   if( ReportFile ){
00148     fclose(ReportFile);
00149     LeaveCriticalSection(&csReport);
00150     }
00151   }
00152 
00153 
00154 DWORD WINAPI HttpExtensionProc(LPEXTENSION_CONTROL_BLOCK lpECB){
00155   LexObject MyLEX;
00156   ReadObject MyREAD;
00157   BuildObject *pMyBUILD;
00158 #define MyBUILD (*pMyBUILD)
00159   eXobject MyEX;
00160   ExecuteObject MyEXE;
00161   peNODE_l CommandList;
00162   unsigned long fErrorFlags;
00163   int iError,iErrorCounter;
00164   char *szInputFile;
00165   char *pszPreprocessedFileName=NULL;
00166   int binarycode;
00167 #define FULL_PATH_BUFFER_LENGTH 256
00168   char *s;
00169   char Argv0[FULL_PATH_BUFFER_LENGTH];
00170   char CachedFileName[FULL_PATH_BUFFER_LENGTH];
00171   unsigned long FileTime,CacheTime;
00172   pCacheItem *ppCache;
00173 
00174 //DebugBreak();
00175 
00176   lpECB->dwHttpStatusCode = 200; /* if no one else sets */
00177 
00178   /* default values for command line options */
00179   szInputFile = lpECB->lpszPathTranslated;
00180   binarycode = 0; /* input is not binary by default */
00181 DoMemoryCache = 0;
00182   if( DoMemoryCache )
00183     ppCache = (pCacheItem *)sym_LookupSymbol(szInputFile,
00184                                              ProgramCache,
00185                                              0,
00186                                              alloc_Alloc,
00187                                              alloc_Free,
00188                                              pCacheMemorySegment);
00189 
00190   if( DoMemoryCache && ppCache && *ppCache && (*ppCache)->pMyBUILD ){
00191 CodeIsCached:;
00192     /* we have to enter this critical section to get sure that
00193        the cache is not under compilation currently */
00194     EnterCriticalSection( &((*ppCache)->csCompile) );
00195     LeaveCriticalSection( &((*ppCache)->csCompile) );
00196     pMyBUILD = (*ppCache)->pMyBUILD;
00197     }else{
00198 
00199     if( DoMemoryCache ){
00200       EnterCriticalSection(&csCacheWrite);
00201       ppCache = (pCacheItem *)sym_LookupSymbol(szInputFile,
00202                                                ProgramCache,
00203                                                1,
00204                                                alloc_Alloc,
00205                                                alloc_Free,
00206                                                pCacheMemorySegment);
00207 
00208       if( *ppCache && (*ppCache)->pMyBUILD ){
00209         /* we get here if the code was not cached when we first looked for it
00210            but while getting here another thread did cache it instead of us.
00211 
00212            *ppCache can be non-NULL while (*ppCache)->pMyBUILD is NULL when the
00213            code was corrupt last time, and it is tried to be executed now. */
00214         LeaveCriticalSection(&csCacheWrite);
00215         goto CodeIsCached;
00216         }
00217 
00218       *ppCache = alloc_Alloc(sizeof(CacheItem),pCacheMemorySegment);
00219       if( *ppCache == NULL ){
00220         sprintf(lpECB->lpszLogData,"Not enough memory.");
00221         IsapiErrorScreen(lpECB);
00222         return HSE_STATUS_SUCCESS;
00223         }
00224       InitializeCriticalSection( &((*ppCache)->csCompile) );
00225       EnterCriticalSection( &((*ppCache)->csCompile) );
00226       LeaveCriticalSection( &csCacheWrite );
00227       }
00228 
00229     if( DoMemoryCache )
00230       pMyBUILD = alloc_Alloc(sizeof(BuildObject),pCacheMemorySegment);
00231     else
00232       pMyBUILD = malloc(sizeof(BuildObject));
00233 
00234     if( pMyBUILD == NULL ){
00235       if( DoMemoryCache ){
00236         (*ppCache)->pMyBUILD = NULL;
00237         LeaveCriticalSection( &((*ppCache)->csCompile) );
00238         }
00239       sprintf(lpECB->lpszLogData,"Not enough memory.");
00240       IsapiErrorScreen(lpECB);
00241       return HSE_STATUS_SUCCESS;
00242       }
00243 
00244     if( DoMemoryCache )
00245       (*ppCache)->pMyBUILD = pMyBUILD;
00246 
00247     if( szCache ){
00248       strcpy(CachedFileName,szCache);
00249       s = CachedFileName + strlen(CachedFileName); /* point to the end of the cache directory */
00250 
00251       strcpy(s,szInputFile);
00252 
00253       strcpy(Argv0,s);
00254       uniqfnam(s,s);
00255       FileTime  = file_time_modified(szInputFile);
00256       CacheTime = file_time_modified(CachedFileName);
00257       if( FileTime && CacheTime && CacheTime > FileTime ){
00258         szInputFile = CachedFileName;
00259       /* Check that the cache file is in correct format.
00260          This call will help upgrade without deleting the cache
00261          files. Former versions tried to load the binary code created by
00262          a previous version of scriba and resulted error messages
00263          complaining about corrupt binary file whe trying to execute
00264          a syntactically correct BASIC program.      */
00265         binarycode = build_IsFileBinaryFormat(szInputFile);
00266         }
00267      }else{
00268       strcpy(Argv0,szInputFile);
00269       }
00270 
00271     if( binarycode || build_IsFileBinaryFormat(szInputFile) ){
00272       /* the code is given as a compiled code */
00273       MyBUILD.memory_allocating_function = malloc;
00274       MyBUILD.memory_releasing_function  = free;
00275       MyBUILD.iErrorCounter = 0;
00276       MyBUILD.reportptr = lpECB;
00277       MyBUILD.report   = isapi_report;
00278       MyBUILD.fErrorFlags = 0;
00279       build_LoadCode(&MyBUILD,szInputFile);
00280       if( MyBUILD.iErrorCounter ){
00281         if( DoMemoryCache ){
00282           (*ppCache)->pMyBUILD = NULL;
00283           LeaveCriticalSection( &((*ppCache)->csCompile) );
00284           }
00285         alloc_FinishSegment(MyBUILD.pMemorySegment);
00286         sprintf(lpECB->lpszLogData,"There were %d error(s) reading the code %s while executing %s.",MyBUILD.iErrorCounter,szInputFile,Argv0);
00287         IsapiErrorScreen(lpECB);
00288         return HSE_STATUS_SUCCESS;
00289         }
00290       }else{
00291       /* the code is source code basic text format */
00292     fErrorFlags = 0;
00293     iErrorCounter = 0;
00294     iError = epreproc(&MyCONF,szInputFile,&pszPreprocessedFileName,NULL,malloc,free);
00295     if( iError ){
00296       isapi_report(stderr,"",0,iError,REPORT_ERROR,&iErrorCounter,NULL,&fErrorFlags);
00297       /* there were errors during preprocess */
00298       sprintf(lpECB->lpszLogData,"There was an error executing the externalpreprocessor.");
00299       IsapiErrorScreen(lpECB);
00300       return HSE_STATUS_SUCCESS;
00301       }
00302 
00303       reader_InitStructure(&MyREAD);
00304       MyREAD.memory_allocating_function = alloc_Alloc;
00305       MyREAD.memory_releasing_function = alloc_Free;
00306       MyREAD.pMemorySegment = alloc_InitSegment(malloc,free);
00307       MyREAD.report = isapi_report;
00308       MyREAD.reportptr = lpECB;
00309       MyREAD.iErrorCounter = 0;
00310       MyREAD.fErrorFlags = 0;
00311       MyREAD.pConfig = &MyCONF;
00312       if( pszPreprocessedFileName )
00313         reader_ReadLines(&MyREAD,pszPreprocessedFileName);
00314       else
00315         reader_ReadLines(&MyREAD,szInputFile);
00316 
00317       if( MyREAD.iErrorCounter ){
00318         /* there were errors during lexical analisys */
00319         if( DoMemoryCache ){
00320           (*ppCache)->pMyBUILD = NULL;
00321           LeaveCriticalSection( &((*ppCache)->csCompile) );
00322           }
00323         sprintf(lpECB->lpszLogData,"There were %d error(s) during read executing %s.",MyREAD.iErrorCounter,szInputFile);
00324         IsapiErrorScreen(lpECB);
00325         return HSE_STATUS_SUCCESS;
00326         }
00327 
00328       reader_StartIteration(&MyREAD);
00329 
00330       MyLEX.memory_allocating_function = alloc_Alloc;
00331       MyLEX.memory_releasing_function = alloc_Free;
00332       MyLEX.pMemorySegment = alloc_InitSegment(malloc,free);
00333       lex_InitStructure(&MyLEX);
00334 
00335       MyLEX.pfGetCharacter = reader_NextCharacter;
00336       MyLEX.pfFileName = reader_FileName;
00337       MyLEX.pfLineNumber = reader_LineNumber;
00338 
00339       MyLEX.pNASymbols = NASYMBOLS;
00340       MyLEX.pASymbols  = ASYMBOLS;
00341       MyLEX.pCSymbols  = CSYMBOLS;
00342       MyLEX.report = isapi_report;
00343       MyLEX.reportptr = lpECB;
00344       MyLEX.fErrorFlags = MyREAD.fErrorFlags;
00345       MyLEX.iErrorCounter = 0;
00346       MyLEX.pLexResult = NULL;
00347 
00348 
00349       MyLEX.pvInput = (void *)&MyREAD;
00350       lex_ReadInput(&MyLEX);
00351 
00352       if( MyLEX.iErrorCounter ){
00353         /* there were errors during lexical analisys */
00354         if( DoMemoryCache ){
00355           (*ppCache)->pMyBUILD = NULL;
00356           LeaveCriticalSection( &((*ppCache)->csCompile) );
00357           }
00358         sprintf(lpECB->lpszLogData,"There were %d error(s) during lex executing %s.",MyLEX.iErrorCounter,szInputFile);
00359         IsapiErrorScreen(lpECB);
00360         return HSE_STATUS_SUCCESS;
00361         }
00362 
00363       lex_RemoveComments(&MyLEX);
00364       lex_HandleContinuationLines(&MyLEX);
00365 
00366       MyEX.memory_allocating_function = malloc;
00367       MyEX.memory_releasing_function = free;
00368       MyEX.cbBuffer = 1024; /* init will allocate the space of this number of characters */
00369       MyEX.cbCurrentNameSpace = 1024; /* init will allocate the space of this number of characters */
00370       MyEX.pLex = &MyLEX;
00371 
00372       MyEX.Unaries  = UNARIES;
00373       MyEX.Binaries = BINARIES;
00374       MyEX.BuiltInFunctions = INTERNALFUNCTIONS;
00375       MyEX.MAXPREC  = MAX_BINARY_OPERATOR_PRECEDENCE;
00376       MyEX.PredeclaredLongConstants = PREDLCONSTS;
00377       MyEX.reportptr = lpECB;
00378       MyEX.report   = isapi_report;
00379       MyEX.fErrorFlags = MyLEX.fErrorFlags;
00380       MyEX.iErrorCounter = 0;
00381 
00382       MyEX.Command = COMMANDS;
00383 
00384       ex_init(&MyEX);
00385 
00386       ex_Command_l(&MyEX,&CommandList);
00387 
00388       if( MyEX.iErrorCounter ){
00389         if( DoMemoryCache ){
00390           (*ppCache)->pMyBUILD = NULL;
00391           LeaveCriticalSection( &((*ppCache)->csCompile) );
00392           }
00393         sprintf(lpECB->lpszLogData,"There were %d error(s) during syntax analisys executing %s.",MyEX.iErrorCounter,szInputFile);
00394         IsapiErrorScreen(lpECB);
00395         return HSE_STATUS_SUCCESS;
00396        }
00397  
00398       MyEX.pCommandList = CommandList;
00399 
00400       MyBUILD.memory_allocating_function = malloc;
00401       MyBUILD.memory_releasing_function  = free;
00402       MyBUILD.pEx = &MyEX;
00403       MyBUILD.iErrorCounter = 0;
00404       MyBUILD.fErrorFlags = MyEX.fErrorFlags;
00405       MyBUILD.FirstUNIXline = NULL; /* On Windows NT there is no need for this. */
00406 
00407       build_Build(&MyBUILD);
00408 
00409       if( MyBUILD.iErrorCounter ){
00410         if( DoMemoryCache ){
00411           (*ppCache)->pMyBUILD = NULL;
00412           LeaveCriticalSection( &((*ppCache)->csCompile) );
00413           }
00414           alloc_FinishSegment(MyBUILD.pMemorySegment);
00415         sprintf(lpECB->lpszLogData,"There were %d error(s) during building executing %s.",MyBUILD.iErrorCounter,szInputFile);
00416         IsapiErrorScreen(lpECB);
00417         return HSE_STATUS_SUCCESS;
00418         }
00419 
00420       if( DoMemoryCache )
00421         alloc_Merge(pCacheMemorySegment,MyBUILD.pMemorySegment);
00422 
00423       /* This is the very first place where we can relase the reader memory
00424          because syntax error messages point to the file name strings that are reserved
00425          by the reader. */
00426       alloc_FinishSegment(MyLEX.pMemorySegment);
00427 
00428       ex_free(&MyEX);
00429 
00430       if( szCache ){
00431         build_SaveCode(&MyBUILD,CachedFileName);
00432         }
00433       alloc_FinishSegment(MyREAD.pMemorySegment);
00434       }/* end of non binary code */
00435     /* now we have it correctly compiled, we can let others use it */
00436     if( DoMemoryCache )
00437       LeaveCriticalSection( &((*ppCache)->csCompile) );
00438     }/* end of no memory cache */
00439 
00440   MyEXE.memory_allocating_function = malloc;
00441   MyEXE.memory_releasing_function = free;
00442   MyEXE.reportptr = lpECB;
00443   MyEXE.report   = isapi_report;
00444   MyEXE.fErrorFlags = MyEX.fErrorFlags;
00445 
00446   MyEXE.pConfig = &MyCONF;
00447   //MyEXE.Argv0 = Argv0;
00448   build_MagicCode(&(MyEXE.Ver));
00449   if( execute_InitStructure(&MyEXE,pMyBUILD) ){
00450     sprintf(lpECB->lpszLogData,"Memory low executing %s.",szInputFile);
00451     IsapiErrorScreen(lpECB);
00452     return HSE_STATUS_SUCCESS;
00453     }
00454 /*
00455   We could alter the standard input, standard output, the environment
00456   function and command arguments here . We do only the command
00457   arguments here in this variation. */
00458   MyEXE.CmdLineArgument = "";  
00459   MyEXE.pEmbedder = lpECB;
00460   MyEXE.fpStdouFunction = IsapiStdOutFunction;
00461   strcpy(MyEXE.Ver.Variation,"WINISAPI");
00462 
00463   execute_Execute(&MyEXE,&iError);
00464   alloc_FinishSegment(MyEXE.pMo->pMemorySegment);
00465   alloc_FinishSegment(MyEXE.pMemorySegment);
00466 
00467   if( pszPreprocessedFileName )free(pszPreprocessedFileName);
00468 
00469   if( ! DoMemoryCache ){
00470     alloc_FinishSegment(MyBUILD.pMemorySegment);
00471     free(pMyBUILD);
00472     }
00473   sprintf(lpECB->lpszLogData,"Executed %s.",szInputFile);
00474   return HSE_STATUS_SUCCESS;
00475   }
00476 
00477 BOOL WINAPI TerminateExtension(DWORD dwFlags){
00478   char timebuf[9],datebuf[9];
00479 
00480   switch( dwFlags ){
00481     case HSE_TERM_ADVISORY_UNLOAD:
00482       if( szReportFile != NULL ){
00483         EnterCriticalSection(&csReport);
00484         ReportFile = fopen(szReportFile,"a");
00485         if( ReportFile != NULL ){
00486           _strtime( timebuf );
00487           _strdate( datebuf );
00488           fprintf(ReportFile,"%s %s: ScriptBasic ISAPI variation was unloaded upon request.\n",datebuf,timebuf);
00489           fclose(ReportFile);
00490           }
00491         LeaveCriticalSection(&csReport);
00492         }
00493       alloc_FinishSegment(MyCONF.pMemorySegment);
00494       MyCONF.pMemorySegment = NULL;
00495       return TRUE;
00496     case HSE_TERM_MUST_UNLOAD:
00497       if( szReportFile != NULL ){
00498         EnterCriticalSection(&csReport);
00499         ReportFile = fopen(szReportFile,"a");
00500         if( ReportFile != NULL ){
00501           _strtime( timebuf );
00502           _strdate( datebuf );
00503           fprintf(ReportFile,"%s %s: ScriptBasic ISAPI variation was forcefully unloaded.\n",datebuf,timebuf);
00504           fclose(ReportFile);
00505           }
00506         LeaveCriticalSection(&csReport);
00507         }
00508       alloc_FinishSegment(MyCONF.pMemorySegment);
00509       MyCONF.pMemorySegment = NULL;
00510       return TRUE;
00511     default:;
00512     }
00513   return 0;
00514   }
00515 
00516 BOOL WINAPI  GetExtensionVersion(HSE_VERSION_INFO *pVer){
00517   char *szErrorMessageFile,*s;
00518   FILE *fp;
00519   int cbErrorMessage;
00520   char timebuf[9],datebuf[9];
00521   void *pMEM;
00522 
00523   pMEM = alloc_InitSegment(malloc,free);
00524   if( pMEM == NULL )return FALSE;
00525 
00526   cft_start(&MyCONF,alloc_Alloc,alloc_Free,pMEM,
00527 #ifdef WIN32
00528             "Software\\ScriptBasic\\config",
00529             "WINNT\\SCRIBA.INI",
00530 #else
00531             "SCRIBACONF",
00532             "/etc/scriba/basic.conf",
00533 #endif
00534             NULL);
00535 DebugBreak();
00536   szCache = cft_GetString(&MyCONF,"cache");
00537   szCache = NULL;
00538   szReportFile = cft_GetString(&MyCONF,"isapi.report");
00539   InitializeCriticalSection(&csReport);
00540 
00541   /* read the error message text that is sent to the client screen when
00542      error happens in the code. */
00543 
00544   szErrorMessageFile = cft_GetString(&MyCONF,"isapi.errmesfile");
00545   szErrorMessage = NULL;
00546   if( szErrorMessageFile ){
00547     fp = fopen(szErrorMessageFile,"rb");
00548     if( fp ){
00549       szErrorMessage = (char *)malloc((cbErrorMessage = file_size(szErrorMessageFile))+1);
00550       if( (s=szErrorMessage) && cbErrorMessage ){
00551         while( cbErrorMessage-- )*s++ = getc(fp);
00552         *s = (char)0;
00553         fclose(fp);
00554         }else szErrorMessage = NULL;
00555       }
00556     }
00557 
00558   if( szReportFile != NULL ){
00559     EnterCriticalSection(&csReport);
00560     ReportFile = fopen(szReportFile,"a");
00561     if( ReportFile != NULL ){
00562       _strtime( timebuf );
00563       _strdate( datebuf );
00564       fprintf(ReportFile,"%s %s: ScriptBasic ISAPI variation was loaded.\n",datebuf,timebuf);
00565       fclose(fp);
00566       }
00567     LeaveCriticalSection(&csReport);
00568     }
00569 
00570   /* This variation caches programs in memory, and we should have
00571      a symbol table that tells us where the collected code is.
00572   */
00573 
00574   s = cft_GetString(&MyCONF,"isapi.memcache");
00575   if( s ){
00576     pCacheMemorySegment = alloc_InitSegment(malloc,free);
00577     if( pCacheMemorySegment == NULL )return FALSE;
00578     ProgramCache = sym_NewSymbolTable(alloc_Alloc,pCacheMemorySegment);
00579     if( ProgramCache == NULL )return FALSE;
00580     InitializeCriticalSection(&csCacheWrite);
00581     DoMemoryCache = 1;
00582     }else{
00583     DoMemoryCache = 0;
00584     pCacheMemorySegment = NULL;
00585     ProgramCache = NULL;
00586     }
00587 
00588   pVer->dwExtensionVersion = HSE_VERSION;
00589   return TRUE;
00590   }

Generated on Sun Mar 12 23:56:32 2006 for ScriptBasic by  doxygen 1.4.6-NO