📄 conscomp.c
字号:
}/***********************************************//* ConstructsToCCommandDefinition: Initializes *//* the constructs-to-c command. *//***********************************************/globle VOID ConstructsToCCommandDefinition() { DefineFunction2("constructs-to-c",'v', PTIF ConstructsToCCommand, "ConstructsToCCommand", "23*kii"); }/*********************************************************//* AddCodeGeneratorItem: Adds another code generator *//* item to the list of items for which code is *//* generated bythe constructs-to-c function. Typically *//* each construct has its own code generator item. *//*********************************************************/globle struct CodeGeneratorItem *AddCodeGeneratorItem(name,priority,beforeFunction, initFunction,generateFunction, arrayCount) char *name; int priority; VOID (*beforeFunction)(VOID_ARG);#if ANSI_COMPILER VOID (*initFunction)(FILE *,int,int); int (*generateFunction)(char *,int,FILE *,int,int);#else VOID (*initFunction)(); int (*generateFunction)();#endif int arrayCount; { struct CodeGeneratorItem *newPtr, *currentPtr, *lastPtr = NULL; static int theCount = 0; register int i; char theBuffer[3]; /*======================================*/ /* Create the code generator item data */ /* structure and initialize its values. */ /*======================================*/ newPtr = get_struct(CodeGeneratorItem); newPtr->name = name; newPtr->beforeFunction = beforeFunction; newPtr->initFunction = initFunction; newPtr->generateFunction = generateFunction; newPtr->priority = priority; /*================================================*/ /* Create the primary and secondary codes used to */ /* provide names for the C data structure arrays. */ /* (The maximum number of arrays is currently */ /* limited to 47. */ /*================================================*/ if (arrayCount != 0) { if ((arrayCount + theCount) > (PRIMARY_LEN + SECONDARY_LEN)) { CLIPSSystemError("CONSCOMP",2); ExitCLIPS(2); } newPtr->arrayNames = (char **) gm2((int) (sizeof(char *) * arrayCount)); for (i = 0 ; i < arrayCount ; i++) { if (theCount < PRIMARY_LEN) { sprintf(theBuffer,"%c",PRIMARY_CODES[theCount]); } else { sprintf(theBuffer,"%c_",SECONDARY_CODES[theCount - PRIMARY_LEN]); } theCount++; newPtr->arrayNames[i] = (char *) gm2((int) (strlen(theBuffer) + 1)); strcpy(newPtr->arrayNames[i],theBuffer); } } else { newPtr->arrayNames = NULL; } /*===========================================*/ /* Add the new item in the appropriate place */ /* in the code generator item list. */ /*===========================================*/ if (ListOfCodeGeneratorItems == NULL) { newPtr->next = NULL; ListOfCodeGeneratorItems = newPtr; return(newPtr); } currentPtr = ListOfCodeGeneratorItems; while ((currentPtr != NULL) ? (priority < currentPtr->priority) : CLIPS_FALSE) { lastPtr = currentPtr; currentPtr = currentPtr->next; } if (lastPtr == NULL) { newPtr->next = ListOfCodeGeneratorItems; ListOfCodeGeneratorItems = newPtr; } else { newPtr->next = currentPtr; lastPtr->next = newPtr; } /*=========================*/ /* Return a pointer to the */ /* code generator item. */ /*=========================*/ return(newPtr); } /************************************************************//* CloseFileIfNeeded: Determines if a C file to which data *//* structures have been written should be closed. The *//* file is closed either when all data structures of *//* that specific type are written to files or the maximum *//* number of array entries for a single file has been *//* exceeded. *//************************************************************/globle FILE *CloseFileIfNeeded(theFile,theCount,arrayVersion,maxIndices, canBeReopened,codeFile) FILE *theFile; int *theCount; int *arrayVersion; int maxIndices; int *canBeReopened; struct CodeGeneratorFile *codeFile; { /*==========================================*/ /* If the maximum number of entries for the */ /* file hasn't been exceeded, then... */ /*==========================================*/ if (*theCount < maxIndices) { /*====================================*/ /* If the file can be reopened later, */ /* close it. Otherwise, keep it open. */ /*====================================*/ if (canBeReopened != NULL) { *canBeReopened = CLIPS_TRUE; fclose(theFile); return(NULL); } return(theFile); } /*===========================================*/ /* Otherwise, the number of entries allowed */ /* in a file has been reached. Indicate that */ /* the file can't be reopened. */ /*===========================================*/ if (canBeReopened != NULL) { *canBeReopened = CLIPS_FALSE; } /*===============================================*/ /* If the file is closed, then we need to reopen */ /* it to print the final closing right brace. */ /*===============================================*/ if (theFile == NULL) { if ((canBeReopened == NULL) || (codeFile == NULL)) { CLIPSSystemError("CONSCOMP",3); ExitCLIPS(2); } if (codeFile->filePrefix == NULL) { return(NULL); } theFile = NewCFile(codeFile->filePrefix,codeFile->id,codeFile->version,CLIPS_TRUE); if (theFile == NULL) { CLIPSSystemError("CONSCOMP",4); ExitCLIPS(2); } } /*================================*/ /* Print the final closing brace. */ /*================================*/ fprintf(theFile,"};\n"); fclose(theFile); /*============================================*/ /* Update index values for subsequent writing */ /* of data structures to files. */ /*============================================*/ *theCount = 0; (*arrayVersion)++; /*=========================*/ /* Return NULL to indicate */ /* the file is closed. */ /*=========================*/ return(NULL); } /**************************************************************//* OpenFileIfNeeded: Determines if a C file to which data *//* structures have been written should be closed. The *//* file is closed either when all data structures of *//* that specific type are written to files or the maximum *//* number of array entries for a single file has been *//* exceeded. *//******************************************************************/globle FILE *OpenFileIfNeeded(theFile,fileName,fileID,imageID,fileCount,arrayVersion, headerFP,structureName,structPrefix,reopenOldFile,codeFile) FILE *theFile; char *fileName; int fileID; int imageID; int *fileCount; int arrayVersion; FILE *headerFP; char *structureName; char *structPrefix; int reopenOldFile; struct CodeGeneratorFile *codeFile; { char arrayName[80]; char *newName; int newID, newVersion; /*===========================================*/ /* If a file is being reopened, use the same */ /* version number, name, and ID as before. */ /*===========================================*/ if (reopenOldFile) { if (codeFile == NULL) { CLIPSSystemError("CONSCOMP",5); ExitCLIPS(2); } newName = codeFile->filePrefix; newID = codeFile->id; newVersion = codeFile->version; } /*=====================================================*/ /* Otherwise, use the specified version number, name, */ /* and ID. If the appropriate argument is supplied, */ /* remember these values for later reopening the file. */ /*=====================================================*/ else { newName = fileName; newVersion = *fileCount; newID = fileID; if (codeFile != NULL) { codeFile->version = newVersion; codeFile->filePrefix = newName; codeFile->id = newID; } } /*=========================================*/ /* If the file is already open, return it. */ /*=========================================*/ if (theFile != NULL) { fprintf(theFile,",\n"); return(theFile); } /*================*/ /* Open the file. */ /*================*/ if ((theFile = NewCFile(newName,newID,newVersion,reopenOldFile)) == NULL) { return(NULL); } /*=========================================*/ /* If this is the first time the file has */ /* been opened, write out the beginning of */ /* the array variable definition. */ /*=========================================*/ if (reopenOldFile == CLIPS_FALSE) { (*fileCount)++; sprintf(arrayName,"%s%d_%d",structPrefix,imageID,arrayVersion); #if SHORT_LINK_NAMES if (strlen(arrayName) > 6) { PrintWarningID("CONSCOMP",2,CLIPS_FALSE); PrintCLIPS(WWARNING,"Array name "); PrintCLIPS(WWARNING,arrayName); PrintCLIPS(WWARNING,"exceeds 6 characters in length.\n"); PrintCLIPS(WWARNING," This variable may be indistinguishable from another by the linker.\n"); }#endif fprintf(theFile,"%s %s[] = {\n",structureName,arrayName); fprintf(headerFP,"extern %s %s[];\n",structureName,arrayName); } else { fprintf(theFile,",\n"); } /*==================*/ /* Return the file. */ /*==================*/ return(theFile); } /*************************************************//* MarkConstructBsaveIDs: Mark all occurences of *//* a specific construct with a unique ID. *//*************************************************/globle VOID MarkConstructBsaveIDs(constructModuleIndex) int constructModuleIndex; { long theCount = 0; DoForAllConstructs(MarkConstruct,constructModuleIndex,CLIPS_FALSE,&theCount); } /*************************************************************//* MarkConstruct: Sets the bsaveID for a specific construct. *//* Used with the MarkConstructBsaveIDs function to mark all *//* occurences of a specific construct with a unique ID. *//*************************************************************/static VOID MarkConstruct(theConstruct,vTheBuffer) struct constructHeader *theConstruct; VOID *vTheBuffer; { long *count = (long *) vTheBuffer; theConstruct->bsaveID = (*count)++; }/***********************************************************//* ConstructHeaderToCode: Writes the C code representation *//* of a single construct header to the specified file. *//***********************************************************/globle VOID ConstructHeaderToCode(theFile,theConstruct,imageID,maxIndices,moduleCount, constructModulePrefix,constructPrefix) FILE *theFile; struct constructHeader *theConstruct; int imageID; int maxIndices; int moduleCount; char *constructModulePrefix; char *constructPrefix; { /*================*/ /* Construct Name */ /*================*/ fprintf(theFile,"{"); PrintSymbolReference(theFile,theConstruct->name); /*===================*/ /* Pretty Print Form */ /*===================*/ fprintf(theFile,",NULL,"); /*====================*/ /* Construct Module */ /*====================*/ fprintf(theFile,"MIHS &%s%d_%d[%d],", constructModulePrefix, imageID, (moduleCount / maxIndices) + 1, moduleCount % maxIndices); /*==========*/ /* Bsave ID */ /*==========*/ fprintf(theFile,"0,"); /*================*/ /* Next Construct */ /*================*/ if (theConstruct->next == NULL) { fprintf(theFile,"NULL}"); } else { fprintf(theFile,"CHS &%s%d_%ld[%ld]}", constructPrefix, imageID, (theConstruct->next->bsaveID / maxIndices) + 1, theConstruct->next->bsaveID % maxIndices); } } /***********************************************************//* ConstructModuleToCode: Writes the C code representation *//* of a single construct module to the specified file. *//***********************************************************/globle VOID ConstructModuleToCode(theFile,theModule,imageID,maxIndices, constructIndex,constructPrefix) FILE *theFile; struct defmodule *theModule; int imageID; int maxIndices; int constructIndex; char *constructPrefix; { struct defmoduleItemHeader *theModuleItem; /*======================*/ /* Associated Defmodule */ /*======================*/ fprintf(theFile,"{"); theModuleItem = (struct defmoduleItemHeader *) GetModuleItem(theModule,constructIndex); PrintDefmoduleReference(theFile,theModule); fprintf(theFile,","); /*=============================*/ /* First Construct Module Item */ /*=============================*/ if (theModuleItem->firstItem == NULL) fprintf(theFile,"NULL,"); else fprintf(theFile,"CHS &%s%d_%ld[%ld],", constructPrefix, imageID, (long) (theModuleItem->firstItem->bsaveID / maxIndices) + 1, (long) theModuleItem->firstItem->bsaveID % maxIndices); /*============================*/ /* Last Construct Module Item */ /*============================*/ if (theModuleItem->lastItem == NULL) fprintf(theFile,"NULL"); else fprintf(theFile,"CHS &%s%d_%ld[%ld]", constructPrefix, imageID, (long) (theModuleItem->lastItem->bsaveID / maxIndices) + 1, (long) theModuleItem->lastItem->bsaveID % maxIndices); fprintf(theFile,"}"); } #else /* CONSTRUCT_COMPILER && (! RUN_TIME) */#if ANSI_COMPILER VOID ConstructsToCCommand(void);#else VOID ConstructsToCCommand();#endif/************************************//* ConstructsToCCommand: Definition *//* for rule compiler stub. *//************************************/VOID ConstructsToCCommand() {}#endif /* CONSTRUCT_COMPILER && (! RUN_TIME) */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -