/*********************************************************************/ /* pC++/Sage++ Copyright (C) 1993 */ /* Indiana University University of Oregon University of Rennes */ /*********************************************************************/ /* This file is used to automatically generate a "#include" header */ /* mkCextern $SAGEROOT/lib/newsrc/low_level.c > ! $SAGEROOT/lib/include/ext_low.h mkC++extern $SAGEROOT/lib/newsrc/low_level.c > ! $SAGEROOT/lib/include/extcxx_low.h */ #include #include #include /* ANSI variable argument header */ #include #include "compatible.h" /* Make different system compatible... (PHB) */ #ifdef SYS5 #include #else #include #endif #include "vpc.h" #include "macro.h" #include "ext_lib.h" #ifdef __SPF extern void addToCollection(const int line, const char *file, void *pointer, int type); extern void removeFromCollection(void *pointer); #endif #define MAX_FILE 1000 /*max number of files in a project*/ #define MAXFIELDSYMB 10 #define MAXFIELDTYPE 10 #define MAX_SYMBOL_FOR_DUPLICATE 1000 char Current_File_name[256]; int debug =NO; /* used in db.c*/ PTR_FILE pointer_on_file_proj; static int number_of_bif_node = 0; int number_of_ll_node = 0; /* this counters are useless anymore ??*/ static int number_of_symb_node = 0; static int number_of_type_node = 0; char *default_filename; int Warning_count = 0; /* FORWARD DECLARATIONS (phb) */ int buildLinearRepSign(); int makeLinearExpr_Sign(); int getLastLabelId(); int isItInSection(); int Init_Tool_Box(); void Message(); PTR_BFND rec_num_near_search(); PTR_BFND Redo_Bif_Next_Chain_Internal(); PTR_SYMB duplicateSymbol(); void Redo_Bif_Next_Chain(); PTR_LABEL getLastLabel(); PTR_BFND getNodeBefore (); char *filter(); PTR_BFND getLastNodeList(); int *evaluateExpression(); PTR_SYMB duplicateSymbolOfRoutine(); void SetCurrentFileTo(); void UnparseProgram_ThroughAllocBuffer(); void updateTypesAndSymbolsInBodyOfRoutine(); extern int write_nodes(); extern char* Tool_Unparse2_LLnode(); extern void Init_Unparser(); extern void Set_Function_Language(); extern void Unset_Function_Language(); extern char* Tool_Unparse_Bif (); extern char* Tool_Unparse_Type(); extern void BufferAllocate(); int out_free_form; int out_upper_case; int out_line_unlimit; int out_line_length; // out_line_length = 132 for -ffo mode; out_line_length = 72 for -uniForm mode PTR_SYMB last_file_symbol; static int CountNullBifNext = 0; /* for internal debugging */ /* records propoerties and type of node */ char node_code_type[LAST_CODE]; /* Number of argument-words in each kind of tree-node. */ int node_code_length[LAST_CODE]; enum typenode node_code_kind[LAST_CODE]; /* special table for infos on type and symbol */ char info_type[LAST_CODE][MAXFIELDTYPE]; char info_symb[LAST_CODE][MAXFIELDSYMB]; char general_info[LAST_CODE][MAXFIELDSYMB]; /*static struct bif_stack_level *stack_level = NULL;*/ /*static struct bif_stack_level *current_level = NULL;*/ PTR_BFND getFunctionHeader(); /***************************************************************************** * * * Procedure of general use * * * *****************************************************************************/ /* Modified to return a pointer (64bit clean) (phb) */ /***************************************************************************/ char* xmalloc(int size) { char *val; val = (char *) malloc (size); #ifdef __SPF addToCollection(__LINE__, __FILE__,val, 0); #endif if (val == 0) Message("Virtual memory exhausted (malloc failed)",0); return val; } /* list of allocated data */ static ptstack_chaining Current_Allocated_Data = NULL; static ptstack_chaining First_STACK= NULL; /***************************************************************************/ void make_a_malloc_stack() { ptstack_chaining pt; pt = (ptstack_chaining) malloc(sizeof(struct stack_chaining)); #ifdef __SPF addToCollection(__LINE__, __FILE__,pt, 0); #endif if (!pt) { Message("sorry : out of memory\n",0); exit(1); } if (Current_Allocated_Data) Current_Allocated_Data->next = pt; pt->first = NULL; pt->last = NULL; pt->prev = Current_Allocated_Data; if (Current_Allocated_Data) pt->level = Current_Allocated_Data->level +1; else pt->level = 0; /* printf("make_a_malloc_stack %d \n",pt->level);*/ Current_Allocated_Data = pt; if (First_STACK == NULL) First_STACK = pt; } /***************************************************************************/ void myfree() { ptstack_chaining pt; ptchaining pt1, pt2; if (!Current_Allocated_Data) { Message("Stack not defined\n",0); exit(1); } pt2 = Current_Allocated_Data->first; /* printf("myfree %d \n", Current_Allocated_Data->level);*/ while (pt2) { #ifdef __SPF removeFromCollection(pt2->zone); #endif free(pt2->zone); pt2->zone = 0; pt2 = pt2->list; } pt2 = Current_Allocated_Data->first; while (pt2) { pt1 = pt2; pt2 = pt2->list; #ifdef __SPF removeFromCollection(pt1); #endif free(pt1); } pt = Current_Allocated_Data; Current_Allocated_Data = pt->prev; Current_Allocated_Data->next = NULL; #ifdef __SPF removeFromCollection(pt); #endif free(pt); } /***************************************************************************/ char* mymalloc(int size) { char *pt1; ptchaining pt2; if (!Current_Allocated_Data) { Message("Allocated Stack not defined\n",0); exit(1); } /* if (Current_Allocated_Data->level > 0) printf("mymalloc %d \n", Current_Allocated_Data->level); */ pt1 = (char *) malloc(size); #ifdef __SPF addToCollection(__LINE__, __FILE__,pt1, 0); #endif if (!pt1) { Message("sorry : out of memory\n",0); exit(1); } pt2 = (ptchaining) malloc(sizeof(struct chaining)); #ifdef __SPF addToCollection(__LINE__, __FILE__,pt2, 0); #endif if (!pt2 ) { Message("sorry : out of memory\n",0); exit(1); } pt2->zone = pt1; pt2->list = NULL; if (Current_Allocated_Data->first == NULL) Current_Allocated_Data->first = pt2; if (Current_Allocated_Data->last == NULL) Current_Allocated_Data->last = pt2; else { Current_Allocated_Data->last->list = pt2; Current_Allocated_Data->last = pt2; } return pt1; } /***************** Provides infos on nodes ******************************** * * * based on the table info in include dir *.def * * * **************************************************************************/ /***************************************************************************/ int isATypeNode(variant) int variant; { return (TYPENODE == (int) node_code_kind[variant]); } /***************************************************************************/ int isASymbNode(variant) int variant; { return (SYMBNODE == (int) node_code_kind[variant]); } /***************************************************************************/ int isABifNode(variant) int variant; { return (BIFNODE == (int) node_code_kind[variant]); } /***************************************************************************/ int isALoNode(variant) int variant; { return (LLNODE == (int) node_code_kind[variant]); } /***************************************************************************/ int hasTypeBaseType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("hasTypeBaseType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][2] == 'b') return TRUE; else return FALSE; } /***************************************************************************/ int isStructType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("isStructType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][0] == 's') return TRUE; else return FALSE; } /***************************************************************************/ int isPointerType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("isPointerType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][0] == 'p') return TRUE; else return FALSE; } /***************************************************************************/ int isUnionType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("isUnionType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][0] == 'u') return TRUE; else return FALSE; } /***************************************************************************/ int isEnumType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("EnumType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][0] == 'e') return TRUE; else return FALSE; } /***************************************************************************/ int hasTypeSymbol(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("hasTypeSymbol not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][1] == 's') return TRUE; else return FALSE; } /***************************************************************************/ int isAtomicType(variant) int variant; { if (!isATypeNode(variant)) { #if !__SPF Message("isAtomicType not applied to a type node", 0); #endif return FALSE; } if (info_type[variant][0] == 'a') return TRUE; else return FALSE; } /***************************************************************************/ int hasNodeASymb(variant) int variant; { if ((!isABifNode(variant)) && (!isALoNode(variant))) { #if !__SPF Message("hasNodeASymb not applied to a bif or low level node", 0); #endif return FALSE; } if (general_info[variant][2] == 's') return TRUE; else return FALSE; } /***************************************************************************/ int isNodeAConst(variant) int variant; { if ((!isABifNode(variant)) && (!isALoNode(variant))) { #if !__SPF Message("isNodeAConst not applied to a bif or low level node", 0); #endif return FALSE; } if (general_info[variant][1] == 'c') return TRUE; else return FALSE; } /***************************************************************************/ int isAStructDeclBif(variant) int variant; { if (!isABifNode(variant)) { #if !__SPF Message("isAStructDeclBif not applied to a bif", 0); #endif return FALSE; } if (general_info[variant][1] == 's') return TRUE; else return FALSE; } /***************************************************************************/ int isAUnionDeclBif(variant) int variant; { if (!isABifNode(variant)) { #if !__SPF Message("isAUnionDeclBif not applied to a bif", 0); #endif return FALSE; } if (general_info[variant][1] == 'u') return TRUE; else return FALSE; } /***************************************************************************/ int isAEnumDeclBif(variant) int variant; { if (!isABifNode(variant)) { #if !__SPF Message("isAEnumDeclBif not applied to a bif", 0); #endif return FALSE; } if (general_info[variant][1] == 'e') return TRUE; else return FALSE; } /***************************************************************************/ int isADeclBif(variant) int variant; { if (!isABifNode(variant)) { #if !__SPF Message("isADeclBif not applied to a bif", 0); #endif return FALSE; } if (general_info[variant][0] == 'd') return TRUE; else return FALSE; } /***************************************************************************/ int isAControlEnd(variant) int variant; { if (!isABifNode(variant)) { #if !__SPF Message("isAControlEnd not applied to a bif", 0); #endif return FALSE; } if (general_info[variant][0] == 'c') return TRUE; else return FALSE; } #ifdef __SPF extern void printLowLevelWarnings(const char *fileName, const int line, const wchar_t* messageR, const char *message, const int group); #endif /***************************************************************************/ void Message(char *s, int l) { if (l != 0) fprintf(stderr, "Warning : %s line %d\n", s, l); else fprintf(stderr, "Warning : %s\n", s); Warning_count++; #ifdef __SPF if (l == 0) l = 1; printLowLevelWarnings(cur_file->filename, l, NULL, s, 4001); if (strstr(s, "Error in")) { char buf[512]; sprintf(buf, "Internal error at line %d and file low_level.c\n", __LINE__); addToGlobalBufferAndPrint(buf); throw -1; } #endif } /***************************************************************************/ /* A set of functions for dealing with a free list for low_level node */ /***************************************************************************/ static int ExpressionNodeInFreeList = 0; static ptstack_chaining expressionFreeNodeList = NULL; void setFreeListForExpressionNode() { if (ExpressionNodeInFreeList) return; ExpressionNodeInFreeList = 1; if (!expressionFreeNodeList) { expressionFreeNodeList = (ptstack_chaining) xmalloc(sizeof(struct stack_chaining)); expressionFreeNodeList->first = NULL; expressionFreeNodeList->last = NULL; expressionFreeNodeList->prev = NULL; expressionFreeNodeList->level = 0; } } void resetFreeListForExpressionNode() { ExpressionNodeInFreeList = 0; } /* Added for garbage collection */ void libFreeExpression(ll) PTR_LLND ll; { ptchaining pt2; if (!ExpressionNodeInFreeList) return; if (!ll) return; if (!expressionFreeNodeList) { Message("Free list for expression node not defined\n",0); exit(1); } pt2 = (ptchaining) xmalloc(sizeof(struct chaining)); pt2->zone = (char *) ll; pt2->list = NULL; if (expressionFreeNodeList->first == NULL) expressionFreeNodeList->first = pt2; if (expressionFreeNodeList->last == NULL) expressionFreeNodeList->last = pt2; else { expressionFreeNodeList->last->list = pt2; expressionFreeNodeList->last = pt2; } } char *allocateFreeListNodeExpression() { char *pt; ptchaining pt2; if (!ExpressionNodeInFreeList) return xmalloc(sizeof (struct llnd)); if (!expressionFreeNodeList) { Message("Free list for expression node not defined\n",0); exit(1); } if (expressionFreeNodeList->first == NULL) return xmalloc(sizeof (struct llnd)); pt2 = expressionFreeNodeList->first; if (expressionFreeNodeList->first == expressionFreeNodeList->last) { expressionFreeNodeList->first = NULL; expressionFreeNodeList->last = NULL; } else expressionFreeNodeList->first = pt2->list; pt = pt2->zone; #ifdef __SPF removeFromCollection(pt2); #endif free(pt2); memset((char *) pt, 0 , sizeof (struct llnd)); return pt; } /***************************************************************************/ POINTER newNode(code) int code; { PTR_BFND tb = NULL; PTR_LLND tl = NULL; PTR_TYPE tt = NULL; PTR_SYMB ts = NULL; PTR_LABEL tlab; PTR_CMNT tcmnt; PTR_BLOB tbl; int length; int kind; if (code == CMNT_KIND) { /* lets create a comment */ length = sizeof(struct cmnt); tcmnt = (PTR_CMNT)xmalloc(length); memset((char *)tcmnt, 0, length); CMNT_ID(tcmnt) = ++CUR_FILE_NUM_CMNT(); CMNT_NEXT(tcmnt) = PROJ_FIRST_CMNT(); PROJ_FIRST_CMNT() = tcmnt; return (POINTER)tcmnt; } if (code == LABEL_KIND) { /* lets create a label */ PTR_LABEL last; /* allocating space... PHB */ length = sizeof (struct Label); tlab = (PTR_LABEL) xmalloc(length); memset((char *) tlab, 0, length); LABEL_ID(tlab) = ++CUR_FILE_NUM_LABEL(); if ((last=getLastLabel())) /* is there an existing label? PHB */ { LABEL_NEXT(last)=tlab; return (POINTER) tlab; } else /* There is no existing label, make one PHB */ { LABEL_NEXT(tlab) = LBNULL; PROJ_FIRST_LABEL() = tlab; /* set pointer to first label */ return (POINTER) tlab; } } if (code == BLOB_KIND) { length = sizeof (struct blob); tbl = (PTR_BLOB) xmalloc (length); memset((char *) tbl, 0, length); CUR_FILE_NUM_BLOBS()++; return (POINTER) tbl; } kind = (int) node_code_kind[(int) code]; switch (kind) { case BIFNODE: length = sizeof (struct bfnd); break; case LLNODE : length = sizeof (struct llnd); break; case SYMBNODE: length = sizeof (struct symb); break; case TYPENODE: length = sizeof (struct data_type); break; default: Message("Node inconnu",0); } switch (kind) { case BIFNODE: tb = (PTR_BFND) xmalloc(length); memset((char *) tb, 0, length); BIF_ID (tb) = ++CUR_FILE_NUM_BIFS (); number_of_bif_node++; /*BIF_ID (tb) = number_of_bif_node++;*/ BIF_CODE(tb) = code; BIF_FILE_NAME(tb) = CUR_FILE_HEAD_FILE();/* recently added, to check */ CUR_FILE_CUR_BFND() = tb; BIF_LINE(tb) = 0; /* set to know that this is a new node */ break; case LLNODE : if (ExpressionNodeInFreeList) tl = (PTR_LLND) allocateFreeListNodeExpression(); else { tl = (PTR_LLND) xmalloc(length); memset((char *) tl, 0, length); } NODE_ID (tl) = ++CUR_FILE_NUM_LLNDS(); NODE_NEXT (tl) = LLNULL; number_of_ll_node++; if (CUR_FILE_NUM_LLNDS() == 1) PROJ_FIRST_LLND () = tl; else NODE_NEXT (CUR_FILE_CUR_LLND()) = tl; CUR_FILE_CUR_LLND() = tl; NODE_CODE(tl) = code; break; case SYMBNODE: ts = (PTR_SYMB) xmalloc(length); memset((char *) ts, 0, length); number_of_symb_node++; SYMB_ID (ts) = ++CUR_FILE_NUM_SYMBS(); SYMB_CODE(ts) = code; if (CUR_FILE_NUM_SYMBS() == 1) PROJ_FIRST_SYMB () = ts; else SYMB_NEXT (CUR_FILE_CUR_SYMB()) = ts; CUR_FILE_CUR_SYMB() = ts; SYMB_NEXT (ts) = NULL; SYMB_SCOPE (ts) = PROJ_FIRST_BIF();/* the default value */ break; case TYPENODE: /*tt = (PTR_TYPE) alloc_type ( cur_file ); xmalloc(length); number_of_type_node++; TYPE_ID (tt) = number_of_type_node++; TYPE_NEXT (tt) = NULL;*/ tt = (PTR_TYPE) xmalloc (length); memset((char *) tt, 0, length); number_of_type_node++; TYPE_ID (tt) = ++CUR_FILE_NUM_TYPES(); TYPE_CODE (tt) = code; TYPE_NEXT (tt) = NULL; if (CUR_FILE_NUM_TYPES () == 1) PROJ_FIRST_TYPE() = tt; else TYPE_NEXT (CUR_FILE_CUR_TYPE()) = tt; CUR_FILE_CUR_TYPE() = tt; /* for VPC very ugly and should be removed later */ if (code == T_POINTER) TYPE_TEMPLATE_DUMMY1(tt) = 1 ; if (code == T_REFERENCE) TYPE_TEMPLATE_DUMMY1(tt) = 1 ; break; default: Message("Node inconnu",0); } switch (kind) { case BIFNODE: return (POINTER) tb; case LLNODE : return (POINTER) tl; case SYMBNODE: return (POINTER) ts; case TYPENODE: return (POINTER) tt; default: Message("Node inconnu",0); } return NULL; } /***************************************************************************/ PTR_LLND copyLlNode(node) PTR_LLND node; { PTR_LLND t; int code; if (!node) return NULL; code = NODE_CODE (node); if (node_code_kind[(int) code] != LLNODE) Message("bif_copy_node != low_level_node",0); t = (PTR_LLND) newNode (code); NODE_SYMB(t) = NODE_SYMB(node); NODE_TYPE(t) = NODE_TYPE(node); NODE_OPERAND0(t) = copyLlNode(NODE_OPERAND0(node)); NODE_OPERAND1(t) = copyLlNode(NODE_OPERAND1(node)); return t; } /***************************************************************************/ PTR_LLND makeInt(low) int low; { PTR_LLND t = (PTR_LLND) newNode(INT_VAL); NODE_TYPE(t) = NULL; NODE_INT_CST_LOW (t) = low; return t; } /* Originally coded by fbodin, but the code used K&R varargs conventions, I have rewritten the code to use ANSI conventions (phb) */ /***************************************************************************/ PTR_LLND newExpr(int code, PTR_TYPE ntype, ... ) { va_list p; PTR_LLND t; int length; /* Create a new node of type 'code' */ t = (PTR_LLND) newNode(code); NODE_TYPE(t) = ntype; /* calculate the number of args required for this type of node */ length = node_code_length[code]; /* Set pointer p to the very first variable argument in list */ va_start(p,ntype); if (hasNodeASymb(code)) { /* Extract third argument (type PTR_SYMB), inc arg pointer p */ PTR_SYMB arg0 = va_arg(p, PTR_SYMB); NODE_SYMB(t) = arg0; } if (length != 0) { if (length == 2) { /* This is equivalent to the loop below, but faster. */ /* Extract another argument (type PTR_LLND), inc arg pointer p */ PTR_LLND arg0 = va_arg(p, PTR_LLND); /* Extract another argument (type PTR_LLND), inc arg pointer p */ PTR_LLND arg1 = va_arg(p, PTR_LLND); NODE_OPERAND0(t) = arg0; NODE_OPERAND1(t) = arg1; va_end (p); return t; } else if (length == 1) { /* This is equivalent to the loop below, but faster. */ /* Extract another argument (type PTR_LLND), inc arg pointer p */ PTR_LLND arg0 = va_arg(p, PTR_LLND); NODE_OPERAND0(t) = arg0; va_end(p); return t; } else Message("A low level node have more than two operands",0); } va_end(p); return t; } /***************************************************************************/ PTR_SYMB newSymbol(code, name, type) int code; char *name; PTR_TYPE type; { PTR_SYMB t; char *str; if(name){ str = (char *) xmalloc(strlen(name) +1); strcpy(str,name); } else str=NULL; t = (PTR_SYMB) newNode (code); SYMB_IDENT (t) = str; SYMB_TYPE (t) = type; return t; } /***************************************************************************/ int Check_Lang_C(proj) PTR_PROJ proj; { PTR_FILE ptf; PTR_BLOB ptb; if (!proj) return TRUE; for (ptb = PROJ_FILE_CHAIN (proj); ptb ; ptb = BLOB_NEXT (ptb)) { ptf = (PTR_FILE) BLOB_VALUE (ptb); /* if (debug) fprintf(stderr,"%s\n",FILE_FILENAME (ptf)); */ if (FILE_LANGUAGE (ptf) != CSrc) return(FALSE); } return(TRUE); } /***************************************************************************/ int Check_Lang_Fortran(proj) PTR_PROJ proj; { PTR_FILE ptf; PTR_BLOB ptb; if (!proj) return FALSE; for (ptb = PROJ_FILE_CHAIN (proj); ptb ; ptb = BLOB_NEXT (ptb)) { ptf = (PTR_FILE) BLOB_VALUE (ptb); /* if (debug) fprintf(stderr,"%s\n",FILE_FILENAME (ptf)); */ if (FILE_LANGUAGE(ptf) != ForSrc) return(FALSE); } return(TRUE); } /* Procedure for unparse a program use when debug is required the current project is taking */ /***************************************************************************/ void UnparseProgram(fout) FILE *fout; { /* char *s; PTR_BLOB b, bl; PTR_FILE f; */ /*podd 15.03.99*/ if (Check_Lang_Fortran(cur_proj)) { Init_Unparser(); fprintf(fout,"%s",filter(Tool_Unparse_Bif(PROJ_FIRST_BIF()))); } else { Init_Unparser(); fprintf(fout,"%s",Tool_Unparse_Bif(PROJ_FIRST_BIF())); } } /***************************************************************************/ void UnparseProgram_ThroughAllocBuffer(fout,filept,size) FILE *fout; PTR_FILE filept; int size; { /* char *s; PTR_BLOB b, bl; PTR_FILE f; */ /*podd 29.01.07*/ //SetCurrentFileTo(filept); //SwitchToFile(GetFileNumWithPt(filept)); if (Check_Lang_Fortran(cur_proj)) { Init_Unparser(); BufferAllocate(size); fprintf(fout,"%s",filter(Tool_Unparse_Bif(PROJ_FIRST_BIF()))); } else { Init_Unparser(); fprintf(fout,"%s",Tool_Unparse_Bif(PROJ_FIRST_BIF())); } } /* Procedure for unparse a program use when debug is required the current project is taking */ /***************************************************************************/ void UnparseBif(bif) PTR_BFND bif; { /* char *s; PTR_BLOB b, bl; */ /* podd 15.03.99*/ if (Check_Lang_Fortran(cur_proj)) { Init_Unparser(); printf("%s",filter(Tool_Unparse_Bif(bif))); } else { Init_Unparser(); printf("%s",(Tool_Unparse_Bif(bif))); } } /***************************************************************************/ /* podd 28.01.07 */ /*change podd 16.12.11*/ char *UnparseBif_Char(bif,lang) PTR_BFND bif; int lang; /* ForSrc=0 - Fortran language, CSrc=1 - C language */ { char *s; /* PTR_BLOB b, bl; */ /* podd 15.03.99*/ if (Check_Lang_Fortran(cur_proj) && lang != CSrc) /*podd 16.12.11*/ { Init_Unparser(); s = filter(Tool_Unparse_Bif(bif)); } else { if(lang == CSrc) Set_Function_Language(CSrc); Init_Unparser(); s = Tool_Unparse_Bif(bif); if(lang == CSrc) Unset_Function_Language(); } return(s); } /* Kataev N.A. 03.09.2013 base on UnparseBif_Char with change podd 16.12.11 Kataev N.A. 19.10.2013 fix */ char *UnparseLLND_Char(llnd) PTR_LLND llnd; { char *s; Init_Unparser(); s = Tool_Unparse2_LLnode(llnd); return(s); } /* Procedure for unparse a program use when debug is required the current project is taking */ /***************************************************************************/ void UnparseLLND(ll) PTR_LLND ll; { Init_Unparser(); printf("%s",Tool_Unparse2_LLnode(ll)); } /***************************************************************************/ char* UnparseTypeBuffer(type) PTR_TYPE type; { Init_Unparser(); return Tool_Unparse_Type(type); } /***************************************************************************/ int open_proj_toolbox(char* proj_name, char* proj_file) { char* mem[MAX_FILE]; /* for file in the project */ int no = 0; /* number of file in the project */ int c; FILE* fd; /* file descriptor for project */ char** p, * t; char* tmp, tmpa[3000]; tmp = &(tmpa[0]); if ((fd = fopen(proj_file, "r")) == NULL) return -1; p = mem; t = tmp; while ((c = getc(fd)) != EOF) { //if (c != ' ') /* assum no blanks in filename */ { if (c == '\n') { if (t != tmp) { /* not a blank line */ *t = '\0'; *p = (char*)malloc((unsigned)(strlen(tmp) + 1)); #ifdef __SPF addToCollection(__LINE__, __FILE__, *p, 0); #endif strcpy(*p++, tmp); t = tmp; } } else *t++ = c; } } fclose(fd); no = p - mem; if (no > 0) { /* Now make it the active project */ if ((cur_proj = OpenProj(proj_name, no, mem))) { cur_file = (PTR_FILE)BLOB_VALUE(CUR_PROJ_FILE_CHAIN()); pointer_on_file_proj = cur_file; return 0; } else { fprintf(stderr, "-2 Cannot open project\n"); return -2; } } else { fprintf(stderr, "-3 No files in the project\n"); return -3; } } int open_proj_files_toolbox(char* proj_name, char** file_list, int no) { if (no > 0) { /* Now make it the active project */ if ((cur_proj = OpenProj(proj_name, no, file_list))) { cur_file = (PTR_FILE)BLOB_VALUE(CUR_PROJ_FILE_CHAIN()); pointer_on_file_proj = cur_file; return 0; } else { fprintf(stderr, "-2 Cannot open project\n"); return -2; } } else { fprintf(stderr, "-3 No files in the project\n"); return -3; } } static int ToolBOX_INIT = 0; /***************************************************************************/ void Reset_Tool_Box() { Init_Tool_Box(); } /***************************************************************************/ void Reset_Bif_Next() { PTR_BLOB ptb; if (cur_proj) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { pointer_on_file_proj = (PTR_FILE) BLOB_VALUE (ptb); Redo_Bif_Next_Chain(PROJ_FIRST_BIF()); } } else if(pointer_on_file_proj) Redo_Bif_Next_Chain(PROJ_FIRST_BIF()); } /***************************************************************************/ int Init_Tool_Box() { PTR_BLOB ptb; pointer_on_file_proj = cur_file; number_of_type_node = CUR_FILE_NUM_TYPES() + 1; number_of_ll_node = CUR_FILE_NUM_LLNDS() + 1; number_of_bif_node = CUR_FILE_NUM_BIFS() + 1; number_of_symb_node = CUR_FILE_NUM_SYMBS() + 1; if (CUR_FILE_NAME()) strcpy(Current_File_name, CUR_FILE_NAME()); if (ToolBOX_INIT) return 0; ToolBOX_INIT = 1; make_a_malloc_stack(); /* initialisation des noeuds */ #define DEFNODECODE(SYM, NAME, TYPE, LENGTH, NT,f1,f2,f3,f4,f5) node_code_type[SYM] = TYPE; #include"bif_node.def" #undef DEFNODECODE #define DEFNODECODE(SYM, NAME, TYPE, LENGTH, NT,f1,f2,f3,f4,f5) node_code_length[SYM] =LENGTH; #include"bif_node.def" #undef DEFNODECODE #define DEFNODECODE(SYM, NAME, TYPE, LENGTH, NT,f1,f2,f3,f4,f5) node_code_kind[SYM] = NT; #include"bif_node.def" #undef DEFNODECODE /* set special table for symbol and type */ #define DEFNODECODE(SYMB,f1,f2,f3,f4,f5) info_type[SYMB][0] = f1; info_type[SYMB][1] = f2; info_type[SYMB][2] = f3; info_type[SYMB][3] = f4; info_type[SYMB][4] = f5; #include"type.def" #undef DEFNODECODE #define DEFNODECODE(SYMB,f1,f2,f3,f4,f5) info_symb[SYMB][0] = f1; info_symb[SYMB][1] = f2; info_symb[SYMB][2] = f3; info_symb[SYMB][3] = f4; info_symb[SYMB][4] = f5; #include"symb.def" #undef DEFNODECODE #define DEFNODECODE(SYM, NAME, TYPE, LENGTH, NT,f1,f2,f3,f4,f5) general_info[SYM][0] = f1; general_info[SYM][1] = f2; general_info[SYM][2] = f3; general_info[SYM][3] = f4; general_info[SYM][4] = f5; #include"bif_node.def" #undef DEFNODECODE if (cur_proj) { for (ptb = PROJ_FILE_CHAIN(cur_proj); ptb; ptb = BLOB_NEXT(ptb)) { pointer_on_file_proj = (PTR_FILE)BLOB_VALUE(ptb); Redo_Bif_Next_Chain_Internal(PROJ_FIRST_BIF()); } } pointer_on_file_proj = cur_file; number_of_type_node = CUR_FILE_NUM_TYPES() + 1; number_of_ll_node = CUR_FILE_NUM_LLNDS() + 1; number_of_bif_node = CUR_FILE_NUM_BIFS() + 1; number_of_symb_node = CUR_FILE_NUM_SYMBS() + 1; return 1; } /* For debug */ /***************************************************************************/ void writeDepFileInDebugdep() { PTR_BFND thebif; int i; thebif = PROJ_FIRST_BIF(); i = 1; for (;thebif;thebif=BIF_NEXT(thebif), i++) BIF_ID(thebif) = i; CUR_FILE_NUM_BIFS() = i-1; if (write_nodes(cur_file,"debug.dep") < 0) Message("Error, write_nodes() failed (000)",0); } int isBlankString(char *str) {int i; for(i=0;i<72;i++) if(str[i] !=' ') return(0); return(1); } /* this function converts a letter to uppercase except char strings (text inside quotes) */ char to_upper_case (char c, int *quote) { if(c == '\'' || c == '\"') { if(*quote == c) *quote = 0; else if(*quote==0) *quote = c; return c; } if(c >= 0 && islower(c) && *quote==0) return toupper(c); return c; } char* filter(char *s) { char c; int i = 1, quote = 0; // 14.10.2016 Kolganov. Switch constant buffer to dynamic int temp_size = 4096; char *temp = (char*)malloc(sizeof(char) * temp_size); #ifdef __SPF addToCollection(__LINE__, __FILE__,temp, 0); #endif // out_line_length = 132 if -ffo option is used or out_line_length = 72 if -uniForm option is used int temp_i = 0; int buf_i = 0; int commentline = 0; char *resul, *init; int OMP, DVM, SPF; /*OMP*/ OMP = DVM = SPF = 0; if (!s) return NULL; if (strlen(s) == 0) return s; make_a_malloc_stack(); //XXX: result is not free at the end of procedure!! resul = (char *)mymalloc(2 * strlen(s)); memset(resul, 0, 2 * strlen(s)); init = resul; c = s[0]; if ((c != ' ') && (c != '\n') && (c != '0') && (c != '1') && (c != '2') && (c != '3') && (c != '4') && (c != '5') && (c != '6') && (c != '7') && (c != '8') && (c != '9')) commentline = 1; else commentline = 0; if (commentline) { if ( (s[1] == '$') && (s[2] == 'O') && (s[3] == 'M') && (s[4] == 'P')) { OMP = 1; DVM = SPF = 0; } else if ( (s[1] == '$') && (s[2] == 'S') && (s[3] == 'P') && (s[4] == 'F')) { SPF = 1; OMP = DVM = 0; } else if (s[1] == '$') { OMP = 2; DVM = SPF = 0; } else if ( (s[1] == 'D') && (s[2] == 'V') && (s[3] == 'M') && (s[4] == '$')) { DVM = 1; OMP = SPF = 0; } else OMP = DVM = SPF = 0; } temp_i = 0; i = 0; buf_i = 0; while (c != '\0') { c = s[i]; temp[buf_i] = out_upper_case && (!commentline || DVM || SPF || OMP) ? to_upper_case(c,"e) : c; if (c == '\n') { if (buf_i + 1 > temp_size) { temp_size *= 2; #ifdef __SPF removeFromCollection(temp); #endif temp = (char*)realloc(temp, sizeof(char) * temp_size); #ifdef __SPF addToCollection(__LINE__, __FILE__,temp, 0); #endif } temp[buf_i + 1] = '\0'; sprintf(resul, "%s", temp); resul = resul + strlen(temp); temp_i = -1; buf_i = -1; if ((s[i + 1] != ' ') && (s[i + 1] != '\n') && (s[i + 1] != '0') && (s[i + 1] != '1') && (s[i + 1] != '2') && (s[i + 1] != '3') && (s[i + 1] != '4') && (s[i + 1] != '5') && (s[i + 1] != '6') && (s[i + 1] != '7') && (s[i + 1] != '8') && (s[i + 1] != '9')) commentline = 1; else commentline = 0; if (commentline) { if ( (s[i+2] == '$') && (s[i+3] == 'O') && (s[i+4] == 'M') && (s[i+5] == 'P')) { OMP = 1; DVM = SPF = 0; } else if ( (s[i+2] == '$') && (s[i+3] == 'S') && (s[i+4] == 'P') && (s[i+5] == 'F')) { SPF = 1; OMP = DVM = 0; } else if (s[i + 2] == '$') { OMP = 2; DVM = SPF = 0; } else { if ( (s[i+2] == 'D') && (s[i+3] == 'V') && (s[i+4] == 'M') && (s[i+5] == '$')) { DVM = 1; OMP = SPF = 0; } else OMP = DVM = SPF = 0; } } } else { if (((!out_free_form && temp_i == 71) || (out_free_form && !out_line_unlimit && temp_i == out_line_length - 1)) && !commentline && (s[i + 1] != '\n')) { if (buf_i + 1 > temp_size) { temp_size *= 2; #ifdef __SPF removeFromCollection(temp); #endif temp = (char*)realloc(temp, sizeof(char) * temp_size); #ifdef __SPF addToCollection(__LINE__, __FILE__,temp, 0); #endif } /* insert where necessary */ temp[buf_i + 1] = '\0'; if (out_free_form) { sprintf(resul, "%s&\n", temp); resul = resul + strlen(temp) + 2; } else { sprintf(resul, "%s\n", temp); resul = resul + strlen(temp) + 1; } if (!out_free_form && isBlankString(temp)) /*24.06.13*/ /* string of 72 blanks in fixed form */ sprintf(resul, " "); else sprintf(resul, " &"); resul = resul + strlen(" &"); commentline = 0; memset(temp, 0, sizeof(char) * temp_size); temp_i = strlen(" &") - 1; buf_i = -1; } if (((!out_free_form && temp_i == 71) || (out_free_form && !out_line_unlimit && temp_i == out_line_length - 1)) && commentline && (s[i + 1] != '\n') && ((OMP == 1) || (OMP == 2) || (DVM == 1) || (SPF == 1))) /*07.08.17*/ { if (buf_i + 1 > temp_size) { temp_size *= 2; #ifdef __SPF removeFromCollection(temp); #endif temp = (char*)realloc(temp, sizeof(char) * temp_size); #ifdef __SPF addToCollection(__LINE__, __FILE__,temp, 0); #endif } temp[buf_i + 1] = '\0'; if (out_free_form) { sprintf(resul, "%s&\n", temp); resul = resul + strlen(temp) + 2; } else { sprintf(resul, "%s\n", temp); resul = resul + strlen(temp) + 1; } if (OMP == 1) { sprintf(resul, "!$OMP&"); resul = resul + strlen("!$OMP&"); temp_i = strlen("!$OMP&") - 1; } if (OMP == 2) { sprintf(resul, "!$ &"); resul = resul + strlen("!$ &"); temp_i = strlen("!$ &") - 1; } if (DVM == 1) { sprintf(resul, "!DVM$&"); resul = resul + strlen("!DVM$&"); temp_i = strlen("!DVM$&") - 1; } if (SPF == 1) { sprintf(resul, "!$SPF&"); resul = resul + strlen("!$SPF&"); temp_i = strlen("!$SPF&") - 1; } memset(temp, 0, sizeof(char) * temp_size); temp_i = strlen(" +") - 1; buf_i = -1; } } i++; temp_i++; buf_i++; if (buf_i > temp_size) { temp_size *= 2; #ifdef __SPF removeFromCollection(temp); #endif temp = (char*)realloc(temp, sizeof(char) * temp_size); #ifdef __SPF addToCollection(__LINE__, __FILE__,temp, 0); #endif } } #ifdef __SPF removeFromCollection(temp); #endif free(temp); return init; } /* BW, june 1994 this function is used in duplicateStmtsBlock to determine how many bif nodes need to be copied */ /***************************************************************************/ int numberOfBifsInBlobList(blob) PTR_BLOB blob; { PTR_BFND cur_bif; if(!blob) return 0; cur_bif = BLOB_VALUE(blob); return (numberOfBifsInBlobList(BIF_BLOB1(cur_bif)) + numberOfBifsInBlobList(BIF_BLOB2(cur_bif)) + numberOfBifsInBlobList(BLOB_NEXT(blob)) + 1); } /***************************************************************************/ int findBifInList1(bif_source, bif_cherche) PTR_BFND bif_source, bif_cherche; { PTR_BLOB temp; if ((bif_cherche == NULL) || (bif_source == NULL)) return FALSE; for (temp = BIF_BLOB1 (bif_source); temp ; temp = BLOB_NEXT (temp)) if (BLOB_VALUE (temp) == bif_cherche) return TRUE; return FALSE; } /***************************************************************************/ int findBifInList2(bif_source, bif_cherche) PTR_BFND bif_source, bif_cherche; { PTR_BLOB temp; if ((bif_cherche == NULL) || (bif_source == NULL)) return FALSE; for (temp = BIF_BLOB2 (bif_source); temp ; temp = BLOB_NEXT (temp)) if (BLOB_VALUE (temp) == bif_cherche) return TRUE; return FALSE; } /***************************************************************************/ int findBif(bif_source, bif_target, i) PTR_BFND bif_source, bif_target; int i; { switch(i){ case 0: if (findBifInList1 (bif_source, bif_target)) return TRUE; else return findBifInList2 (bif_source, bif_target); case 1: return findBifInList1 (bif_source, bif_target); case 2: return findBifInList2 (bif_source, bif_target); } return 0; } /***************************************************************************/ PTR_BLOB appendBlob(b1, b2) PTR_BLOB b1, b2; { if (b1) { PTR_BLOB p, q; for (p = b1; p; p = BLOB_NEXT (p)) /* skip to the end of b1 */ q = p; BLOB_NEXT (q) = b2; } else b1 = b2; return b1; } /* *delete a bif node from the list of blob node */ /***************************************************************************/ PTR_BFND deleteBfndFromBlobAndLabel(bf,label) PTR_BFND bf; PTR_LABEL label; { PTR_BLOB first; PTR_BLOB bl1, bl2; if (label) { first = LABEL_UD_CHAIN(label); if (first && (BLOB_VALUE (first) == bf)) { bl2 = first; LABEL_UD_CHAIN(label) = BLOB_NEXT (first); return (BLOB_VALUE (bl2)); } for (bl1 = bl2 = first; bl1; bl1 = BLOB_NEXT (bl1)) { if (BLOB_VALUE (bl1) == bf) { BLOB_NEXT (bl2) = BLOB_NEXT (bl1); return (BLOB_VALUE (bl2)); } bl2 = bl1; } return NULL; } return NULL; } /***************************************************************************/ PTR_BLOB lookForBifInBlobList(first, bif) PTR_BLOB first; PTR_BFND bif; { PTR_BLOB tail; if (first == NULL) return NULL; for (tail = first; tail; tail = BLOB_NEXT(tail) ) { if (BLOB_VALUE(tail) == bif) return tail; } return NULL; } /***************************************************************************/ PTR_BFND childfInBlobList(first, num) PTR_BLOB first; int num; { PTR_BLOB tail; int len = 0; if (first == NULL) return NULL; for (tail = first; tail; tail = BLOB_NEXT(tail) ) { if (len == num) return BLOB_VALUE(tail); len++; } return NULL; } /***************************************************************************/ int blobListLength(first) PTR_BLOB first; { PTR_BLOB tail; int len = 0; if (first == NULL) return(0); for (tail = first; tail; tail = BLOB_NEXT(tail) ) len++; return(len); } /***************************************************************************/ PTR_BFND lastBifInBlobList1(noeud) PTR_BFND noeud; { PTR_BLOB bl1 = NULL; if (!noeud ) return NULL; /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB1(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } if (bl1) return BLOB_VALUE(bl1); else return NULL; } /***************************************************************************/ PTR_BFND lastBifInBlobList2(noeud) PTR_BFND noeud; { PTR_BLOB bl1 = NULL; if (!noeud ) return NULL; /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB2(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } if (bl1) return BLOB_VALUE(bl1); else return NULL; } /***************************************************************************/ PTR_BFND lastBifInBlobList(noeud) PTR_BFND noeud; { if (!BIF_INDEX(noeud)) return lastBifInBlobList1( noeud); else return lastBifInBlobList2( noeud); } /***************************************************************************/ PTR_BLOB lastBlobInBlobList1(noeud) PTR_BFND noeud; { PTR_BLOB bl1 = NULL; if (!noeud ) return NULL; /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB1(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } if (bl1) return bl1; else return NULL; } /***************************************************************************/ PTR_BLOB lastBlobInBlobList2(noeud) PTR_BFND noeud; { PTR_BLOB bl1 = NULL; if (!noeud ) return NULL; /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB2(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } if (bl1) return bl1; else return NULL; } /***************************************************************************/ PTR_BLOB lastBlobInBlobList(noeud) PTR_BFND noeud; { if (!BIF_INDEX(noeud)) return lastBlobInBlobList1( noeud); else return lastBlobInBlobList2( noeud); } /* * * append dans la blob liste d'un noeud bif, un noeud bif * */ /***************************************************************************/ int appendBfndToList1(biftoinsert, noeud) PTR_BFND biftoinsert, noeud; { PTR_BLOB bl1; if (!noeud || !biftoinsert) return 0; if (BIF_BLOB1(noeud) == NULL) { BIF_BLOB1(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE(BIF_BLOB1(noeud)) = biftoinsert; BLOB_NEXT(BIF_BLOB1(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB1(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } BLOB_NEXT(bl1) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE(BLOB_NEXT(bl1)) = biftoinsert; BIF_CP(biftoinsert) = noeud; BLOB_NEXT(BLOB_NEXT(bl1)) = NULL; } return 1; } /***************************************************************************/ int appendBfndToList2(biftoinsert, noeud) PTR_BFND biftoinsert, noeud; { PTR_BLOB bl1; if (!noeud || !biftoinsert) return 0; if (BIF_BLOB2(noeud) == NULL) { BIF_BLOB2(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB2(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB2(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { /* on va cherche le dernier dans la liste */ for (bl1 = BIF_BLOB2(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_NEXT(bl1) == NULL) break; } BLOB_NEXT(bl1) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE(BLOB_NEXT(bl1)) = biftoinsert; BLOB_NEXT(BLOB_NEXT(bl1)) = NULL; BIF_CP(biftoinsert) = noeud; } return 1; } /* replace chain_up() */ /***************************************************************************/ int appendBfndToList(noeud, biftoinsert) PTR_BFND biftoinsert, noeud; { /* use the index field to set the right blob node list */ if (!noeud || !biftoinsert) return 0; if (!BIF_INDEX(noeud)) return appendBfndToList1(biftoinsert, noeud); else return appendBfndToList2(biftoinsert, noeud); } /***************************************************************************/ int firstBfndInList1(biftoinsert, noeud) PTR_BFND biftoinsert, noeud; { PTR_BLOB bl2; if (!noeud || !biftoinsert) return 0; if (BIF_BLOB1(noeud) == NULL) { BIF_BLOB1(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB1(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB1(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { bl2 = BIF_BLOB1(noeud); BIF_BLOB1(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB1(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB1(noeud)) = bl2 ; BIF_CP(biftoinsert) = noeud; } return 1; } /***************************************************************************/ int firstBfndInList2(biftoinsert, noeud) PTR_BFND biftoinsert, noeud; { PTR_BLOB bl2; if (!noeud || !biftoinsert) return 0; if (BIF_BLOB2(noeud) == NULL) { BIF_BLOB2(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB2(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB2(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { bl2 = BIF_BLOB2(noeud); BIF_BLOB2(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB2(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB2(noeud)) = bl2 ; BIF_CP(biftoinsert) = noeud; } return 1; } /***************************************************************************/ int insertBfndInList1(biftoinsert, current, noeud) PTR_BFND biftoinsert, noeud,current; { PTR_BLOB bl1 = NULL, bl2; if (!noeud || !biftoinsert || !current) return 0; if (BIF_BLOB1(noeud) == NULL) { BIF_BLOB1(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB1(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB1(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { /* on va cherche current dans la liste */ for (bl1 = BIF_BLOB1(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_VALUE(bl1) == current) break; } if (!bl1) { Message("insertBfndInList1 failed",0); return FALSE; } bl2 = BLOB_NEXT(bl1); BLOB_NEXT(bl1) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BLOB_NEXT(bl1)) = biftoinsert; BLOB_NEXT (BLOB_NEXT(bl1)) = bl2; BIF_CP(biftoinsert) = noeud; } return TRUE; } /***************************************************************************/ int insertBfndInList2(biftoinsert, current, noeud) PTR_BFND biftoinsert, noeud,current; { PTR_BLOB bl1 = NULL, bl2; if (!noeud || !biftoinsert || !current) return 0; if (BIF_BLOB2(noeud) == NULL) { BIF_BLOB2(noeud) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BIF_BLOB2(noeud)) = biftoinsert; BLOB_NEXT (BIF_BLOB2(noeud)) = NULL; BIF_CP(biftoinsert) = noeud; } else { /* on va cherche current dans la liste */ for (bl1 = BIF_BLOB2(noeud); bl1; bl1 = BLOB_NEXT(bl1)) { if (BLOB_VALUE(bl1) == current) break; } if (!bl1) { Message("insertBfndInList2 failed",0); abort(); } bl2 = BLOB_NEXT(bl1); BLOB_NEXT(bl1) = (PTR_BLOB) newNode (BLOB_KIND); BLOB_VALUE (BLOB_NEXT(bl1)) = biftoinsert; BLOB_NEXT(BLOB_NEXT(bl1)) = bl2 ; BIF_CP(biftoinsert) = noeud; } return 1; } /* enleve in noeud de la liste de bif node si s'y trouve */ /***************************************************************************/ PTR_BLOB deleteBfndFrom(b1,b2) PTR_BFND b1,b2; { PTR_BLOB temp, last, res = NULL; if (!b1) return NULL; last = NULL; for (temp = BIF_BLOB1(b1) ; temp ; temp = BLOB_NEXT (temp)) { if (BLOB_VALUE(temp) == b2) { res = temp; if (last == NULL) { BIF_BLOB1(b1) = BLOB_NEXT (temp); break; } else { BLOB_NEXT (last) = BLOB_NEXT (temp); break; } } last = temp; } if (!res) { last = NULL; for (temp = BIF_BLOB2(b1) ; temp ; temp = BLOB_NEXT (temp)) { if (BLOB_VALUE(temp) == b2) { res = temp; if (last == NULL) { BIF_BLOB2(b1) = BLOB_NEXT (temp); break; } else { BLOB_NEXT (last) = BLOB_NEXT (temp); break; } } last = temp; } } return res; } /***************************************************************************/ PTR_BFND getNodeBefore(b) PTR_BFND b; { PTR_BFND temp, first; if (!b) return NULL; if (BIF_CP(b)) first = BIF_CP(b); else first = PROJ_FIRST_BIF(); for (temp = first; temp ; temp = BIF_NEXT(temp)) { if (BIF_NEXT(temp) == b) return temp; } if (BIF_CP(b)) { for (temp = BIF_CP(BIF_CP(b)); temp ; temp = BIF_NEXT(temp)) { if (BIF_NEXT(temp) == b) return temp; } } if (debug) Message("Node Before not found ",0); return NULL; } /***************************************************************************/ void updateControlParent(first,last,cp) PTR_BFND first,cp,last; { PTR_BFND temp; for (temp = first; temp && (temp != last); temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) BIF_CP(temp) = cp; } if (!isItInSection(first,last,BIF_CP(last))) BIF_CP(last) = cp; } /***************************************************************************/ PTR_BFND getWhereToInsertInBfnd(where,cpin) PTR_BFND where, cpin; { PTR_BFND temp; PTR_BLOB blob; if (!cpin || !where) return NULL; if (findBifInList1 (cpin, where)) return where; if (findBifInList2 (cpin, where)) return where; for (blob = BIF_BLOB1(cpin) ; blob; blob = BLOB_NEXT(blob)) { temp = getWhereToInsertInBfnd(where,BLOB_VALUE(blob)); if (temp) return BLOB_VALUE(blob); } for (blob = BIF_BLOB2(cpin) ; blob; blob = BLOB_NEXT(blob)) { temp = getWhereToInsertInBfnd(where,BLOB_VALUE(blob)); if (temp) return BLOB_VALUE(blob); } return NULL; } /* Given a node where we want to insert another node, compute the control parent */ /***************************************************************************/ PTR_BFND computeControlParent(where) PTR_BFND where; { PTR_BFND cp; if (!where) { Message("where not defined in computeControlParent: abort()",0); abort(); } if (!BIF_CP(where)) { switch(BIF_CODE(where)) { /* node that can be a bif control parent */ case GLOBAL : case PROG_HEDR : case PROC_HEDR : case PROS_HEDR : case BASIC_BLOCK : case IF_NODE : case WHERE_BLOCK_STMT : case LOOP_NODE : case FOR_NODE : case FORALL_NODE : case WHILE_NODE : case CDOALL_NODE : case SDOALL_NODE : case DOACROSS_NODE : case CDOACROSS_NODE : case FUNC_HEDR : case ENUM_DECL: case STRUCT_DECL: case UNION_DECL: case CLASS_DECL: case TECLASS_DECL: case COLLECTION_DECL: case SWITCH_NODE: case ELSEIF_NODE : return where; default: Message("No Control Parent in computeControlParent: abort()",0); abort(); } } switch(BIF_CODE(where)) { case CONT_STAT : if (BIF_CP(where) && (BIF_CODE(BIF_CP(where)) != FOR_NODE) && (BIF_CODE(BIF_CP(where)) != WHILE_NODE) && (BIF_CODE(BIF_CP(where)) != LOOP_NODE) && (BIF_CODE(BIF_CP(where)) != CDOALL_NODE) && (BIF_CODE(BIF_CP(where)) != SDOALL_NODE) && (BIF_CODE(BIF_CP(where)) != DOACROSS_NODE) && (BIF_CODE(BIF_CP(where)) != CDOACROSS_NODE)) { cp = BIF_CP(where); break; } case CONTROL_END : cp = BIF_CP(BIF_CP(where)); /* handle by the function insert in */ break; /* that a node with a list of blobs */ case GLOBAL : case PROG_HEDR : case PROC_HEDR : case PROS_HEDR : case BASIC_BLOCK : case IF_NODE : case WHERE_BLOCK_STMT : case LOOP_NODE : case FOR_NODE : case FORALL_NODE : case WHILE_NODE : case CDOALL_NODE : case SDOALL_NODE : case DOACROSS_NODE : case CDOACROSS_NODE : case FUNC_HEDR : case ENUM_DECL: case STRUCT_DECL: case UNION_DECL: case CLASS_DECL: case TECLASS_DECL: case COLLECTION_DECL: case SWITCH_NODE: case ELSEIF_NODE : cp = where; break; default: cp = BIF_CP(where); /* dont specify it */ } return cp; } /***************************************************************************/ int insertBfndListIn(first,where,cpin) PTR_BFND first,where; PTR_BFND cpin; { PTR_BFND cp; PTR_BFND biforblob; PTR_BFND temp, last; int inblob2; if (!first) return 0; if (!where) { Message("where not defined in insertBfndListIn: abort()",0); abort(); } if (!cpin) cp = computeControlParent(where); else cp = cpin; /* find where in the blob list where to insert it */ /* treat first the special case of if_node */ if ((BIF_CODE(where) == CONTROL_END) && BIF_CP(where) && (BIF_CODE(BIF_CP(where)) == IF_NODE || BIF_CODE(BIF_CP(where)) == ELSEIF_NODE) && (!findBifInList2 (BIF_CP(where),where)) && BIF_BLOB2(BIF_CP(where))) { cp = BIF_CP(where); inblob2 = TRUE; biforblob = NULL; last = getLastNodeList(first); } else { biforblob = getWhereToInsertInBfnd(where,cp); last = getLastNodeList(first); inblob2 = findBifInList2 (cp,biforblob); /* if (BIF_CODE(where) == ELSEIF_NODE) inblob2 = TRUE;*/ } for (temp = first; temp; temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) { if (!biforblob) { if (inblob2) firstBfndInList2(temp, cp); else firstBfndInList1(temp, cp); } else { if (inblob2) insertBfndInList2(temp,biforblob, cp); else insertBfndInList1(temp,biforblob, cp); } biforblob = temp; } } updateControlParent(first,last,cp); BIF_NEXT(last) = BIF_NEXT(where); BIF_NEXT(where) = first; return 1; } /***************************************************************************/ int insertBfndListInList1(first,cpin) PTR_BFND first; PTR_BFND cpin; { PTR_BFND biforblob; PTR_BFND temp, last; if (!first || !cpin) return 0; biforblob = NULL; last = getLastNodeList(first); for (temp = first; temp; temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) { if (!biforblob) { firstBfndInList1(temp, cpin); } else { insertBfndInList1(temp,biforblob, cpin); } biforblob = temp; } } updateControlParent(first,last,cpin); return 1; } /***************************************************************************/ int appendBfndListToList1(first,cpin) PTR_BFND first; PTR_BFND cpin; { PTR_BFND biforblob; PTR_BFND temp, last; if (!first || !cpin) return 0; biforblob = NULL; last = getLastNodeList(first); for (temp = first; temp; temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) { if (!biforblob) { appendBfndToList1(temp, cpin); } else { insertBfndInList1(temp,biforblob, cpin); } biforblob = temp; } } updateControlParent(first,last,cpin); return 1; } /***************************************************************************/ int firstInBfndList2(first,cpin) PTR_BFND first; PTR_BFND cpin; { PTR_BFND biforblob; PTR_BFND temp, last; if (!first || !cpin) return 0; biforblob = NULL; last = getLastNodeList(first); for (temp = first; temp; temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) { if (!biforblob) { firstBfndInList2(temp, cpin); } else { insertBfndInList2(temp,biforblob, cpin); } biforblob = temp; } } updateControlParent(first,last,cpin); return 1; } /***************************************************************************/ int appendBfndListToList2(first,cpin) PTR_BFND first; PTR_BFND cpin; { PTR_BFND biforblob; PTR_BFND temp, last; if (!first || !cpin) return 0; biforblob = NULL; last = getLastNodeList(first); for (temp = first; temp; temp = BIF_NEXT(temp)) { if (!isItInSection(first,last,BIF_CP(temp))) { if (!biforblob) { appendBfndToList2(temp, cpin); } else { insertBfndInList2(temp,biforblob, cpin); } biforblob = temp; } } updateControlParent(first,last,cpin); return 1; } /***************************************************************************/ void insertBfndBeforeIn(biftoinsert, bif_current, cpin) PTR_BFND bif_current, biftoinsert,cpin; { PTR_BFND the_one_before = NULL; if (! bif_current || ! biftoinsert) { Message("NULL bif node in biftoinsert\n",0); exit(-1); } if (BIF_CODE (bif_current) == GLOBAL) { Message("Cannot insert before global\n",0); exit(-1); } the_one_before = getNodeBefore (bif_current); insertBfndListIn (biftoinsert, the_one_before,cpin); } /* warning to be used carefully; i.e. remove sons before a root */ /***************************************************************************/ PTR_BFND deleteBfnd(bif) PTR_BFND bif; { PTR_BFND temp; temp = getNodeBefore (bif); deleteBfndFrom (BIF_CP (bif), bif); if (temp) BIF_NEXT (temp) = BIF_NEXT (bif); return temp; } /***************************************************************************/ int isItInSection(bif_depart, bif_fin, noeud) PTR_BFND bif_depart, bif_fin, noeud; { PTR_BFND temp; if (! noeud) return FALSE; for (temp = bif_depart; temp; temp = BIF_NEXT (temp)) { if (temp == noeud) return TRUE; if (temp == bif_fin) return FALSE; } return FALSE; } /***************************************************************************/ PTR_BFND extractBifSectionBetween(bif_depart, bif_fin) PTR_BFND bif_depart, bif_fin; { PTR_BFND temp; if (bif_depart && bif_fin) { for (temp = bif_depart; temp != bif_fin; temp = BIF_NEXT (temp)) { if (!isItInSection(bif_depart, bif_fin,BIF_CP (temp))) { deleteBfndFrom(BIF_CP (temp),temp); BIF_CP (temp) = NULL; } } /* on traite maintenant bif_fin */ if (!isItInSection(bif_depart, bif_fin,BIF_CP ( bif_fin))) { deleteBfndFrom(BIF_CP (bif_fin), bif_fin); BIF_CP (bif_fin) = NULL; } temp = getNodeBefore(bif_depart); if (temp && bif_fin) BIF_NEXT(temp) = BIF_NEXT (bif_fin); BIF_NEXT (bif_fin) = NULL; } return bif_depart; } /***************************************************************************/ PTR_BFND getLastNodeList(b) PTR_BFND b; { PTR_BFND temp; for (temp = b; temp; temp = BIF_NEXT(temp)) { if (!BIF_NEXT(temp)) { return temp; } } return temp; } /***************************************************************************/ PTR_BFND getLastNodeOfStmt(b) PTR_BFND b; { PTR_BLOB temp,last = NULL; if (!b) return NULL; if (BIF_BLOB2(b)) { for (temp = BIF_BLOB2(b); temp ; temp = BLOB_NEXT(temp)) { last = temp; } } else { for (temp = BIF_BLOB1(b); temp ; temp = BLOB_NEXT(temp)) { last = temp; } } if (last) { if (Check_Lang_Fortran(cur_proj)) return BLOB_VALUE(last); else { /* in C the Control end may not exist */ return getLastNodeOfStmt(BLOB_VALUE(last)); } } else return b; } /* version that does not assume, there is a last */ /***************************************************************************/ PTR_BFND getLastNodeOfStmtNoControlEnd(b) PTR_BFND b; { PTR_BLOB temp,last = NULL; if (!b) return NULL; if (BIF_BLOB2(b)) { for (temp = BIF_BLOB2(b); temp ; temp = BLOB_NEXT(temp)) { last = temp; } } else { for (temp = BIF_BLOB1(b); temp ; temp = BLOB_NEXT(temp)) { last = temp; } } if (last) { return getLastNodeOfStmt(BLOB_VALUE(last)); } else return b; } /* preset some values of symbols for evaluateExpression*/ #define ALLOCATECHUNKVALUE 100 static PTR_SYMB *ValuesSymb = NULL; static int *ValuesInt = NULL; static int NbValues = 0; static int NbElement = 0; /***************************************************************************/ void allocateValueEvaluate() { int i; PTR_SYMB *pt1; int *pt2; pt1 = (PTR_SYMB *) xmalloc( sizeof(PTR_SYMB *) * (NbValues + ALLOCATECHUNKVALUE)); pt2 = (int *) xmalloc( sizeof(int *) * (NbValues + ALLOCATECHUNKVALUE)); for (i=0; i 1) { PTR_LLND listlab, ptl; int trouve = 0; listlab = (kind == 2) ? BIF_LL1(copie) : BIF_LL2(copie); while (listlab) { ptl = NODE_OPERAND0(listlab); /* we look in the list */ if (ptl) { lab = NODE_LABEL(ptl); trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2 * j]) if (LABEL_STMTNO(label_insection[2 * j]) == LABEL_STMTNO(lab)) { trouve = j + 1; break; } } if (trouve) { NODE_LABEL(ptl) = label_insection[2 * (trouve - 1) + 1]; } } listlab = NODE_OPERAND1(listlab); } temp = BIF_NEXT(temp); continue; } lab = NULL; if (BIF_LL3(temp) && (NODE_CODE(BIF_LL3(temp)) == LABEL_REF)) { lab = NODE_LABEL(BIF_LL3(temp)); cas = 2; } else if (BIF_LL1(temp) && (NODE_CODE(BIF_LL1(temp)) == LABEL_REF)) { lab = NODE_LABEL(BIF_LL1(temp)); cas = 3; } else { lab = BIF_LABEL_USE(temp); cas = 1; } if (lab) { /* look where the label is the label is defined somewhere */ int trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2 * j]) if (LABEL_STMTNO(label_insection[2 * j]) == LABEL_STMTNO(lab)) { trouve = j + 1; break; } } if (trouve) { if (cas == 1) { BIF_LABEL_USE(copie) = label_insection[2 * (trouve - 1) + 1]; } if (cas == 2) { if (BIF_LL3(copie)) { NODE_LABEL(BIF_LL3(copie)) = label_insection[2 * (trouve - 1) + 1]; } } if (cas == 3) { if (BIF_LL1(copie)) { NODE_LABEL(BIF_LL1(copie)) = label_insection[2 * (trouve - 1) + 1]; } } } else { if (cas == 1) BIF_LABEL_USE(copie) = lab; /* outside */ /* if ((cas == 2) no change */ } } temp = BIF_NEXT(temp); } /* on met a jour le blob list */ copie = alloue[1]; for (temp = body; temp; temp = BIF_NEXT(temp)) { if (BIF_BLOB1(temp)) { /* on doit cree la blob liste */ for (blobtemp = BIF_BLOB1(temp); blobtemp; blobtemp = BLOB_NEXT(blobtemp)) { /* on cherche la reference dans le tableaux allouer */ cherche = NULL; for (i = 0; i < lenght; i++) { if (alloue[2 * i] == BLOB_VALUE(blobtemp)) { cherche = alloue[2 * i + 1]; break; } } appendBfndToList1(cherche, copie); } } if (BIF_BLOB2(temp)) { /* on doit cree la blob liste */ for (blobtemp = BIF_BLOB2(temp); blobtemp; blobtemp = BLOB_NEXT(blobtemp)) { /* on cherche la reference dans le tableaux allouer */ cherche = NULL; for (i = 0; i < lenght; i++) { if (alloue[2 * i] == BLOB_VALUE(blobtemp)) { cherche = alloue[2 * i + 1]; break; } } appendBfndToList2(cherche, copie); } } copie = BIF_NEXT(copie); if (temp == lastnode) break; } /* on remet ici a jour les CP */ copie = alloue[1]; for (temp = body; temp; temp = BIF_NEXT(temp)) { if (isItInSection(body, lastnode, BIF_CP(temp))) { /* on cherche le bif_cp pour la copie */ cherche = NULL; for (i = 0; i < lenght; i++) { if (alloue[2 * i] == BIF_CP(temp)) { cherche = alloue[2 * i + 1]; break; } } BIF_CP(copie) = cherche; } else BIF_CP(copie) = NULL; copie = BIF_NEXT(copie); if (temp == lastnode) break; } copie = alloue[1]; #ifdef __SPF removeFromCollection(alloue); removeFromCollection(label_insection); #endif free(alloue); free(label_insection); return copie; } /* (ajm) This function will copy one statement and all of its children (presumably; I didn't touch that one way or the other). It differs from low_level.c:duplicateStmt (v1.00) in that does not copy all of the BIF_NEXT successors of the statement as well. */ /***************************************************************************/ PTR_BFND duplicateOneStmt(body) PTR_BFND body; { PTR_BFND copie, last, temp, cherche, lastnode; int lenght,i,j; PTR_BFND *alloue; PTR_BLOB blobtemp; PTR_LABEL *label_insection; PTR_LABEL lab; int maxlabelname; if (! body) return NULL; /* on calcul d'abord la longueur */ maxlabelname = getLastLabelId(); lenght = 0; /* Changed area, by ajm 1-Feb-94 */ #if 0 for (temp = body; temp ; temp = BIF_NEXT(temp)) { lenght++; lastnode = temp; } #else if ( body != 0 ) { lenght = 1; lastnode = body;/*podd 12.03.99*/ } #endif /* ajm */ alloue = (PTR_BFND *) xmalloc(2*lenght * sizeof(PTR_BFND)); memset((char *) alloue, 0, 2* lenght * sizeof(PTR_BFND)); /* label part, we record label */ label_insection = (PTR_LABEL *) xmalloc(2*lenght * sizeof(PTR_LABEL)); memset((char *) label_insection, 0, 2* lenght * sizeof(PTR_LABEL)); temp = body; last = NULL; for (i = 0; i < lenght; i++) { copie = (PTR_BFND) newNode (BIF_CODE (temp)); BIF_SYMB (copie) = BIF_SYMB (temp); BIF_LL1 (copie) = copyLlNode(BIF_LL1 (temp)); BIF_LL2 (copie) = copyLlNode(BIF_LL2 (temp)); BIF_LL3 (copie) = copyLlNode(BIF_LL3 (temp)); BIF_DECL_SPECS (copie) = BIF_DECL_SPECS(temp); if (last) BIF_NEXT(last) = copie; if (BIF_LABEL(temp))/* && (LABEL_BODY(BIF_LABEL(temp)) == temp))*/ { /* create a new label */ label_insection[2*i+1] = (PTR_LABEL) newNode(LABEL_KIND); maxlabelname++; LABEL_STMTNO(label_insection[2*i+1]) = maxlabelname; LABEL_BODY(label_insection[2*i+1]) = copie; LABEL_USED(label_insection[2*i+1]) = LABEL_USED(BIF_LABEL(temp)); LABEL_ILLEGAL(label_insection[2*i+1])=LABEL_ILLEGAL(BIF_LABEL(temp)); LABEL_DEFINED(label_insection[2*i+1])=LABEL_DEFINED(BIF_LABEL(temp)); BIF_LABEL(copie) = label_insection[2*i+1]; label_insection[2*i] = BIF_LABEL(temp); } /* on fait corresponde temp et copie */ alloue[2*i] = temp; alloue[2*i+1] = copie; temp = BIF_NEXT(temp); last = copie; } /* On met a jour les labels */ temp = body; for (i = 0; i < lenght; i++) { int cas; copie = alloue[2*i+1]; lab = NULL; /* We treat first the COMGOTO_NODE first */ if (BIF_CODE(temp) == COMGOTO_NODE) { PTR_LLND listlab, ptl; int trouve = 0; listlab = BIF_LL1(copie); while (listlab) { ptl = NODE_OPERAND0(listlab); /* we look in the list */ if (ptl) { lab = NODE_LABEL(ptl); trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { NODE_LABEL(ptl) = label_insection[2*(trouve-1)+1]; } } listlab = NODE_OPERAND1(listlab); } temp = BIF_NEXT(temp); continue; } if (BIF_LL3(temp) && (NODE_CODE(BIF_LL3(temp)) == LABEL_REF)) { lab = NODE_LABEL(BIF_LL3(temp)); cas = 2; } else { lab = BIF_LABEL_USE(temp); cas = 1; } if (lab) { /* look where the label is the label is defined somewhere */ int trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { if (cas == 1) { BIF_LABEL_USE(copie) = label_insection[2*(trouve-1)+1]; } if (cas == 2) { if (BIF_LL3(copie)) { NODE_LABEL(BIF_LL3(copie)) = label_insection[2*(trouve-1)+1]; } } } else { if (cas == 1) BIF_LABEL_USE(copie) = lab; /* outside */ /* if ((cas == 2) no change */ } } temp = BIF_NEXT(temp); } /* on met a jour le blob list */ copie = alloue[1]; /* Change by ajm */ #if 0 for (temp = body; temp ; temp = BIF_NEXT(temp)) #else for (temp = body; temp ; temp = 0 /* not BIF_NEXT(temp)!! */ ) #endif { if (BIF_BLOB1(temp)) { /* on doit cree la blob liste */ for (blobtemp = BIF_BLOB1(temp);blobtemp; blobtemp = BLOB_NEXT(blobtemp)) { /* on cherche la reference dans le tableaux allouer */ cherche = NULL; for (i = 0; i newlabelname *//*podd 13.01.14*/ LABEL_BODY(label_insection[2*i+1]) = copie; LABEL_USED(label_insection[2*i+1]) = LABEL_USED(BIF_LABEL(temp)); LABEL_ILLEGAL(label_insection[2*i+1])=LABEL_ILLEGAL(BIF_LABEL(temp)); LABEL_DEFINED(label_insection[2*i+1])=LABEL_DEFINED(BIF_LABEL(temp)); BIF_LABEL(copie) = label_insection[2*i+1]; label_insection[2*i] = BIF_LABEL(temp); } /* on fait corresponde temp et copie */ alloue[2*i] = temp; alloue[2*i+1] = copie; temp = BIF_NEXT(temp); last = copie; } /* On met a jour les labels */ /*podd 06.04.13 this fragment (renewing of label references ) is copied from function duplicateStmtsNoExtract()*/ temp = body; for (i = 0; i < lenght; i++) { int cas, kind; copie = alloue[2*i+1]; lab = NULL; /* We treat first the COMGOTO_NODE first */ switch(BIF_CODE(temp)) { case COMGOTO_NODE: case ASSGOTO_NODE: kind = 2; break; case ARITHIF_NODE: kind = 3; break; case WRITE_STAT: case READ_STAT: case PRINT_STAT: case BACKSPACE_STAT: case REWIND_STAT: case ENDFILE_STAT: case INQUIRE_STAT: case OPEN_STAT: case CLOSE_STAT: kind = 1; break; default: kind = 0; break; } if(kind == 1) { PTR_LLND lb, list; list = BIF_LL2(copie); /*control list or format*/ if(list && NODE_CODE(list) == EXPR_LIST) { for(;list;list=NODE_OPERAND1(list)) { lb = NODE_OPERAND1(NODE_OPERAND0(list)); if(NODE_CODE(lb) == LABEL_REF) lab = NODE_LABEL(lb); if (lab) { /* look where the label is the label is defined somewhere */ int trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { NODE_LABEL(lb) = label_insection[2*(trouve-1)+1]; } } } } else if(list && (NODE_CODE(list) == SPEC_PAIR)) { lb =(NODE_OPERAND1(list)); if(NODE_CODE(lb) == LABEL_REF) lab = NODE_LABEL(lb); if (lab) { /* look where the label is the label is defined somewhere */ int trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { NODE_LABEL(lb) = label_insection[2*(trouve-1)+1]; } } } temp = BIF_NEXT(temp); continue; } if(kind > 1) { PTR_LLND listlab, ptl; int trouve = 0; listlab = (kind==2) ? BIF_LL1(copie) : BIF_LL2(copie); while (listlab) { ptl = NODE_OPERAND0(listlab); /* we look in the list */ if (ptl) { lab = NODE_LABEL(ptl); trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { NODE_LABEL(ptl) = label_insection[2*(trouve-1)+1]; } } listlab = NODE_OPERAND1(listlab); } temp = BIF_NEXT(temp); continue; } lab=NULL; if (BIF_LL3(temp) && (NODE_CODE(BIF_LL3(temp)) == LABEL_REF)) { lab = NODE_LABEL(BIF_LL3(temp)); cas = 2; } else if (BIF_LL1(temp) && (NODE_CODE(BIF_LL1(temp)) == LABEL_REF)) { lab = NODE_LABEL(BIF_LL1(temp)); cas = 3; } else { lab = BIF_LABEL_USE(temp); cas = 1; } if (lab) { /* look where the label is the label is defined somewhere */ int trouve = 0; for (j = 0; j < lenght; j++) { if (label_insection[2*j]) if (LABEL_STMTNO(label_insection[2*j]) == LABEL_STMTNO(lab)) { trouve = j+1; break; } } if(trouve) { if (cas == 1) { BIF_LABEL_USE(copie) = label_insection[2*(trouve-1)+1]; } if (cas == 2) { if (BIF_LL3(copie)) { NODE_LABEL(BIF_LL3(copie)) = label_insection[2*(trouve-1)+1]; } } if (cas == 3) { if (BIF_LL1(copie)) { NODE_LABEL(BIF_LL1(copie)) = label_insection[2*(trouve-1)+1]; } } } else { if (cas == 1) BIF_LABEL_USE(copie) = lab; /* outside */ /* if ((cas == 2) no change */ } } temp = BIF_NEXT(temp); } /* on met a jour le blob list */ copie = alloue[1]; for (temp = body, iii = 0; iii num) return last; last =temp; } return(NULL); } /********* Add a comment to a node *************************************/ /***************************************************************************/ void LibAddComment(PTR_BFND bif, char *str) { char *pt; PTR_CMNT cmnt; if (!bif || !str) return; if (!BIF_CMNT(bif)) { pt = (char *)xmalloc(strlen(str) + 1); cmnt = (PTR_CMNT)newNode(CMNT_KIND); strcpy(pt, str); CMNT_STRING(cmnt) = pt; BIF_CMNT(bif) = cmnt; } else { cmnt = BIF_CMNT(bif); if (CMNT_STRING(cmnt)) { pt = (char *)xmalloc(strlen(str) + strlen(CMNT_STRING(cmnt)) + 1); sprintf(pt, "%s%s", CMNT_STRING(cmnt), str); CMNT_STRING(cmnt) = pt; } else { pt = (char *)xmalloc(strlen(str) + 1); sprintf(pt, "%s", str); CMNT_STRING(cmnt) = pt; } } } /* ajm */ /********************** Set a node's comment *******************************/ //Kolganov 15.11.2017 void LibDelAllComments(PTR_BFND bif) { PTR_CMNT cmnt; char *pt; if (!bif) return; if (BIF_CMNT(bif)) { if (CMNT_STRING(BIF_CMNT(bif))) { #ifdef __SPF removeFromCollection(CMNT_STRING(BIF_CMNT(bif))); #endif free(CMNT_STRING(BIF_CMNT(bif))); CMNT_STRING(BIF_CMNT(bif)) = NULL; } cmnt = BIF_CMNT(bif); // remove comment from list before free if (cmnt == PROJ_FIRST_CMNT()) { if (cmnt->thread) PROJ_FIRST_CMNT() = cmnt->thread; else PROJ_FIRST_CMNT() = NULL; } else { PTR_CMNT before = PROJ_FIRST_CMNT(); while (before->thread) { if (before->thread == cmnt) { if (cmnt->thread) { before->thread = cmnt->thread; cmnt->thread = NULL; } else before->thread = NULL; break; } before = before->thread; } } /* #ifdef __SPF removeFromCollection(BIF_CMNT(bif)); #endif free(BIF_CMNT(bif));*/ BIF_CMNT(bif) = NULL; } } void LibSetAllComments(PTR_BFND bif, char *str) { PTR_CMNT cmnt; char *pt; if ( !bif || !str ) return; LibDelAllComments(bif); pt = (char *) xmalloc(strlen(str) + 1); cmnt = (PTR_CMNT) newNode(CMNT_KIND); strcpy(pt, str); CMNT_STRING(cmnt) = pt; BIF_CMNT(bif) = cmnt; } /***************************************************************************/ int patternMatchExpression(ll1,ll2) PTR_LLND ll1,ll2; { /* char *string1, *string2;*/ /*podd 15.03.99*/ int *res1, *res2; if (ll1 == ll2) return TRUE; if (!ll1 || !ll2) return FALSE; if (NODE_CODE(ll1) != NODE_CODE(ll2)) return FALSE; /* because of identical names does not work also no commutativity string1 = funparse_llnd(ll1); string2 = funparse_llnd(ll2); if (strcmp(string1, string2) == 0) return TRUE; */ /* first test if constant equations identical */ res1 = evaluateExpression(ll1); res2 = evaluateExpression(ll2); if ((res1[0] != -1) && (res2[0] != -1) && (res1[1] == res2[1])) { #ifdef __SPF removeFromCollection(res1); removeFromCollection(res2); #endif free(res1); free(res2); return TRUE; } if ((res1[0] != -1) && (res2[0] == -1)) { #ifdef __SPF removeFromCollection(res1); removeFromCollection(res2); #endif free(res1); free(res2); return FALSE; } if ((res1[0] == -1) && (res2[0] != -1)) { #ifdef __SPF removeFromCollection(res1); removeFromCollection(res2); #endif free(res1); free(res2); return FALSE; } #ifdef __SPF removeFromCollection(res1); removeFromCollection(res2); #endif free(res1); free(res2); /* for each kind of node do the pattern match */ switch (NODE_CODE(ll1)) { case VAR_REF: if (NODE_SYMB(ll1) == NODE_SYMB(ll2)) return TRUE; break; /* commutatif operator */ case EQ_OP: if ((NODE_SYMB(ll1) == NODE_SYMB(ll2)) && patternMatchExpression(NODE_OPERAND0(ll1), NODE_OPERAND1(ll2)) && patternMatchExpression(NODE_OPERAND0(ll1), NODE_OPERAND1(ll2))) return TRUE; default : if ((NODE_SYMB(ll1) == NODE_SYMB(ll2)) && patternMatchExpression(NODE_OPERAND0(ll1), NODE_OPERAND0(ll2)) && patternMatchExpression(NODE_OPERAND1(ll1), NODE_OPERAND1(ll2))) return TRUE; } return FALSE; } /* new functions added, they have a match with the one in the C++ interface library */ /***************************************************************************/ void SetCurrentFileTo(file) PTR_FILE file; { if (!file) return; if (pointer_on_file_proj == file) return; cur_file = file; /* reset the toolbox and pointers*/ Init_Tool_Box(); } /***************************************************************************/ int LibnumberOfFiles() { PTR_BLOB ptb; int count = 0; if (cur_proj) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { count++; } } else if(pointer_on_file_proj) return 1; return count; } /***************************************************************************/ PTR_FILE GetPointerOnFile(dep_file_name) char *dep_file_name; { /* PTR_FILE pt;*/ /*podd 15.03.99*/ PTR_BLOB ptb; if (cur_proj && dep_file_name) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { cur_file = (PTR_FILE) BLOB_VALUE (ptb); /* reset the toolbox and pointers*/ SetCurrentFileTo(cur_file); if (CUR_FILE_NAME() && !strcmp(CUR_FILE_NAME(),dep_file_name)) return pointer_on_file_proj; } } return NULL; } /***************************************************************************/ int GetFileNum(dep_file_name) char *dep_file_name; { PTR_FILE pt; PTR_BLOB ptb; int count= 0; if (cur_proj && dep_file_name) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { count++; pt = (PTR_FILE) BLOB_VALUE (ptb); /* reset the toolbox and pointers*/ SetCurrentFileTo(pt); if (FILE_FILENAME(pt) && !strcmp(FILE_FILENAME(pt),dep_file_name)) return count; } } return 0; } /***************************************************************************/ int GetFileNumWithPt(dep_file) PTR_FILE dep_file; { PTR_FILE pt; PTR_BLOB ptb; int count= 0; if (cur_proj && dep_file) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { count++; pt = (PTR_FILE) BLOB_VALUE (ptb); /* reset the toolbox and pointers*/ SetCurrentFileTo(pt); if (pt==dep_file) return count; } } return 0; } /***************************************************************************/ PTR_FILE GetFileWithNum(num) int num; { PTR_FILE pt; PTR_BLOB ptb; int count= 0; if (cur_proj) { for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { pt = (PTR_FILE) BLOB_VALUE (ptb); /* reset the toolbox and pointers*/ SetCurrentFileTo(pt); if (count == num) return pt; count++; } } return NULL; } /***************************************************************************/ void LibsaveDepFile(str) char *str; { PTR_BFND thebif; int i; if (!str) { Message("No name specified in saveDepFile",0); return; } thebif = PROJ_FIRST_BIF(); i = 1; for (;thebif;thebif=BIF_NEXT(thebif), i++) BIF_ID(thebif) = i; CUR_FILE_NUM_BIFS() = i-1; if (write_nodes(cur_file,str) < 0) Message("Error, write_nodes() failed (001)",0); } /***************************************************************************/ int getNumberOfFunction() { PTR_BFND thebif; int count = 0; thebif = PROJ_FIRST_BIF(); for (; thebif; thebif = BIF_NEXT(thebif)) { if ((BIF_CODE(thebif) == FUNC_HEDR) || (BIF_CODE(thebif) == PROC_HEDR) || (BIF_CODE(thebif) == PROS_HEDR) || (BIF_CODE(thebif) == PROG_HEDR)) { if (thebif->control_parent->variant != INTERFACE_STMT && thebif->control_parent->variant != INTERFACE_OPERATOR && thebif->control_parent->variant != INTERFACE_ASSIGNMENT) count++; } } return count; } /***************************************************************************/ PTR_BFND getFunctionNumHeader(int num) { PTR_BFND thebif; int count = 0; thebif = PROJ_FIRST_BIF(); for (; thebif; thebif = BIF_NEXT(thebif)) { if ((BIF_CODE(thebif) == FUNC_HEDR) || (BIF_CODE(thebif) == PROC_HEDR) || (BIF_CODE(thebif) == PROS_HEDR) || (BIF_CODE(thebif) == PROG_HEDR)) { if (thebif->control_parent->variant != INTERFACE_STMT && thebif->control_parent->variant != INTERFACE_OPERATOR && thebif->control_parent->variant != INTERFACE_ASSIGNMENT) { if (count == num) return thebif; count++; } } } return NULL; } /***************************************************************************/ int getNumberOfStruct() { PTR_BFND thebif; int count =0; thebif = PROJ_FIRST_BIF(); for (;thebif;thebif=BIF_NEXT(thebif)) { if (isAStructDeclBif(BIF_CODE(thebif))) count++; } return count; } /***************************************************************************/ PTR_BFND getStructNumHeader(num) int num; { PTR_BFND thebif; int count =0; thebif = PROJ_FIRST_BIF(); for (;thebif;thebif=BIF_NEXT(thebif)) { if (isAStructDeclBif(BIF_CODE(thebif))) { if (count == num) return thebif; count++; } } return NULL; } /***************************************************************************/ PTR_BFND getFirstStmt() { return PROJ_FIRST_BIF(); } /***************************************************************************/ PTR_TYPE GetAtomicType(tt) int tt; { PTR_TYPE ttype = NULL; if(!isAtomicType(tt)) { Message("Misuse of GetAtomicType",0); return NULL; } for (ttype = PROJ_FIRST_TYPE () ; ttype; ttype = TYPE_NEXT(ttype)) { if (TYPE_CODE(ttype) == tt) return ttype; } return (ttype); } /***************************************************************************/ PTR_BFND LiblastDeclaration(start) PTR_BFND start; { PTR_BFND temp; if (start) temp = start; else temp = PROJ_FIRST_BIF (); for ( ; temp; temp = BIF_NEXT(temp)) { if ( BIF_NEXT(temp) && !isADeclBif(BIF_CODE(BIF_NEXT(temp)))) return temp; } Message("LiblastDeclaration return NULL",0); return NULL; } /***************************************************************************/ int LibIsSymbolInScope(bif,symb) PTR_BFND bif; PTR_SYMB symb; { PTR_BFND scope; if (!symb || !bif) return FALSE; scope = SYMB_SCOPE(symb); /* return isItInSection(BIF_CP(bif), getLastNodeOfStmt(BIF_CP(bif)), scope);*/ if (scope) /* assume scope is the declaration of the variable, otherwise to be removed*/ return isItInSection(BIF_CP(scope), getLastNodeOfStmt(BIF_CP(scope)), bif); else return FALSE; } /***************************************************************************/ int IsRefToSymb(expr,symb) PTR_LLND expr; PTR_SYMB symb; { if (!expr) return FALSE; if (!hasNodeASymb(NODE_CODE(expr))) return FALSE; if (NODE_SYMB(expr) != symb) return FALSE; return TRUE; } /***************************************************************************/ void LibreplaceSymbByExp(exprold, symb, exprnew) PTR_SYMB symb; PTR_LLND exprold, exprnew; { if (!exprold) return ; if (IsRefToSymb(NODE_OPERAND0(exprold),symb)) NODE_OPERAND0(exprold) = exprnew; else LibreplaceSymbByExp(NODE_OPERAND0(exprold), symb, exprnew); if (IsRefToSymb(NODE_OPERAND1(exprold),symb)) NODE_OPERAND1(exprold) = exprnew; else LibreplaceSymbByExp(NODE_OPERAND1(exprold), symb, exprnew); } /***************************************************************************/ void LibreplaceSymbByExpInStmts(debut, fin, symb, expr) PTR_BFND debut, fin; PTR_SYMB symb; PTR_LLND expr; { PTR_BFND temp; for (temp = debut; temp ; temp = BIF_NEXT(temp)) { if (IsRefToSymb(BIF_LL1(temp),symb)) BIF_LL1(temp) = expr; else LibreplaceSymbByExp(BIF_LL1(temp), symb, expr); if (IsRefToSymb(BIF_LL2(temp),symb)) BIF_LL2(temp) = expr; else LibreplaceSymbByExp(BIF_LL2(temp), symb, expr); if (IsRefToSymb(BIF_LL3(temp),symb)) BIF_LL3(temp) = expr; else LibreplaceSymbByExp(BIF_LL3(temp), symb, expr); if (fin && (temp == fin)) break; } } /***************************************************************************/ PTR_LLND LibIsSymbolInExpression(exprold, symb) PTR_SYMB symb; PTR_LLND exprold; { PTR_LLND pt =NULL; if (!exprold) return NULL; if (IsRefToSymb(NODE_OPERAND0(exprold),symb)) return NODE_OPERAND0(exprold); else pt = LibIsSymbolInExpression(NODE_OPERAND0(exprold), symb); if (pt) return pt; if (IsRefToSymb(NODE_OPERAND1(exprold),symb)) return NODE_OPERAND1(exprold) ; else pt = LibIsSymbolInExpression(NODE_OPERAND1(exprold), symb); return pt; } /***************************************************************************/ PTR_BFND LibWhereIsSymbDeclare(symb) PTR_SYMB symb; { PTR_BFND scopeof, temp, last; if (!symb) return NULL; scopeof = SYMB_SCOPE(symb); if (!scopeof) return NULL; last = getLastNodeOfStmt(scopeof); for (temp = scopeof; temp ; temp=BIF_NEXT(temp)) { #if __SPF //SKIP SPF dirs //for details see dvm_tag.h if (scopeof->variant >= 950 && scopeof->variant <= 958) continue; #endif if (LibIsSymbolInExpression(BIF_LL1(temp), symb)) return temp; if (LibIsSymbolInExpression(BIF_LL2(temp), symb)) return temp; if (temp == last) break; } return NULL; } /* return a symbol in a declaration list replace find_suit_declarator() but also more ... replace also find_parameter_name() */ /***************************************************************************/ PTR_LLND giveLlSymbInDeclList(expr) PTR_LLND expr; { PTR_LLND list1, list2; if (!expr) return NULL; if (NODE_CODE(expr) == EXPR_LIST) { for (list1= expr; list1; list1 = NODE_OPERAND1(list1)) { if (NODE_OPERAND0(list1)) { for (list2= NODE_OPERAND0(list1); list2; ) { if (hasNodeASymb(NODE_CODE(list2))) { if (NODE_SYMB(list2)) return list2; } if(NODE_CODE(list2) == SCOPE_OP) list2 = NODE_OPERAND1(list2); else list2 = NODE_OPERAND0(list2); } } } } else { for (list2= expr; list2; ) { if (hasNodeASymb(NODE_CODE(list2))) { if (NODE_SYMB(list2)) return list2; } if(NODE_CODE(list2) == SCOPE_OP) list2 = NODE_OPERAND1(list2); else list2 = NODE_OPERAND0(list2); } } /* Message("giveSymbInDeclList did not find the symbol (crash will happen)",0); */ return NULL; } /* return the first non null type in the base type list */ /***************************************************************************/ PTR_TYPE lookForInternalBasetype(type) PTR_TYPE type; { if (!type) return NULL; if (TYPE_CODE(type) == T_MEMBER_POINTER){ if (TYPE_COLL_BASE(type)) return lookForInternalBasetype(TYPE_COLL_BASE(type)); else return type; } else if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) return lookForInternalBasetype(TYPE_BASE(type)); else return type; } else return type; } /* return the first non null type in the base type list */ /***************************************************************************/ PTR_TYPE lookForTypeDescript(type) PTR_TYPE type; { if (!type) return NULL; if (TYPE_CODE(type) == T_DESCRIPT) return type; if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) return lookForTypeDescript(TYPE_BASE(type)); else return NULL; } else return NULL; } /***************************************************************************/ int getTypeNumDimension(type) PTR_TYPE type; { if (!type) return 0; return exprListLength(TYPE_DECL_RANGES(type)); } /***************************************************************************/ int isElementType(type) PTR_TYPE type; { if (!type) return 0; if (TYPE_CODE(type) == T_DERIVED_TYPE) { if (TYPE_SYMB_DERIVE(type) && SYMB_IDENT(TYPE_SYMB_DERIVE(type)) && (strcmp(SYMB_IDENT(TYPE_SYMB_DERIVE(type)), "ElementType") == 0)) return 1; } return 0; } /***************************************************************************/ PTR_TYPE getDerivedTypeWithName(str) char *str; { PTR_TYPE ttype = NULL; for (ttype = PROJ_FIRST_TYPE () ; ttype; ttype = TYPE_NEXT(ttype)) { if (TYPE_CODE(ttype) == T_DERIVED_TYPE) { if (TYPE_SYMB_DERIVE(ttype) && SYMB_IDENT(TYPE_SYMB_DERIVE(ttype)) && (strcmp(SYMB_IDENT(TYPE_SYMB_DERIVE(ttype)), str) == 0)) return ttype; } } return (ttype); } /***************************************************************************/ int sameName(symb1,symb2) PTR_SYMB symb1,symb2; { if (!symb1 || !symb2) return FALSE; if (!SYMB_IDENT(symb1) || !SYMB_IDENT(symb2)) return FALSE; if (strcmp(SYMB_IDENT(symb1),SYMB_IDENT(symb2)) == 0) return TRUE; else return FALSE; } /***************************************************************************/ PTR_SYMB lookForNameInParamList(functor,name) PTR_SYMB functor; char *name; { PTR_SYMB list1; if (!functor || !name) return NULL; for ( list1 = SYMB_MEMBER_PARAM(functor) ; list1 ; list1 = SYMB_NEXT_DECL(list1)) { if (!strcmp(SYMB_IDENT(list1),name)) return(list1) ; } return(NULL); } /***************************************************************************/ PTR_TYPE FollowTypeBaseAndDerived(type) PTR_TYPE type; { PTR_TYPE tmp; PTR_SYMB symb; if (!type) return NULL; if (isAtomicType(TYPE_CODE(type))) return type; tmp = lookForInternalBasetype(type); if (hasTypeSymbol(TYPE_CODE(tmp))) { symb = TYPE_SYMB_DERIVE(tmp); if (symb && SYMB_TYPE(symb)) return FollowTypeBaseAndDerived(SYMB_TYPE(symb)); else return tmp; } return tmp; } /* replace chain_up_type() */ /***************************************************************************/ PTR_TYPE addToBaseTypeList(type1,type2) PTR_TYPE type1,type2; { PTR_TYPE tmp; if (!type2) return(type1); if (!type1) return(type2); tmp = lookForInternalBasetype(type2); if (tmp) { TYPE_BASE(tmp) = type1; return(type2); } else Message("error in addToBaseTypeList",0); return NULL; } /* return the symbol it inherit from */ /***************************************************************************/ PTR_SYMB doesClassInherit(bif) PTR_BFND bif; { PTR_LLND ll; int lenght; if (!bif) return NULL; ll = BIF_LL2(bif); lenght = exprListLength(ll); if (lenght > 1) Message("Multiple inheritance not allowed",BIF_LINE(bif)); ll = giveLlSymbInDeclList(ll); if (ll) return NODE_SYMB(ll); else return NULL; } /***************************************************************************/ PTR_SYMB getClassNextFieldOrMember(symb) PTR_SYMB symb; { if (!symb) return NULL; if (SYMB_CODE(symb) == FIELD_NAME) return SYMB_NEXT_FIELD(symb); else if (SYMB_CODE(symb) == MEMBER_FUNC) return SYMB_MEMBER_NEXT(symb); else return symb->next_symb; /* return NULL; */ } /* find_first_field(pred) and find_first_field_2(pred)*/ /***************************************************************************/ PTR_SYMB getFirstFieldOfStruct(pred) PTR_BFND pred ; { /* PTR_LLND ll_ptr1; */ /* podd 15.03.99*/ PTR_LLND l2; /* PTR_BFND bf1 ;*/ /* podd 15.03.99*/ PTR_BLOB blob; if (!pred) return NULL; if (isAStructDeclBif(BIF_CODE(pred)) || isAUnionDeclBif(BIF_CODE(pred)) || isAEnumDeclBif(BIF_CODE(pred))) { if (!(blob= BIF_BLOB1(pred))) { return NULL; } else { for ( ; blob ; blob = BLOB_NEXT(blob)) { if (BLOB_VALUE(blob)) l2 = giveLlSymbInDeclList(BIF_LL1(BLOB_VALUE(blob))); else l2 = NULL; if (l2) { return NODE_SYMB(l2); } } } } return(NULL); } /***************************************************************************/ PTR_LLND addToExprList(expl,ll) PTR_LLND expl, ll; { PTR_LLND tmp, lptr; if (!ll) return expl; if (!expl) return newExpr(EXPR_LIST,NULL,ll,NULL); tmp = newExpr(EXPR_LIST,NULL,ll,NULL); lptr = Follow_Llnd(expl,2); NODE_OPERAND1(lptr) = tmp; return expl; } /***************************************************************************/ PTR_LLND addToList(first,pt) PTR_LLND first, pt; { PTR_LLND tail = first; if (!pt) return first; if (!first) return pt; else { while (NODE_OPERAND1(tail)) tail = NODE_OPERAND1(tail); NODE_OPERAND1(tail) = pt; return first; } } /* was find_class_bfnd(object)*/ /***************************************************************************/ PTR_BFND getObjectStmt(object) PTR_SYMB object; { PTR_TYPE type; if (!object) return NULL; type = FollowTypeBaseAndDerived(SYMB_TYPE(object)); if (type) { if (isStructType(TYPE_CODE(type)) || isEnumType(TYPE_CODE(type)) || isUnionType(TYPE_CODE(type)) ) { return TYPE_COLL_ORI_CLASS(type); } else Message("unexpected class/struct constructs",0); } return NULL; } /* was chain_field_symb() */ /***************************************************************************/ void addSymbToFieldList(first_one, current_one) PTR_SYMB first_one,current_one ; { PTR_SYMB old_symb,symb; if (!first_one || !current_one) return; for ( old_symb = symb = first_one ;symb ; ) { old_symb = symb ; symb = getClassNextFieldOrMember(symb); } if (SYMB_CODE(old_symb) == FIELD_NAME) SYMB_NEXT_FIELD(old_symb) = current_one ; else /* if(SYMB_CODE(old_symb) = MEMBER_FUNC) */ SYMB_MEMBER_NEXT(old_symb) = current_one ; old_symb->next_symb = current_one; } /* look for Array Reference From an expression There are chained in an expression list */ /***************************************************************************/ PTR_LLND LibarrayRefs(expr,listin) PTR_LLND expr,listin; { PTR_LLND list = listin; if (!expr) return listin; if (NODE_CODE(expr) == ARRAY_REF) { list = addToExprList(list, expr); } list = LibarrayRefs(NODE_OPERAND0(expr),list); list = LibarrayRefs(NODE_OPERAND1(expr),list); return list; } /* all reference to a symbol (does not go inside array index expression ...)*/ /***************************************************************************/ PTR_LLND LibsymbRefs(expr,listin) PTR_LLND expr,listin; { PTR_LLND list = listin; if (!expr) return listin; if (hasNodeASymb(NODE_CODE(expr))) { list = addToExprList(list, expr); return list; } list = LibsymbRefs(NODE_OPERAND0(expr),list); list = LibsymbRefs(NODE_OPERAND1(expr),list); return list; } /***************************************************************************/ void LibreplaceWithStmt(biftoreplace,newbif) PTR_BFND biftoreplace,newbif; { PTR_BFND before,parent,last; if (!biftoreplace|| !newbif) return; before = getNodeBefore(biftoreplace); parent = BIF_CP(biftoreplace); last = getLastNodeOfStmt(biftoreplace); extractBifSectionBetween(biftoreplace,last); insertBfndListIn(newbif,before,parent); } /***************************************************************************/ PTR_BFND LibdeleteStmt(bif) PTR_BFND bif; { PTR_BFND last,current; if (!bif) return NULL; last = getLastNodeOfStmt(bif); /*podd 03.06.14*/ current = bif; /*podd 19.11.14*/ if(BIF_CODE(bif)==IF_NODE || BIF_CODE(bif)==ELSEIF_NODE) while(current != last && BIF_CODE(last)==ELSEIF_NODE) { current = last; last = getLastNodeOfStmt(last); } else if(BIF_CODE(bif)==FOR_NODE || BIF_CODE(bif)==WHILE_NODE) { while( ((current != last) && (BIF_CODE(last) == FOR_NODE)) || (BIF_CODE(last) == WHILE_NODE) ) { current = last; last = getLastNodeOfStmt(last); } if(BIF_CODE(last)==LOGIF_NODE && BIF_CP(BIF_NEXT(last))==last) last = BIF_NEXT(last); } extractBifSectionBetween(bif,last); return bif; } /***************************************************************************/ int LibIsSymbolReferenced(bif,symb) PTR_BFND bif; PTR_SYMB symb; { PTR_BFND last,temp; if (!bif) return FALSE; last = getLastNodeOfStmt(bif); for (temp = bif; temp; temp = BIF_NEXT (temp)) { if (IsRefToSymb(BIF_LL1(temp),symb) || LibIsSymbolInExpression(BIF_LL1(temp),symb)) return TRUE; if (IsRefToSymb(BIF_LL2(temp),symb) || LibIsSymbolInExpression(BIF_LL2(temp),symb)) return TRUE; if (IsRefToSymb(BIF_LL3(temp),symb) || LibIsSymbolInExpression(BIF_LL3(temp),symb)) return TRUE; if (temp == last) break; } return FALSE; } /***************************************************************************/ PTR_BFND LibextractStmt(bif) PTR_BFND bif; { /*PTR_BFND last;*/ /* podd 15.03.99*/ return LibdeleteStmt (bif); } /***************************************************************************/ PTR_LLND getPositionInExprList(first,pos) PTR_LLND first; int pos; { PTR_LLND tail; int len = 0; if (first == NULL) return NULL; for (tail = first; (len variant == ARITHIF_NODE || temp->variant == COMGOTO_NODE || temp->variant == ASSGOTO_NODE) { PTR_LLND lb; if (temp->variant == COMGOTO_NODE || temp->variant == ASSGOTO_NODE) lb = BIF_LL1(temp); else lb = BIF_LL2(temp); PTR_LABEL arith_lab[256]; int idx = 0; while (lb) { arith_lab[idx++] = NODE_LABEL(NODE_OPERAND0(lb)); lb = NODE_OPERAND1(lb); } int z; for (z = 0; z < idx; ++z) { if (arith_lab[z] && (LABEL_STMTNO(arith_lab[z]) == LABEL_STMTNO(label))) { if (blob) { BLOB_NEXT(blob) = (PTR_BLOB)newNode(BLOB_KIND); blob = BLOB_NEXT(blob); BLOB_VALUE(blob) = temp; } else { blob = (PTR_BLOB)newNode(BLOB_KIND); BLOB_VALUE(blob) = temp; first = blob; } break; } } } else { if (tl && (LABEL_STMTNO(tl) == LABEL_STMTNO(label))) { if (blob) { BLOB_NEXT(blob) = (PTR_BLOB)newNode(BLOB_KIND); blob = BLOB_NEXT(blob); BLOB_VALUE(blob) = temp; } else { blob = (PTR_BLOB)newNode(BLOB_KIND); BLOB_VALUE(blob) = temp; first = blob; } } } } return first; } /***************************************************************************/ void LibconvertLogicIf(PTR_BFND ifst) { if (!ifst) return; if (BIF_CODE(ifst) == LOGIF_NODE) {/* Convert to if */ PTR_BFND last, ctl; BIF_CODE(ifst) = IF_NODE; /* need to add a contro_end */ last = getLastNodeOfStmt(ifst); ctl = (PTR_BFND)newNode(CONTROL_END); insertBfndListIn(ctl, last, ifst); } } /***************************************************************************/ int convertToEnddoLoop(PTR_BFND loop) { PTR_BFND cend, bif, lastcend; PTR_BLOB blob, list_ud; PTR_LABEL label; PTR_CMNT comment; if (!loop) return 0; if (BIF_CODE(loop) != FOR_NODE) return 0; if (!LibisEnddoLoop(loop)) { bif = getLastNodeOfStmt(loop); if (!bif) return 0; while (BIF_CODE(bif) == FOR_NODE) { /* because of continue stmt shared by loops */ bif = getLastNodeOfStmt(bif); if (!bif) return 0; } if (BIF_CODE(bif) == CONT_STAT) { if (BIF_LABEL(bif) != NULL) { label = BIF_LABEL(bif); if (BIF_LABEL_USE(loop) && (LABEL_STMTNO(BIF_LABEL_USE(loop)) == LABEL_STMTNO(label))) { list_ud = getLabelUDChain(label, loop); if (blobListLength(list_ud) <= 1) { cend = (PTR_BFND)newNode(CONTROL_END); BIF_CP(cend) = loop; BIF_LABEL_USE(loop) = NULL; BIF_CMNT(cend) = BIF_CMNT(bif); BIF_LINE(cend) = BIF_LINE(bif); /*Bakhtin 26.01.10*/ bif = deleteBfnd(bif); insertBfndListIn(cend, bif, loop); } else { /* more than on uses of the label check if ok */ for (blob = list_ud; blob; blob = BLOB_NEXT(blob)) { if (!BLOB_VALUE(blob) || (BIF_CODE(BLOB_VALUE(blob)) != FOR_NODE)) return 0; } /* we insert as much enddo than necessary */ comment = BIF_CMNT(bif); bif = deleteBfnd(bif); lastcend = bif; for (blob = list_ud; blob; blob = BLOB_NEXT(blob)) { if (BLOB_VALUE(blob) && (BIF_CODE(BLOB_VALUE(blob)) == FOR_NODE)) { BIF_LABEL_USE(BLOB_VALUE(blob)) = NULL; cend = (PTR_BFND)newNode(CONTROL_END); BIF_CMNT(cend) = comment; BIF_LINE(cend) = BIF_LINE(lastcend); /*Bakhtin 26.01.10*/ comment = NULL; BIF_CMNT(bif) = NULL; insertBfndListIn(cend, lastcend, BLOB_VALUE(blob)); /*lastcend = Get_Node_Before(cend); */ } } } return 1; } else return 0; /* something is wrong the label is not the same */ } else { /* should not appear CONTINUE without label */ cend = (PTR_BFND)newNode(CONTROL_END);/*podd 12.03.99*/ BIF_CMNT(cend) = BIF_CMNT(bif); BIF_LINE(cend) = BIF_LINE(bif); /*Bakhtin 26.01.10*/ bif = deleteBfnd(bif); insertBfndListIn(cend, bif, loop); return 0; } } else { /* this not a enddo or a cont stat; probably a statement */ label = BIF_LABEL(bif); list_ud = getLabelUDChain(label, loop); if (label && blobListLength(list_ud) <= 1) { cend = (PTR_BFND)newNode(CONTROL_END); BIF_LINE(cend) = BIF_LINE(bif); /*Bakhtin 26.01.10*/ insertBfndListIn(cend, bif, loop); BIF_LABEL(bif) = NULL; BIF_LABEL_USE(loop) = NULL; } else return 0; } return 1; } else return 1; } /* (fbodin) Duplicate Symbol and type routine (modified phb) */ /***************************************************************************/ PTR_TYPE duplicateType(type) PTR_TYPE type; { PTR_TYPE newtype; if (!type) return NULL; if (!isATypeNode(NODE_CODE(type))) { Message("duplicateType; Not a type node",0); return NULL; } if (isAtomicType(TYPE_CODE(type)) && TYPE_CODE(type)!= T_STRING && !TYPE_RANGES(type) && !TYPE_KIND_LEN(type)) return(GetAtomicType(TYPE_CODE(type))); /*07.06.06*/ /*22.04.14*/ /***** Allocate a new node *****/ newtype = (PTR_TYPE) newNode(TYPE_CODE(type)); /* Copy the fields that are NOT in the union */ TYPE_SYMB(newtype) = TYPE_SYMB(type); TYPE_LENGTH(newtype) =TYPE_LENGTH(type); /* Copy the size of the union (all of the fields) (phb)*/ memcpy(&(newtype->entry),&(type->entry),sizeof(type->entry)); if (isAtomicType(TYPE_CODE(type))) { if (TYPE_RANGES(type)) TYPE_RANGES(newtype) = copyLlNode(TYPE_RANGES(type)); if (TYPE_KIND_LEN(type)) TYPE_KIND_LEN(newtype) = copyLlNode(TYPE_KIND_LEN(type)); /*22.04.14*/ return newtype; } if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) TYPE_BASE(newtype) = duplicateType(TYPE_BASE(type)); } if (hasTypeSymbol(TYPE_CODE(type))) { TYPE_SYMB_DERIVE(newtype) = TYPE_SYMB_DERIVE(type); } switch (TYPE_CODE(type)) { case T_ARRAY : TYPE_RANGES(newtype) = copyLlNode(TYPE_RANGES(type)); break; case T_DESCRIPT : TYPE_LONG_SHORT(newtype) = TYPE_LONG_SHORT(type); break; } return newtype; } /***************************************************************************/ PTR_SYMB duplicateSymbolAcrossFiles(); PTR_TYPE duplicateTypeAcrossFiles(type) PTR_TYPE type; { PTR_TYPE newtype; if (!type) return NULL; if (!isATypeNode(NODE_CODE(type))) { Message("duplicateTypeAcrossFiles; Not a type node",0); return NULL; } if (isAtomicType(TYPE_CODE(type)) && TYPE_CODE(type)!= T_STRING && !TYPE_RANGES(type) && !TYPE_KIND_LEN(type)) return(GetAtomicType(TYPE_CODE(type))); /*07.06.06*/ /*22.04.14*/ /***** Allocate a new node *****/ newtype = (PTR_TYPE) newNode(TYPE_CODE(type)); /* Copy the fields that are NOT in the union */ TYPE_SYMB(newtype) = TYPE_SYMB(type); TYPE_LENGTH(newtype) =TYPE_LENGTH(type); /* Copy the size of the union (all of the fields) (phb)*/ memcpy(&(newtype->entry),&(type->entry),sizeof(type->entry)); if (isAtomicType(TYPE_CODE(type))) { if (TYPE_RANGES(type)) TYPE_RANGES(newtype) = copyLlNode(TYPE_RANGES(type)); /*07.06.06*/ if (TYPE_KIND_LEN(type)) TYPE_KIND_LEN(newtype) = copyLlNode(TYPE_KIND_LEN(type)); /*22.04.14*/ return newtype; } if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) TYPE_BASE(newtype) = duplicateTypeAcrossFiles(TYPE_BASE(type)); } if (hasTypeSymbol(TYPE_CODE(type))) { TYPE_SYMB_DERIVE(newtype) = duplicateSymbolAcrossFiles(TYPE_SYMB_DERIVE(type)); } switch (TYPE_CODE(type)) { case T_ARRAY : TYPE_RANGES(newtype) = copyLlNode(TYPE_RANGES(type)); break; case T_DESCRIPT : TYPE_LONG_SHORT(newtype) = TYPE_LONG_SHORT(type); break; } return newtype; } /***************************************************************************/ PTR_SYMB duplicateParamList(symb) PTR_SYMB symb; { PTR_SYMB first, previous, ptsymb,ts; ptsymb = SYMB_FUNC_PARAM (symb); ts = NULL; first = NULL; previous = NULL; while (ptsymb) { ts = duplicateSymbol(ptsymb); if (!first) first = ts; if (previous) SYMB_NEXT_DECL (previous) = ts; previous = ts; ptsymb = SYMB_NEXT_DECL (ptsymb); } if (ts) SYMB_NEXT_DECL (ts) = NULL; return first; } /***************************************************************************/ PTR_SYMB duplicateSymbol(symb) PTR_SYMB symb; { PTR_SYMB newsymb; /* char *str;*/ /* podd 15.03.99*/ if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("duplicateSymbol; Not a symbol node",0); return NULL; } newsymb = (PTR_SYMB) newSymbol(SYMB_CODE(symb),SYMB_IDENT(symb),SYMB_TYPE(symb)); SYMB_ATTR(newsymb) = SYMB_ATTR(symb); /* Copy the size of the union (all of the fields) (phb)*/ memcpy(&(newsymb->entry.Template),&(symb->entry.Template), sizeof(newsymb->entry.Template)); /*dirty trick for debug, to identify copie/ str = (char *) xmalloc(512); sprintf(str,"DEBUG%d%s",newsymb,SYMB_IDENT(newsymb)); SYMB_IDENT(newsymb) = str; */ /* copy the expression for Constant Node */ if (SYMB_CODE(newsymb) == CONST_NAME) SYMB_VAL(newsymb) = copyLlNode(SYMB_VAL(newsymb)); return newsymb; } /***************************************************************************/ PTR_SYMB duplicateSymbolLevel1(symb) PTR_SYMB symb; { PTR_SYMB newsymb; if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("duplicateSymbolLevel1; Not a symbol node",0); return NULL; } newsymb = duplicateSymbol(symb); /* to be updated later Not that simple*/ switch (SYMB_CODE(symb)) { case MEMBER_FUNC: case FUNCTION_NAME: case PROCEDURE_NAME: case PROCESS_NAME: SYMB_FUNC_PARAM (newsymb) = duplicateParamList(symb); break; } return newsymb; } /***************************************************************************/ PTR_BFND getBodyOfSymb(symb) PTR_SYMB symb; { /* PTR_SYMB newsymb = NULL;*/ PTR_BFND body = NULL; PTR_TYPE type; if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("getbodyofsymb; not a symbol node",0); return NULL; } switch (SYMB_CODE(symb)) { case MEMBER_FUNC: case FUNCTION_NAME: case PROCEDURE_NAME: case PROCESS_NAME: case MODULE_NAME: body = SYMB_FUNC_HEDR(symb); if (!body) body = getFunctionHeaderAllFile(symb); break; case PROGRAM_NAME: body = symb->entry.prog_decl.prog_hedr; if (!body) body = getFunctionHeaderAllFile(symb); break; case CLASS_NAME: case TECLASS_NAME: case COLLECTION_NAME: type = SYMB_TYPE(symb); if (type) { body = TYPE_COLL_ORI_CLASS(type); } else { Message("body of collection or class not found",0); return NULL; } break; } return body; } /***************************************************************************/ void replaceSymbInExpression(PTR_LLND exprold, PTR_SYMB symb, PTR_SYMB new) { if (!exprold || !symb || !new) return; if (!isASymbNode(SYMB_CODE(symb))) { Message(" not a symbol node in replaceSymbInExpression", 0); return; } if (!isASymbNode(SYMB_CODE(new))) { Message(" not a symbol node in replaceSymbInExpression", 0); return; } if (hasNodeASymb(NODE_CODE(exprold))) { if (NODE_SYMB(exprold) == symb) NODE_SYMB(exprold) = new; } replaceSymbInExpression(NODE_OPERAND0(exprold), symb, new); replaceSymbInExpression(NODE_OPERAND1(exprold), symb, new); } /***************************************************************************/ void replaceSymbInStmts(debut, fin, symb, new) PTR_BFND debut, fin; PTR_SYMB symb,new; { PTR_BFND temp; for (temp = debut; temp; temp = BIF_NEXT(temp)) { if (BIF_SYMB(temp) == symb) BIF_SYMB(temp) = new; replaceSymbInExpression(BIF_LL1(temp), symb, new); replaceSymbInExpression(BIF_LL2(temp), symb, new); replaceSymbInExpression(BIF_LL3(temp), symb, new); if (fin && (temp == fin)) break; } } /***************************************************************************/ void replaceSymbInExpressionSameName(exprold,symb, new) PTR_LLND exprold; PTR_SYMB symb, new; { if (!exprold || !symb || !new) return; if (!isASymbNode(SYMB_CODE(symb))) { Message(" not a symbol node in replaceSymbInExpressionSameName",0); return; } if (!isASymbNode(SYMB_CODE(new))) { Message(" not a symbol node in replaceSymbInExpressionSameName",0); return; } if (hasNodeASymb(NODE_CODE(exprold))) { if (sameName(NODE_SYMB(exprold),symb)) { NODE_SYMB(exprold) = new; } } replaceSymbInExpressionSameName(NODE_OPERAND0(exprold), symb, new); replaceSymbInExpressionSameName(NODE_OPERAND1(exprold), symb, new); } /***************************************************************************/ void replaceSymbInStmtsSameName(debut, fin, symb, new) PTR_BFND debut, fin; PTR_SYMB symb,new; { PTR_BFND temp; for (temp = debut; temp ; temp = BIF_NEXT(temp)) { if (sameName(BIF_SYMB(temp),symb)) BIF_SYMB(temp) = new; replaceSymbInExpressionSameName(BIF_LL1(temp), symb,new); replaceSymbInExpressionSameName(BIF_LL2(temp), symb,new); replaceSymbInExpressionSameName(BIF_LL3(temp), symb,new); if (fin && (temp == fin)) break; } } /***************************************************************************/ PTR_SYMB duplicateSymbolLevel2(symb) PTR_SYMB symb; { PTR_SYMB newsymb; PTR_BFND body,newbody,last,before,cp; PTR_SYMB ptsymb,ptref; if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("duplicateSymbolLevel2; Not a symbol node",0); return NULL; } newsymb = duplicateSymbolLevel1(symb); /* to be updated later Not that simple*/ switch (SYMB_CODE(symb)) { case MEMBER_FUNC: case FUNCTION_NAME: case PROCEDURE_NAME: case PROCESS_NAME: /* duplicate the body */ body = getBodyOfSymb(symb); if (body) { before = getNodeBefore(body); cp = BIF_CP(body); last = getLastNodeOfStmt(body); body = extractBifSectionBetween(body,last); newbody = duplicateStmts (body); insertBfndListIn (body, before,cp); insertBfndListIn (newbody, before,cp); BIF_SYMB(newbody) = newsymb; SYMB_FUNC_HEDR(newsymb) = newbody; /* we have to propagate change in the param list in the new body */ ptsymb = SYMB_FUNC_PARAM (newsymb); ptref = SYMB_FUNC_PARAM (symb); last = getLastNodeOfStmt(newbody); while (ptsymb) { replaceSymbInStmts(newbody,last,ptref,ptsymb); ptsymb = SYMB_NEXT_DECL (ptsymb); ptref = SYMB_NEXT_DECL (ptref); } } break; case CLASS_NAME: case TECLASS_NAME: case COLLECTION_NAME: case STRUCT_NAME: case UNION_NAME: body = getBodyOfSymb(symb); if (body) { before = getNodeBefore(body); cp = BIF_CP(body); last = getLastNodeOfStmt(body); body = extractBifSectionBetween(body,last); newbody = duplicateStmts (body); insertBfndListIn (body, before,cp); insertBfndListIn (newbody, before,cp); BIF_SYMB(newbody) = newsymb; /* probably more to do here */ SYMB_TYPE(newsymb) = duplicateType(SYMB_TYPE(symb)); /* set the new body for the symbol */ TYPE_COLL_ORI_CLASS(SYMB_TYPE(newsymb)) = newbody; } break; } return newsymb; } /***************************************************************************/ int arraySymbol(symb) PTR_SYMB symb; { PTR_TYPE type; if (!symb) return FALSE; type = SYMB_TYPE(symb); if (!type) return FALSE; if (TYPE_CODE(type) == T_ARRAY) return TRUE; return FALSE; } /***************************************************************************/ int pointerType(type) PTR_TYPE type; { if (!type) return FALSE; return isPointerType(TYPE_CODE(type)); } /***************************************************************************/ int isIntegerType(type) PTR_TYPE type; { if (!type) return FALSE; return (TYPE_CODE(type) == T_INT); } /***************************************************************************/ /* this function was all wrong, fixed May 25 1994, BW */ PTR_SYMB getFieldOfStructWithName(name,typein) char *name; PTR_TYPE typein; { PTR_TYPE type; PTR_SYMB ptsymb = NULL; if (!typein || !name) return NULL; type = SYMB_TYPE(TYPE_SYMB_DERIVE(typein)); if(TYPE_CODE(type) == T_DESCRIPT) type = TYPE_BASE(type); /* the if statement above is necessary because of another bug */ /* with "friend" specifier */ ptsymb = TYPE_COLL_FIRST_FIELD(type); if (! (ptsymb)) Message("did not find the first field\n",0); while (ptsymb) { if (!strcmp(SYMB_IDENT(ptsymb), name)) return ptsymb; ptsymb = getClassNextFieldOrMember (ptsymb); } return NULL; } /***************************************************************************/ PTR_LLND addLabelRefToExprList(expl,label) PTR_LLND expl; PTR_LABEL label; { PTR_LLND tmp, lptr,pt; if (!label) return expl; pt = (PTR_LLND) newNode(LABEL_REF); NODE_LABEL(pt) = label; tmp = newExpr(EXPR_LIST,NULL,pt,NULL); if (!expl) return tmp; lptr = Follow_Llnd(expl,2); NODE_OPERAND1(lptr) = tmp; return expl; } /***************************************************************************/ PTR_BFND getStatementNumber(bif,pos) int pos; PTR_BFND bif; { PTR_BFND ptbfnd = NULL; /* PTR_TYPE type;*/ /* podd 15.03.99*/ int count = 0; if (!bif) return NULL; ptbfnd = bif; while (ptbfnd) { count++; if (count == pos) return ptbfnd; ptbfnd = BIF_NEXT(ptbfnd); } return NULL; } /***************************************************************************/ PTR_LLND deleteNodeInExprList(first,pos) PTR_LLND first; int pos; { PTR_LLND tail,old = NULL; int len = 0; if (first == NULL) return NULL; if (pos == 0) return NODE_OPERAND1(first); for (tail = first; tail; tail = NODE_OPERAND1(tail) ) { len++; if (len == pos) { NODE_OPERAND1(old) = NODE_OPERAND1(tail); return first; } old = tail; } return first; } /***************************************************************************/ PTR_LLND deleteNodeWithItemInExprList(first,ll) PTR_LLND first,ll; { PTR_LLND tail,old = NULL; if (first == NULL) return NULL; if (NODE_OPERAND0(first) == ll) return NODE_OPERAND1(first); for (tail = first; tail; tail = NODE_OPERAND1(tail) ) { if (NODE_OPERAND0(tail) == ll) { NODE_OPERAND1(old) = NODE_OPERAND1(tail); return first; } old = tail; } return first; } /***************************************************************************/ PTR_LLND addSymbRefToExprList(expl,symb) PTR_LLND expl; PTR_SYMB symb; { PTR_LLND tmp, lptr,pt; if (!symb) return expl; pt = newExpr(VAR_REF,SYMB_TYPE(symb), symb); tmp = newExpr(EXPR_LIST,NULL,pt,NULL); if (!expl) return tmp; lptr = Follow_Llnd(expl,2); NODE_OPERAND1(lptr) = tmp; return expl; } /* functions mainly dedicated to libcreatecollectionwithtype */ /***************************************************************************/ void duplicateAllSymbolDeclaredInStmt(symb,stmt, oldident) PTR_SYMB symb; /* symb is not to duplicate */ PTR_BFND stmt; char *oldident; { PTR_SYMB oldsymb, newsymb, ptsymb, ptref; PTR_BFND cur,last,last1; /*PTR_BFND body;*/ /* podd 15.03.99*/ PTR_BFND cur1,last2; PTR_LLND ll1, ll2; char str[512], *str1 = NULL; PTR_SYMB tabsymbold[MAX_SYMBOL_FOR_DUPLICATE]; PTR_SYMB tabsymbnew[MAX_SYMBOL_FOR_DUPLICATE]; int nbintabsymb = 0; int i; if (!stmt || !symb ) return; last = getLastNodeOfStmt(stmt); /* if that is a class/collection we have to take care of the constructor and destructor */ if (oldident) { str1 = (char *) xmalloc(strlen(SYMB_IDENT(symb))+2); if ((int)strlen(oldident) >= 511) { Message("internal error: string too long exit",0); exit(1); } sprintf(str1,"~%s",SYMB_IDENT(symb)); sprintf(str,"~%s",oldident); } for (cur = stmt; cur ; cur = BIF_NEXT(cur)) { if ((BIF_CODE(cur) == FUNC_HEDR) && (isInStmt(stmt,cur))) { /* local declaration, update the owner */ if (BIF_SYMB(cur)) { oldsymb = BIF_SYMB(cur); newsymb = duplicateSymbolLevel1(BIF_SYMB(cur)); /* str1 = (char *) xmalloc(512); sprintf(str1,"COPYFORDEBUG%d%s",newsymb,SYMB_IDENT(newsymb)); SYMB_IDENT(newsymb) = str1;*/ tabsymbold[nbintabsymb] = oldsymb; tabsymbnew[nbintabsymb] = newsymb; nbintabsymb ++; if (nbintabsymb >= MAX_SYMBOL_FOR_DUPLICATE) { Message("To many symbol in duplicateAllSymbolDeclaredInStmt",0); exit(1); } BIF_SYMB(cur) = newsymb; SYMB_FUNC_HEDR(newsymb) = cur; SYMB_SCOPE(newsymb) = stmt; ptsymb = SYMB_FUNC_PARAM (newsymb); ptref = SYMB_FUNC_PARAM (oldsymb); last2 = getLastNodeOfStmt(cur); while (ptsymb) { replaceSymbInStmts(cur,last2,ptref,ptsymb); ptsymb = SYMB_NEXT_DECL (ptsymb); ptref = SYMB_NEXT_DECL (ptref); } duplicateAllSymbolDeclaredInStmt(newsymb,cur,oldident); if (SYMB_CODE(newsymb) == MEMBER_FUNC) { /* there is more to do here */ SYMB_MEMBER_BASENAME(newsymb) = symb; } if (oldident) { /* change name of constructor and destructor */ if (!strcmp(SYMB_IDENT(newsymb),oldident)) { SYMB_IDENT(newsymb) = SYMB_IDENT(symb); } if (!strcmp(SYMB_IDENT(newsymb),str)) { SYMB_IDENT(newsymb) = str1; } } cur = getLastNodeOfStmt(cur); } } if ((BIF_CODE(cur) == VAR_DECL) && (isInStmt(stmt,cur))) { /* we have to declare what is declare there */ /* ll1= BIF_LL1(cur); this is the declaration */ for (ll1= BIF_LL1(cur); ll1; ll1 = NODE_OPERAND1(ll1)) { ll2 = giveLlSymbInDeclList(NODE_OPERAND0(ll1)); if (ll2 && NODE_SYMB(ll2) && (NODE_SYMB(ll2) != symb)) { oldsymb = NODE_SYMB(ll2); NODE_SYMB(ll2) = duplicateSymbolLevel2(NODE_SYMB(ll2)); tabsymbold[nbintabsymb] = oldsymb; tabsymbnew[nbintabsymb] = NODE_SYMB(ll2); nbintabsymb ++; if (nbintabsymb >= MAX_SYMBOL_FOR_DUPLICATE) { Message("To many symbol in duplicateAllSymbolDeclaredInStmt",0); exit(1); } /* apply recursively */ if (getBodyOfSymb(NODE_SYMB(ll2)) && (!isInStmt(stmt,getBodyOfSymb(NODE_SYMB(ll2))))) { duplicateAllSymbolDeclaredInStmt(NODE_SYMB(ll2), getBodyOfSymb(NODE_SYMB(ll2)),oldident); } /* if member function we must attach the new symbol of collection also true for field name */ if (SYMB_CODE(NODE_SYMB(ll2)) == MEMBER_FUNC) { /* there is more to do here */ SYMB_MEMBER_BASENAME(NODE_SYMB(ll2)) = symb; } if (SYMB_CODE(NODE_SYMB(ll2)) == FIELD_NAME) { /* there is more to do here */ SYMB_FIELD_BASENAME(NODE_SYMB(ll2)) = symb; } SYMB_SCOPE(NODE_SYMB(ll2)) = stmt; /* is that correct??? */ if (oldident) { /* change name of constructor and destructor */ if (!strcmp(SYMB_IDENT(NODE_SYMB(ll2)),oldident)) { SYMB_IDENT(NODE_SYMB(ll2)) = SYMB_IDENT(symb); } if (!strcmp(SYMB_IDENT(NODE_SYMB(ll2)),str)) { SYMB_IDENT(NODE_SYMB(ll2)) = str1; } } /* we have to replace the old symbol in the section */ replaceSymbInStmts(stmt,last,oldsymb,NODE_SYMB(ll2)); } } } if (cur == last) break; } /* we need to replace in the member function the symbol declared in the structure */ for (cur = stmt; cur ; cur = BIF_NEXT(cur)) { if ((BIF_CODE(cur) == FUNC_HEDR) && isInStmt(stmt,cur)) { /* local declaration, update the owner */ if (BIF_SYMB(cur)) { cur1 = stmt; last1 = getLastNodeOfStmt(cur1); for (i=0; i */ symb1 = TYPE_SYMB_DERIVE(type1); symb2 = TYPE_SYMB_DERIVE(type2); if (symb1 && symb2) { if (symb1 == symb2) return isTypeEquivalent(TYPE_COLL_BASE(type1), TYPE_COLL_BASE(type2)); else if (sameName(symb1,symb2)) /* this is a type name, the same ident should be enough*/ return isTypeEquivalent(TYPE_COLL_BASE(type1), TYPE_COLL_BASE(type2)); else return 0; } } else if (hasTypeSymbol(TYPE_CODE(type1))) { symb1 = TYPE_SYMB_DERIVE(type1); symb2 = TYPE_SYMB_DERIVE(type2); if (symb1 && symb2) { if (symb1 == symb2) return 1; else if (sameName(symb1,symb2)) /* this is a type name, the same ident should be enough*/ return 1; else return 0; } } return(0); } /***************************************************************************/ int lookForTypeInType(type,comp) PTR_TYPE type,comp; { if (!type) return 0; if (!isATypeNode(TYPE_CODE(type))) { Message("lookForTypeInType; arg1 Not a type node",0); return 0; } if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) { if (isTypeEquivalent(TYPE_BASE(type), comp)) { return 1; } return lookForTypeInType(TYPE_BASE(type),comp); } } return 0; } /***************************************************************************/ int replaceTypeInType(type,comp,new) PTR_TYPE type,comp,new; { if (!type) return 0; if (!isATypeNode(TYPE_CODE(type))) { Message("replaceTypeInType; arg1 Not a type node",0); return 0; } if (hasTypeBaseType(TYPE_CODE(type))) { if (TYPE_BASE(type)) { if (isTypeEquivalent(TYPE_BASE(type), comp)) { TYPE_BASE(type) = new; return 1; } return replaceTypeInType(TYPE_BASE(type),comp,new); } } return 0; } /***************************************************************************/ void replaceTypeForSymb(symb, type, new) PTR_SYMB symb; PTR_TYPE type, new; { PTR_TYPE ts; PTR_SYMB ptsymb; if (!symb || !type || !new) return; if (!isATypeNode(TYPE_CODE(type))) { Message(" not a type node in replaceTypeForSymb",0); return; } if (!isASymbNode(SYMB_CODE(symb))) { Message(" not a symbol node in replaceTypeForSymb",0); return; } ts = SYMB_TYPE(symb); if (isTypeEquivalent(ts,type)) { SYMB_TYPE(symb) = new; } else if (lookForTypeInType(ts,type)) { SYMB_TYPE(symb) = duplicateType(SYMB_TYPE(symb)); replaceTypeInType(SYMB_TYPE(symb),type, new); } /* look if have a param list */ switch (SYMB_CODE(symb)) { case MEMBER_FUNC: case FUNCTION_NAME: case PROCEDURE_NAME: case PROCESS_NAME: ptsymb = SYMB_FUNC_PARAM (symb); while (ptsymb) { replaceTypeForSymb(ptsymb,type,new); ptsymb = SYMB_NEXT_DECL (ptsymb); } break; } } /***************************************************************************/ void replaceTypeInExpression(exprold, type, new) PTR_LLND exprold; PTR_TYPE type, new; { /* PTR_SYMB symb, newsymb;*/ /* podd 15.03.99*/ if (!exprold || !type || !new) return; if (!isATypeNode(TYPE_CODE(type))) { Message(" not a type node in replaceTypeInExpression",0); return; } if (!isATypeNode(TYPE_CODE(new))) { Message(" not a type node in replaceTypeInExpression",0); return; } if (isTypeEquivalent(NODE_TYPE(exprold),type)) { NODE_TYPE(exprold) = new; } else { if (lookForTypeInType(NODE_TYPE(exprold),type)) { NODE_TYPE(exprold) = duplicateType(NODE_TYPE(exprold)); replaceTypeInType(NODE_TYPE(exprold),type,new); } } /* if (hasNodeASymb(NODE_CODE(exprold))) do not do that it will alias some symbols not to be changes { if (symb = NODE_SYMB(exprold)) { replaceTypeForSymb(symb,type,new); } }*/ replaceTypeInExpression(NODE_OPERAND0(exprold), type, new); replaceTypeInExpression(NODE_OPERAND1(exprold), type, new); } /***************************************************************************/ void replaceTypeInStmts(debut, fin, type, new) PTR_BFND debut, fin; PTR_TYPE type,new; { PTR_BFND temp; for (temp = debut; temp ; temp = BIF_NEXT(temp)) { /* if (BIF_SYMB(temp)) do not do that it will alias some symbols not to be changes { replaceTypeForSymb(BIF_SYMB(temp),type,new); }*/ replaceTypeInExpression(BIF_LL1(temp), type,new); replaceTypeInExpression(BIF_LL2(temp), type,new); replaceTypeInExpression(BIF_LL3(temp), type,new); if (fin && (temp == fin)) break; } } /* the following fonction are mainly dedicated to libcreatecollectionwithtype used in the C++ library also with symb == NULL */ /***************************************************************************/ void replaceTypeUsedInStmt(symb,stmt,type,new) PTR_SYMB symb; /* symb is not to duplicate */ PTR_BFND stmt; PTR_TYPE type,new; { PTR_SYMB oldsymb; PTR_BFND cur,last,body; PTR_LLND ll1, ll2; if (!stmt) return; last = getLastNodeOfStmt(stmt); if (symb) replaceTypeForSymb(symb,type,new); replaceTypeInStmts(stmt,last,type,new); for (cur = stmt; cur ; cur = BIF_NEXT(cur)) { if (symb) { if (isADeclBif(BIF_CODE(cur)) && (isInStmt(stmt,cur))) { /* we have to declare what is declare there */ for (ll1= BIF_LL1(cur); ll1; ll1 = NODE_OPERAND1(ll1)) { ll2 = giveLlSymbInDeclList(NODE_OPERAND0(ll1)); if (ll2 && NODE_SYMB(ll2) && (NODE_SYMB(ll2) != symb)) { oldsymb = NODE_SYMB(ll2); /*symbol is declared here so change the type*/ replaceTypeForSymb(oldsymb,type,new); /* apply recursively */ body = getBodyOfSymb(NODE_SYMB(ll2)); if (body && (!isInStmt(stmt,body))) { replaceTypeUsedInStmt(NODE_SYMB(ll2),body,type,new); replaceTypeInStmts(body,getLastNodeOfStmt(body),type,new); } } } } } else { /* simpler we have just to look the stmt this is an replacement for everywhere */ if (isADeclBif(BIF_CODE(cur))) { /* we have to declare what is declare there */ for (ll1= BIF_LL1(cur); ll1; ll1 = NODE_OPERAND1(ll1)) { ll2 = giveLlSymbInDeclList(NODE_OPERAND0(ll1)); if (ll2 && NODE_SYMB(ll2) && (NODE_SYMB(ll2) != symb)) { oldsymb = NODE_SYMB(ll2); /*symbol is declared here so change the type*/ replaceTypeForSymb(oldsymb,type,new); } } } } if (cur == last) break; } } /***************************************************************************/ PTR_TYPE createDerivedCollectionType(col,etype) PTR_SYMB col; PTR_TYPE etype; { PTR_TYPE newtc; newtc = (PTR_TYPE) newNode(T_DERIVED_COLLECTION); /*wasted*/ TYPE_COLL_BASE(newtc) = etype; TYPE_SYMB_DERIVE(newtc) = col; return newtc; } /* the following function is not trivial take a collection and generate the right instance of the collection with name collection_typename. replace the type in the new body by the right one needs many duplication, not only duplicate for the code, but also for symbol type and so on this function is presently use in the translator pc++2c++ make basically an identical work as Templates........ elemtype is going to replace elementtype; warning, all the symbol are not duplicated, expression are not duplicated too useless to to it for all (at least for the moment) */ /***************************************************************************/ PTR_BFND LibcreateCollectionWithType(colltype, elemtype) PTR_TYPE colltype, elemtype; { PTR_SYMB coltoduplicate, copystruct,se = NULL; PTR_TYPE etype,newt,newtc; int len; char *newname; if (!colltype || !elemtype) return NULL; /* the symbol we are duplicating */ coltoduplicate = TYPE_SYMB_DERIVE(colltype); etype = getDerivedTypeWithName("ElementType"); if (!coltoduplicate || !etype) { Message("internal error in libcreatecollectionwithtype",0); return NULL; } if (TYPE_CODE(elemtype) == T_DERIVED_TYPE) { se = TYPE_SYMB_DERIVE(elemtype); if (!se) { Message("The element type must be a class type-1",0); exit(1); } if (!SYMB_TYPE(se)) { Message("The element type must be a class type-2",0); exit(1); } if (SYMB_TYPE(se) && ((TYPE_CODE(SYMB_TYPE(se)) != T_CLASS) && (TYPE_CODE(SYMB_TYPE(se)) != T_TECLASS))) { Message("The element type must be a class type-3",0); exit(1); } } /* look for element type is given by iselementtype(type) */ /* first we have to duplicate the code look at all the symbol */ /* first duplicate the collection structure then we will do the methods declare outside of the structure */ copystruct = duplicateSymbolLevel2(coltoduplicate); if (!copystruct) Message("internal error in LibcreateCollectionWithType",0); /* duplicate at level 2 so must it is not necessary to do more for duplicating */ /* we have to set the new ID for the symbol according to the element type */ len = strlen(SYMB_IDENT(copystruct)) + strlen(SYMB_IDENT(se))+10; newname = (char *) xmalloc(len); memset(newname, 0, len); sprintf(newname,"%s__%s",SYMB_IDENT(copystruct),SYMB_IDENT(se)); SYMB_IDENT(copystruct) = newname; /* duplicate the symbol declared inside so we can attach a new type eventually */ duplicateAllSymbolDeclaredInStmt(copystruct, getBodyOfSymb(copystruct),SYMB_IDENT(coltoduplicate)); /* the collection body and the method have been duplicated no we have to replace the type */ /* first replace element type */ replaceTypeUsedInStmt(copystruct, getBodyOfSymb(copystruct),etype,elemtype); /* now replace type like DistributedArray but first construct the new type corresponding to that */ newt = (PTR_TYPE) newNode(T_DERIVED_CLASS); TYPE_SYMB_DERIVE(newt) = copystruct; /* need to create a type for reference */ newtc = createDerivedCollectionType(coltoduplicate,etype); replaceTypeUsedInStmt(copystruct, getBodyOfSymb(copystruct),newtc,newt); /* replacing DistributedArray for instance is done elsewhere*/ return getBodyOfSymb(copystruct); } /***************************************************************************/ int LibisMethodOfElement(symb) PTR_SYMB symb; { if (!symb) return FALSE; if ((int) SYMB_ATTR(symb) & (int) ELEMENT_FIELD) return TRUE; else return FALSE; } /***************************************************************************/ PTR_BFND LibfirstElementMethod(coll) PTR_BFND coll; { PTR_BFND pt,last; PTR_SYMB symb; PTR_LLND ll; if (!coll ) return NULL; last = getLastNodeOfStmt(coll); for (pt = coll; pt && (pt != BIF_NEXT(last)); pt = BIF_NEXT(pt)) { if (isADeclBif(BIF_CODE(pt)) && (BIF_CP(pt) == coll)) { ll = giveLlSymbInDeclList(BIF_LL1(pt)); if (ll && NODE_SYMB(ll)) { symb = NODE_SYMB(ll); if (LibisMethodOfElement(symb)) return pt; } } } return NULL; } /***************************************************************************/ int buildLinearRep(exp,coef,symb,size,last) PTR_LLND exp; int *coef; PTR_SYMB *symb; int size; int *last; { return buildLinearRepSign(exp,coef,symb,size, last,1,1); } /* initialy coeff are 0, return 1 if Ok, 0 if abort*/ /***************************************************************************/ int buildLinearRepSign(exp,coef,symb,size, last,sign,factor) PTR_LLND exp; int *coef; PTR_SYMB *symb; int size; int *last; int sign; int factor; { int code; int i, *res1,*res2; if (!exp) return TRUE; code = NODE_CODE(exp); switch (code) { case VAR_REF: for (i=0; i< size; i++) { if (NODE_SYMB(exp) == symb[i]) { coef[i] = coef[i] + sign*factor; return TRUE; } } return FALSE; case SUBT_OP: if (!buildLinearRepSign(NODE_OPERAND0(exp),coef,symb,size,last,sign,factor)) return FALSE; if (!buildLinearRepSign(NODE_OPERAND1(exp),coef,symb,size,last,-1*sign,factor)) return FALSE; break; case ADD_OP: if (!buildLinearRepSign(NODE_OPERAND0(exp),coef,symb,size,last,sign,factor)) return FALSE; if (!buildLinearRepSign(NODE_OPERAND1(exp),coef,symb,size,last,sign,factor)) return FALSE; break; case MULT_OP: res1 = evaluateExpression (NODE_OPERAND0(exp)); res2 = evaluateExpression (NODE_OPERAND1(exp)); if ((res1[0] != -1) && (res2[0] != -1)) { *last = *last + factor*sign*(res1[1]*res2[1]); } else { int found; if (res1[0] != -1) { /* la constante est le fils gauche */ if (NODE_CODE(NODE_OPERAND1(exp)) != VAR_REF) return buildLinearRepSign(NODE_OPERAND1(exp),coef,symb,size, last,sign,res1[1]*factor); found = 0; for (i=0; i< size; i++) { if (NODE_SYMB(NODE_OPERAND1(exp)) == symb[i]) { coef[i] = coef[i] + factor*sign*(res1[1]); found = 1; break; } } if (!found) return FALSE; } else if (res2[0] != -1) { /* la constante est le fils droit */ if (NODE_CODE(NODE_OPERAND0(exp)) != VAR_REF) return buildLinearRepSign(NODE_OPERAND0(exp),coef,symb,size, last,sign,res2[1]*factor); found =0; for (i=0; i< size; i++) { if (NODE_SYMB(NODE_OPERAND0(exp)) == symb[i]) { coef[i] = coef[i] + factor*sign*(res2[1]); found = 1; break; } } if (!found) return FALSE; } else return FALSE; } break; case INT_VAL: *last = *last + factor*sign*(NODE_INT_CST_LOW(exp)); break; default: return FALSE; } return TRUE; } /********************** FB ADDED JULY 94 *********************** * ALLOW TO COPY A FULL SYMBOL ACCROSS FILE * * THIS IS A FRAGILE FUNCTION BE CAREFUL WITH IT * ***************************************************************/ void resetDoVarForSymb() { PTR_FILE ptf, saveptf; PTR_BLOB ptb; /* PTR_BFND tmp;*/ /* podd 15.03.99*/ PTR_SYMB tsymb; saveptf = pointer_on_file_proj; for (ptb = PROJ_FILE_CHAIN (cur_proj); ptb ; ptb = BLOB_NEXT (ptb)) { ptf = (PTR_FILE) BLOB_VALUE (ptb); cur_file = ptf; /* reset the toolbox and pointers*/ Init_Tool_Box(); for (tsymb = PROJ_FIRST_SYMB() ; tsymb; tsymb = SYMB_NEXT(tsymb)) { tsymb->dovar = 0; } } cur_file = saveptf; Init_Tool_Box(); } void updateTypesAndSymbolsInBody(symb, stmt, where) PTR_BFND stmt, where; PTR_SYMB symb; { PTR_SYMB oldsymb, newsymb, param; PTR_BFND cur,last; PTR_LLND ll1, ll2; PTR_TYPE type,new; int isparam; if (!stmt) return; last = getLastNodeOfStmt(stmt); for (cur = stmt; cur ; cur = BIF_NEXT(cur)) { if (isADeclBif(BIF_CODE(cur))) { /* we have to declare what is declare there */ for (ll1= BIF_LL1(cur); ll1; ll1 = NODE_OPERAND1(ll1)) { ll2 = giveLlSymbInDeclList(NODE_OPERAND0(ll1)); if (ll2 && NODE_SYMB(ll2) && (NODE_SYMB(ll2) != symb)) { oldsymb = NODE_SYMB(ll2); if (oldsymb != symb) { /* should check for param since already propagated needs TO BE WRITTEN EXPRESSION?????? */ param = SYMB_FUNC_PARAM (symb); isparam = 0; while (param) { if (param == oldsymb ) { isparam = 1; break; } param = SYMB_NEXT_DECL (param ); } if (! isparam) { newsymb = duplicateSymbolAcrossFiles(oldsymb, where); SYMB_SCOPE(newsymb) = stmt; type = SYMB_TYPE(oldsymb); new = duplicateTypeAcrossFiles(type); SYMB_TYPE(newsymb) = new; replaceTypeInStmts(stmt, last, type, new); replaceSymbInStmts(stmt,last,oldsymb,newsymb); } } } } } if (cur == last) break; } } PTR_SYMB duplicateSymbolAcrossFiles(symb, where) PTR_SYMB symb; PTR_BFND where; { PTR_SYMB newsymb; PTR_BFND body,newbody,last,before,cp; PTR_SYMB ptsymb,ptref; if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("duplicateSymbolAcrossFiles; Not a symbol node",0); return NULL; } if (symb->dovar) { /* already duplicated don't do it again */ return symb; } newsymb = duplicateSymbolLevel1(symb); newsymb->dovar = 1; symb->dovar = 1; /* need a function resetDovar for all files and all symb to be called before*/ SYMB_SCOPE(newsymb) = where; /* to be updated later Not that simple*/ switch (SYMB_CODE(symb)) { case MEMBER_FUNC: case FUNCTION_NAME: case PROCEDURE_NAME: case PROCESS_NAME: /* find the body in the right file????*/ body = getBodyOfSymb(symb); if (body) { before = getNodeBefore(body); cp = BIF_CP(body); last = getLastNodeOfStmt(body); newbody = duplicateStmtsNoExtract(body); if (BIF_CODE (where) == GLOBAL) insertBfndListIn (newbody, where,where); else insertBfndListIn (newbody, where,BIF_CP(where)); BIF_SYMB(newbody) = newsymb; SYMB_FUNC_HEDR(newsymb) = newbody; /* we have to propagate change in the param list in the new body */ ptsymb = SYMB_FUNC_PARAM (newsymb); ptref = SYMB_FUNC_PARAM (symb); last = getLastNodeOfStmt(newbody); while (ptsymb) { SYMB_SCOPE(ptsymb) = newbody; replaceSymbInStmts(newbody,last,ptref,ptsymb); ptsymb = SYMB_NEXT_DECL (ptsymb); ptref = SYMB_NEXT_DECL (ptref); } /* update the all the symbol and type used in the statement */ updateTypesAndSymbolsInBody(newsymb,newbody, where); /* printf(">>>>>>>>>>>>>>>>>>>>>>\n"); UnparseProgram(stdout); printf("<<<<<<<<<<<<<<<<<<<<<<\n");*/ } break; case TECLASS_NAME: case CLASS_NAME: case COLLECTION_NAME: case STRUCT_NAME: case UNION_NAME: body = getBodyOfSymb(symb); if (body) { cp = BIF_CP(body);/*podd 12.03.99*/ before = getNodeBefore(body);/*podd 12.03.99*/ newbody = duplicateStmtsNoExtract(body); insertBfndListIn (newbody, before,cp); BIF_SYMB(newbody) = newsymb; /* probably more to do here */ SYMB_TYPE(newsymb) = duplicateTypeAcrossFiles(SYMB_TYPE(symb)); /* set the new body for the symbol */ TYPE_COLL_ORI_CLASS(SYMB_TYPE(newsymb)) = newbody; updateTypesAndSymbolsInBody(newsymb,newbody, where); } break; } return newsymb; } /*-----------------------------------------------------------------*/ /*podd 20.03.07*/ void updateExpression(exp, symb, newsymb) PTR_LLND exp; PTR_SYMB symb, newsymb; { PTR_SYMB param,newparam; param = SYMB_FUNC_PARAM (symb); newparam = SYMB_FUNC_PARAM (newsymb); while(param) { replaceSymbInExpression(exp,param, newparam); param=SYMB_NEXT_DECL(param); newparam=SYMB_NEXT_DECL(newparam); } } /*podd 06.06.06*/ void updateTypeAndSymbolInStmts(PTR_BFND stmt, PTR_BFND last, PTR_SYMB oldsymb, PTR_SYMB newsymb) { PTR_TYPE type, new; type = SYMB_TYPE(oldsymb); new = duplicateTypeAcrossFiles(type); SYMB_TYPE(newsymb) = new; replaceTypeInStmts(stmt, last, type, new); replaceSymbInStmts(stmt, last, oldsymb, newsymb); } /*podd 26.02.19*/ void replaceSymbByNameInExpression(PTR_LLND exprold, PTR_SYMB new) { if(!exprold) return; if (hasNodeASymb(NODE_CODE(exprold))) { if ( !strcmp(SYMB_IDENT(NODE_SYMB(exprold)), new->ident) ) NODE_SYMB(exprold) = new; } replaceSymbByNameInExpression(NODE_OPERAND0(exprold), new); replaceSymbByNameInExpression(NODE_OPERAND1(exprold), new); } /*podd 26.02.19*/ void replaceSymbByNameInConstantValues(PTR_SYMB first_const_name, PTR_SYMB new) { PTR_SYMB s; for (s=first_const_name; s; s = SYMB_LIST(s)) { replaceSymbByNameInExpression (SYMB_VAL(s),new); } } /*podd 26.02.19*/ void updateConstantSymbolsInParameterValues(PTR_SYMB first_const_name) { PTR_SYMB symb, prev_symb; for (symb=first_const_name; symb; symb = SYMB_LIST(symb)) { replaceSymbByNameInConstantValues(first_const_name,symb); } symb=first_const_name; while (symb) { prev_symb = symb; symb = SYMB_LIST(symb); SYMB_LIST(prev_symb) = SMNULL; } } /*podd 26.02.19*/ void replaceSymbInType(PTR_TYPE type, PTR_SYMB newsymb) { if (!type) return; if (!isATypeNode(NODE_CODE(type))) { Message("duplicateTypeAcrossFiles; Not a type node",0); return ; } if (isAtomicType(TYPE_CODE(type))) { replaceSymbByNameInExpression(TYPE_RANGES(type),newsymb); replaceSymbByNameInExpression(TYPE_KIND_LEN(type),newsymb); } if (hasTypeBaseType(TYPE_CODE(type))) replaceSymbInType(TYPE_BASE(type), newsymb); if ( TYPE_CODE(type) == T_ARRAY) replaceSymbByNameInExpression(TYPE_RANGES(type),newsymb); } /*podd 26.02.19*/ void replaceSymbInTypeOfSymbols(PTR_SYMB newsymb,PTR_SYMB first_new) { PTR_SYMB symb; for( symb=first_new; symb; symb = SYMB_NEXT(symb) ) replaceSymbInType(SYMB_TYPE(symb),newsymb); } /*podd 26.02.19*/ void updatesSymbolsInTypeExpressions(PTR_BFND new_stmt) { PTR_SYMB symb, first_new; first_new= BIF_SYMB(new_stmt); for( symb=first_new; symb; symb = SYMB_NEXT(symb)) replaceSymbInTypeOfSymbols(symb,first_new); } /*podd 05.12.20*/ void updateSymbInInterfaceBlock(PTR_BFND block) { PTR_BFND last, stmt; PTR_SYMB symb, newsymb; last = getLastNodeOfStmt(block); stmt = BIF_NEXT(block); while(stmt != last) { symb = BIF_SYMB(stmt); if(symb && (BIF_CODE(stmt) == FUNC_HEDR || BIF_CODE(stmt) == PROC_HEDR)) { newsymb = duplicateSymbolLevel1(symb); SYMB_SCOPE(newsymb) = block; updateTypesAndSymbolsInBodyOfRoutine(newsymb, stmt, stmt); stmt = BIF_NEXT(getLastNodeOfStmt(stmt)); } else stmt = BIF_NEXT(stmt); } } void updateSymbolsOfList(PTR_LLND slist, PTR_BFND struct_stmt) { PTR_LLND ll; PTR_SYMB symb, newsymb; for(ll=slist; ll; ll=ll->entry.Template.ll_ptr2) { symb = NODE_SYMB(ll->entry.Template.ll_ptr1); if(symb) { newsymb = duplicateSymbolLevel1(symb); SYMB_SCOPE(newsymb) = struct_stmt; NODE_SYMB(ll->entry.Template.ll_ptr1) = newsymb; } } } void updateSymbolsOfStructureFields(PTR_BFND struct_stmt) { PTR_BFND last, stmt; last = getLastNodeOfStmt(struct_stmt); for(stmt=BIF_NEXT(struct_stmt); stmt!=last; stmt=BIF_NEXT(stmt)) { if(BIF_CODE(stmt) == VAR_DECL || BIF_CODE(stmt) == VAR_DECL_90) updateSymbolsOfList(stmt->entry.Template.ll_ptr1, struct_stmt); } } void updateSymbolsInStructures(PTR_BFND new_stmt) { PTR_BFND last, stmt; last = getLastNodeOfStmt(new_stmt); for(stmt=BIF_NEXT(new_stmt); stmt!=last; stmt=BIF_NEXT(stmt)) { if( BIF_CODE(stmt) == STRUCT_DECL) { updateSymbolsOfStructureFields(stmt); stmt = getLastNodeOfStmt(stmt); } } } void updateSymbolsInInterfaceBlocks(PTR_BFND new_stmt) { PTR_BFND last, stmt; last = getLastNodeOfStmt(new_stmt); for(stmt=BIF_NEXT(new_stmt); stmt!=last; stmt=BIF_NEXT(stmt)) { if(BIF_CODE(stmt) == INTERFACE_STMT || BIF_CODE(stmt) == INTERFACE_ASSIGNMENT || BIF_CODE(stmt) == INTERFACE_OPERATOR ) { updateSymbInInterfaceBlock(stmt); stmt = getLastNodeOfStmt(stmt); } } } PTR_BFND getHedrOfSymb(PTR_SYMB symb, PTR_BFND new_stmt) { PTR_BFND last, stmt; last = getLastNodeOfStmt(new_stmt); for(stmt = new_stmt; stmt != last; stmt = BIF_NEXT(stmt)) { if((stmt->variant == FUNC_HEDR || stmt->variant == PROC_HEDR) && BIF_SYMB(stmt) && !strcmp(symb->ident,BIF_SYMB(stmt)->ident)) return stmt; } return NULL; } void updateTypesAndSymbolsInBodyOfRoutine(PTR_SYMB new_symb, PTR_BFND stmt, PTR_BFND new_stmt) { PTR_SYMB oldsymb, newsymb, until, const_list, first_const_name; PTR_BFND last, last_new; PTR_TYPE type; PTR_SYMB symb, ptsymb, ptref; if (!stmt || !new_stmt) return; symb = BIF_SYMB(stmt); BIF_SYMB(new_stmt) = new_symb; new_symb->decl = 1; if(SYMB_CODE(new_symb) == PROGRAM_NAME) new_symb->entry.prog_decl.prog_hedr = new_stmt; else SYMB_FUNC_HEDR(new_symb) = new_stmt; last_new = getLastNodeOfStmt(new_stmt); updateTypeAndSymbolInStmts(new_stmt, last_new, symb, new_symb); /* we have to propagate change in the param list in the new body */ if(SYMB_CODE(new_symb) == PROGRAM_NAME || SYMB_CODE(new_symb) == MODULE_NAME) ptsymb = ptref = SMNULL; else { ptsymb = SYMB_FUNC_PARAM(new_symb); ptref = SYMB_FUNC_PARAM(symb); } while (ptsymb) { SYMB_SCOPE(ptsymb) = new_stmt; updateTypeAndSymbolInStmts(new_stmt, last_new, ptref, ptsymb); ptsymb = SYMB_NEXT_DECL(ptsymb); ptref = SYMB_NEXT_DECL(ptref); } const_list = first_const_name = SMNULL; /* to make a list of constant names */ last = getLastNodeOfStmt(stmt); if (BIF_NEXT(last) && BIF_CODE(BIF_NEXT(last)) != COMMENT_STAT && stmt != new_stmt) until = BIF_SYMB(BIF_NEXT(last)); else until = SYMB_NEXT(last_file_symbol); /*last_file_symbol is last symbol of source file's Symbol Table */ for (oldsymb = SYMB_NEXT(symb); oldsymb && oldsymb != until; oldsymb = SYMB_NEXT(oldsymb)) { if (SYMB_SCOPE(oldsymb) == stmt) { if (SYMB_TEMPLATE_DUMMY1(oldsymb) != IO) /*is not a dummy parameter */ { newsymb = duplicateSymbolLevel1(oldsymb); if(SYMB_CODE(newsymb)==CONST_NAME) { if(first_const_name == SMNULL) { first_const_name = const_list = newsymb; newsymb->id_list = SMNULL; } const_list->id_list = newsymb; newsymb->id_list = SMNULL; const_list = newsymb; } if((SYMB_CODE(newsymb)==FUNCTION_NAME || SYMB_CODE(newsymb)==PROCEDURE_NAME) && SYMB_FUNC_HEDR(oldsymb)) updateTypesAndSymbolsInBodyOfRoutine(newsymb, SYMB_FUNC_HEDR(oldsymb), getHedrOfSymb(oldsymb,new_stmt)); SYMB_SCOPE(newsymb) = new_stmt; updateTypeAndSymbolInStmts(new_stmt, last_new, oldsymb, newsymb); } } } updateConstantSymbolsInParameterValues(first_const_name); /*podd 26.02.19*/ updatesSymbolsInTypeExpressions(new_stmt); /*podd 26.02.19*/ updateSymbolsInInterfaceBlocks(new_stmt); /*podd 07.12.20*/ updateSymbolsInStructures(new_stmt); /*podd 07.12.20*/ } PTR_SYMB duplicateSymbolOfRoutine(PTR_SYMB symb, PTR_BFND where) { PTR_SYMB newsymb; PTR_BFND body, newbody, last; if (!symb) return NULL; if (!isASymbNode(NODE_CODE(symb))) { Message("duplicateSymbolAcrossFiles; Not a symbol node", 0); return NULL; } newsymb = duplicateSymbolLevel1(symb); SYMB_SCOPE(newsymb) = SYMB_SCOPE(symb); /*where*/ /* to be updated later Not that simple*/ switch (SYMB_CODE(symb)) { case FUNCTION_NAME: case PROCEDURE_NAME: case PROGRAM_NAME: case MODULE_NAME: body = getBodyOfSymb(symb); last = getLastNodeOfStmt(body); newbody = duplicateStmtsNoExtract(body); if (where) { if (BIF_CODE(where) == GLOBAL) insertBfndListIn(newbody, where, where); else insertBfndListIn(newbody, where, BIF_CP(where)); } /* update the all the symbol and type used in the program unit */ updateTypesAndSymbolsInBodyOfRoutine(newsymb, body, newbody); /* printf(">>>>>>>>>>>>>>>>>>>>>>\n"); UnparseProgram(stdout); printf("<<<<<<<<<<<<<<<<<<<<<<\n"); */ break; } return newsymb; }