?? xrun.c
字號:
/*sys lib header files*/#include <stdio.h>#include <stdlib.h>#include <memory.h>/*local application files*/#include "xrun.h" /*--varible---------------------------------------*/ static Funtable *funs; static int funssize; static Caller *calltree; static Caller roottree; static Caller *rootcall= &roottree; static unsigned long cycle = 0;/*--cycles op----------------------------------------*/ unsigned long cycleread(){ return (cycle);}void cyclewrite(unsigned long va){ cycle = va;}/*--funs op----------------------------------------*/ /*--------------------------------------- fun_name: GetFileSizeauthor: date: 20090315purpose: in: out: return: history: create it on 315; -----------------------------------------*/ long GetFileSize(const char* FileNameStr) { long fsize = 0; FILE* fp = fopen(FileNameStr, "r"); if (fp == NULL) return -1; fseek(fp, 0L, SEEK_END); fsize = ftell(fp); fclose(fp); return fsize; } /* insert here 20090318 */int GetFunsCount(const char* FileNameStr){ char count[16]; char cmd[LEN_PER_LINE]; FILE *pp; memset(count, 0x00, 16); memset(cmd, 0x00,LEN_PER_LINE); sprintf(cmd, "cat %s | wc -l", FileNameStr); if((pp = popen(cmd, "r")) == NULL) { printf("popen() error!\n"); exit(1); } fgets(count, 16, pp); count[15] = 0; pclose(pp); return (atoi(count));} /*--------------------------------------- fun_name: transmitfuntableauthor: date: 20090314purpose: in: out: return: history: 20090314 0.0-----------------------------------------*/ void transmitfuntable(const char *filename, Funtable *ft) { FILE *fdb; int len = 0; int i = 0; char linebuf[LEN_PER_LINE]; char *ph = linebuf; if(ft == NULL) return; fdb = fopen(filename, "rb"); if(fdb <= 0) return; memset(linebuf, 0x00, sizeof(char)*LEN_PER_LINE); while(fgets(linebuf, LEN_PER_LINE, fdb) != NULL) { /*id*/ ph = linebuf; ft[i].id = atoi(ph); /*name*/ ph = strchr(ph, ' '); len = strchr(ph + 1, ' ') - ph -1; memcpy(ft[i].name, ph+1, len); /*start & end address*/ ph = strstr(ph, "0x"); ft[i].go = (unsigned int)strtoul(ph+2, NULL, 16); ph = strstr(ph+1, "0x"); ft[i].bound = (unsigned int)strtoul(ph+2, NULL, 16); i++; memset(linebuf, 0x00, sizeof(char)*LEN_PER_LINE); } fclose(fdb); } /*--------------------------------------- fun_name: searchoffauthor: date: purpose: in: out: return: history: -----------------------------------------*/ Offtype searchoff(const unsigned int insna) { int i = 0; Offtype ret = OTHER; /* modify it insna >= funs[1].go */ if((insna >= funs[0].go) && (insna < (funs[funssize-1].go + funs[funssize-1].bound))) { ret = WAIST; for(; i < funssize; i++) { if(insna == funs[i].go) { ret = HEADER; break; } } } return (ret); } /*--------------------------------------- fun_name: searchidauthor: date: purpose: history: 20090314 0.0-----------------------------------------*/ int searchid(const unsigned int insna) { int i = 0; for(; i < funssize; i++) { if(insna == funs[i].go) break; } return (i); } /*--------------------------------------- fun_name: searchnearestidauthor: date: purpose: in: out: return: history: -----------------------------------------*/ int searchnearestid(const unsigned int insna) { int i = 0; for(; i < funssize; i++) { if(insna <= funs[i].go) break; } return (i-1); } /*--------------------------------------- fun_name: searchaddressauthor: date: purpose: in: out: return: history: -----------------------------------------*/ unsigned int searchaddress(const int fid) { int i = 0; for(; i < funssize; i++) { if(fid == funs[i].id) break; } return (funs[i].go); } /*--------------------------------------- fun_name: searchoffsetauthor: date: purpose: get a function 's offsetin: id in funtable.txtout: nonereturn: offsethistory: liyi creat it on 20090401-----------------------------------------*/ unsigned int searchoffset(const int fid) { int i = 0; for(; i < funssize; i++) { if(fid == funs[i].id) break; } return (funs[i].bound); }/*--------------------------------------- fun_name: searchnameasidauthor: date: purpose: in: out: return: history: 20090326 completed-----------------------------------------*/ char *searchnameasid(const int cid) { char *pname = NULL; pname = funs[cid].name; return pname; } /*--caller op----------------------------------------*/ /*--------------------------------------- fun_name: creatcallerauthor: date: 090314purpose: in: out: return: history: create it on 03014 -----------------------------------------*/ Caller * creatcaller(unsigned int cia, unsigned int lia) { Caller *pcall = NULL; pcall = (Caller *)malloc(sizeof(Caller)); if(pcall != NULL) { pcall->id = searchid(cia); pcall->depth = 0; /*exeinfo*/ pcall->exeinfo.parentid = 0; pcall->exeinfo.elapse = 0; pcall->exeinfo.abegin = cia; pcall->exeinfo.aleave = 0; pcall->exeinfo.aretur = lia + 0x00000008; // liyi 20090318 not +4 /*link info*/ pcall->father = NULL; pcall->front = NULL; pcall->next = NULL; pcall->head = NULL; pcall->rear = NULL; } return (pcall);} /*--wiretap op----------------------------------------*/ /*--------------------------------------- fun_name: wiretapkillauthor: date: purpose: in: out: return: history: -----------------------------------------*/ Status KillCallerTree(Caller * tree);void wiretapkill() { free(funs); KillCallerTree(rootcall); cyclewrite(0);} /*--------------------------------------- fun_name: author: date: purpose: in: out: return: history: -----------------------------------------*/ void wiretapopen(Caller *pstart) { Exeinfo *anewCall; if(pstart != NULL) { pstart->exeinfo.elapse = cycleread(); } } /*--------------------------------------- fun_name: wiretapcloseauthor: date: purpose: in: out: return: history: -----------------------------------------*/ void wiretapclose(Caller *pend) { if(pend != NULL) { pend->exeinfo.elapse = cycleread() - (pend->exeinfo.elapse); } } /*--------------------------------------- fun_name: buildfuntablefileauthor: liyidate: purpose: in: out: return: history: liyi 20090324 make here-----------------------------------------*/ void buildfuntablefile(char *fname, FILE *fhand){ char *pstr = NULL; char command[256]; char pinline[LEN_NAME+10]; char funline[LEN_PER_LINE]; char fnnline[LEN_PER_LINE]; char nm[LEN_NAME]; char ad[LEN_ADD_BEGIN]; FILE *phand = NULL; unsigned int id = 0; unsigned int add = 0; unsigned int off = 0; memset(command, 0x00, sizeof(char)*256); memset(pinline, 0x00, sizeof(char)*(LEN_NAME+10)); memset(funline, 0x00, sizeof(char)*LEN_PER_LINE); memset(fnnline, 0x00, sizeof(char)*LEN_PER_LINE); memset(nm, 0x00, sizeof(char)*LEN_NAME); memset(ad, 0x00, sizeof(char)*LEN_ADD_BEGIN); #if RELEASE sprintf(command, "%s %s %s", "../tool/mipsisa32-nm -n", fname, "| grep T"); #else sprintf(command, "%s %s %s", "~/ictoolchain/bin/mipsisa32-nm -n", fname, "| grep T"); #endif if((phand = popen(command, "r")) == NULL) { printf("error popen!"); exit(1); } /* find the main()*/ while(fgets(pinline, LEN_PER_LINE, phand)) { if(strstr(pinline,"main")) break; } /* process the pinline*/ pstr = pinline; do { /*ad*/ strncpy(ad, pstr, (strchr(pstr,0x20)-pstr)); add = (unsigned int)strtoul(ad, NULL, 16); /*nm*/ pstr += strlen(pinline) -1; *pstr = 0x00; for(;*pstr != 0x20; pstr--); strcpy(nm, pstr); nm[LEN_NAME-1] = 0; /*assemble*/ sprintf(funline, "%d%s 0x%x 0x%x", id, nm, add, 0); /*write into app_funtable.txt*/ if(id > 0) { off = add - off; /*off*/ pstr = strstr(fnnline, "0x0"); sprintf(pstr,"0x%x\n", off); fputs(fnnline, fhand); } strcpy(fnnline, funline); /*id*/ id ++; if((strstr(pinline,"exit")) || (strstr(pinline,"_start")) || (strstr(pinline,"zerobss")) || (strstr(pinline,"init")) || (strstr(pinline,"_exit")) || (strstr(pinline,"atexit")) || (strstr(pinline,"free")) ) break; /* clean all of buffer to prepare for next line*/ off = add; add = 0; memset(pinline, 0x00, sizeof(char)*(LEN_NAME+10)); memset(funline, 0x00, sizeof(char)*LEN_PER_LINE); memset(nm, 0x00, sizeof(char)*LEN_NAME); memset(ad, 0x00, sizeof(char)*LEN_ADD_BEGIN); pstr = pinline; }while(fgets(pinline, LEN_PER_LINE, phand)); pclose(phand);}/*--------------------------------------- fun_name: wiretapinit author: date: 20090311 purpose: init the wiretapper in: none out: none return: Okay or Do not history: 20090311 creat it by -----------------------------------------*/ Status wiretapinit(char *app) { char filename[LEN_NAME-14]; /*14 = strlen("_funtable.txt")*/ char cmd[LEN_NAME]; FILE * filehand = NULL; if(app == NULL) return (DONT); /* strcat app_funtable.txt*/ memset(filename, 0x00, (LEN_NAME-14)*sizeof(char)); memset(cmd, 0x00, LEN_NAME*sizeof(char)); sprintf(filename, "%s%s", app, "_funtable.txt"); sprintf(cmd, "rm -f %s", filename); system(cmd); filehand = fopen(filename, "wt"); buildfuntablefile(app, filehand); fclose(filehand); #if (!RELEASE) system("echo ____________________________________________________________________"); printf("i name entry offset\n\n"); sprintf(cmd, "cat %s", filename); system(cmd); system("echo ____________________________________________________________________"); #endif /*functions --> funs */ funssize = GetFunsCount(filename); funs = (Funtable *)malloc(funssize * sizeof(Funtable)); if(funs == NULL) return DONT; memset(funs, 0x00, funssize * sizeof(Funtable)); transmitfuntable(filename, funs); /* init the 0 level caller */ roottree.id = 0; roottree.depth = 0; /*exe info*/ memset(&roottree, 0x00, sizeof(Caller)); roottree.father = NULL; roottree.exeinfo.parentid = -1; roottree.exeinfo.elapse = cycle; roottree.exeinfo.abegin = searchaddress(0); roottree.exeinfo.aretur = searchaddress(0) + searchoffset(0) - 8; /* 20090104*/ calltree = rootcall; return (OKAY);} /*Inorder to get start anD end of function*/ /*--------------------------------------- fun_name: wiretapauthor: date: 2009-03-12purpose: in: out: return: history: 2009-03-12 0.0-----------------------------------------*/ void wiretap(Caller **hostcall, unsigned int lastia, unsigned int currentia) { Offtype offflag = WAIST; Caller *subcall = NULL; int idfun = 0; static unsigned int ncall = 0; /* modify on 0403 , it is important when there is only main() */ /* check a new caller or a return */ offflag = searchoff(currentia); #if APPLE printf(" %x ,%d \n", currentia, offflag); #endif if(offflag == HEADER) { if(ncall == 0) /* the main()*/ { #if(!RELEASE) printf("id deep dad start \n\n"); #endif subcall = *hostcall; subcall->exeinfo.aretur = lastia + 0x00000008; } if((*hostcall != NULL) && (ncall > 0)) { /* creat a caller */ subcall = creatcaller(currentia,lastia); if(subcall == NULL) return ; /* link the host */ subcall->father = (*hostcall); idfun = searchnearestid(lastia); if((*hostcall)->id == idfun) { subcall->exeinfo.parentid = (*hostcall)->id; /*Son Queue*/ if((*hostcall)->head != NULL) { /*Buddy Queue*/ (*hostcall)->rear->next = subcall; subcall->front = (*hostcall)->rear; (*hostcall)->rear = subcall; } else { (*hostcall)->head = subcall; (*hostcall)->rear = subcall; } /* update level */ subcall->depth = (*hostcall)->depth + 1; /* update the host ,move it to lower rank*/ *hostcall = subcall; } } /* open a wiretap for the caller */ wiretapopen(subcall); #if(!RELEASE) printf("%d - %d - %d - %ld \n", subcall->id, subcall->depth, subcall->exeinfo.parentid, subcall->exeinfo.elapse); #endif ncall ++; } else if(((*hostcall)->exeinfo.aretur) == currentia) { (*hostcall)->exeinfo.aleave = lastia; /* close a wiretap for the caller */ wiretapclose(*hostcall); #if(!RELEASE) //printf("%d eat %ld\n", (*hostcall)->id, (*hostcall)->exeinfo.elapse); #endif /* return to his parents ,move it to upper rank*/ if((*hostcall != &roottree)) /* 20090401 */ (*hostcall) = (*hostcall)->father; } else { /* Reserved */ } }
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -