⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 loadpecofflib.c

📁 vxworks源码源码解读是学习vxworks的最佳途径
💻 C
📖 第 1 页 / 共 4 页
字号:
/* loadPecoffLib.c - pecoff object module loader *//* Copyright 1984-1998 Wind River Systems, Inc. */#include "copyright_wrs.h"/*modification history--------------------01g,30nov98,dbt  no longer clear seg.flags<xxx> after loadSegmentAllocate()                 call. (SPR #23553).01f,05oct98,pcn  Initialize all the fields in the SEG_INFO structure.01e,23sep98,cym  adding check for STYP_INFO,NO_LOAD,REG,PAD before relocating.01d,18sep98,pcn  Set to _ALLOC_ALIGN_SIZE the flags field in seg structure                 (SPR #21836).01c,15sep98,cym  ignoring s_vaddr for relocatable objects until ldsimpc -r		 is fixed to sych it correctly.01b,17jul98,pcn  Fixed SPR #21836: alignment mismatch between sections and                 target.01a,19mar98,cym  created from on loadCoffLib.c*//*DESCRIPTIONThis library provides an object module loading facility for loadingPECOFF format object files.  The object files are loaded into memory, relocated properly, their external references resolved, and their external definitions added to the system symbol table for use by other modules and from the shell.  Modules may be loaded from any I/O stream.EXAMPLE.CS    fdX = open ("/devX/objFile", READ);    loadModule (fdX, ALL_SYMBOLS);    close (fdX);.CEThis code fragment would load the PECOFF file "objFile" located ondevice "/devX/" into memory which would be allocated from the systemmemory pool.  All external and static definitions from the file would beadded to the system symbol table.This could also have been accomplished from the shell, by typing:.CS    -> ld (1) </devX/objFile.CEINCLUDE FILE: loadLib.hSEE ALSO: usrLib, symLib, memLib,.pG "Basic OS"*//* LINTLIBRARY */#include "vxWorks.h"#include "bootLoadLib.h"#include "cacheLib.h"#include "errnoLib.h"#include "fioLib.h"#include "ioLib.h"#include "loadLib.h"#include "memLib.h"#include "pathLib.h"#include "stdio.h"#include "stdlib.h"#include "string.h"#include "symLib.h"#include "symbol.h"	/* for SYM_TYPE typedef */#include "sysSymTbl.h"#include "private/vmLibP.h"#if CPU==SIMNT#include "loadPecoffLib.h"/*  VxWorks Symbol Type definitions. * *  These are the symbol types for symbols stored in the vxWorks symbol table. *  These are currently defined in b_out.h as N_xxx (e.g. N_ABS). *  They are defined with new macro names so that they are *       independent of the object format. *  It would probably be better to define these in symLib.h. */#define VX_ABS	2	/* Absolute symbol	*/#define VX_TEXT	4	/* Text symbol		*/#define VX_DATA	6	/* Data symbol		*/#define VX_BSS	8	/* BSS symbol		*/#define VX_EXT	1	/* External symbol (OR'd in with one of above)	*/#define IMAGE_NT_SIGNATURE	0x00004550#define IMAGE_DOS_SIGNATURE	0x5A4D#define IMAGE_FILE_MACHINE_I386	0x14c/* fast download */#define BAL_LOAD 0x80	/* flag indicating download with branch-and-link			   optimization - results in slower download */LOCAL int fast_load = TRUE;/* *  Abridged edition of a object file symbol entry SYMENT * *  This is used to minimize the amount of malloc'd memory. *  The abridged edition contains all elements of SYMENT required *  to perform relocation. */#ifdef __GNUC__#pragma align 1			/* tell gcc960 to not pad structures */#endifstruct symentAbridged {	long		n_value;	/* value of symbol		*/	short		n_scnum;	/* section number		*/	char		n_sclass;	/* storage class		*/	char		n_numaux;       /* number of auxiliary entries  */};#define	SYMENT_A struct symentAbridged#define	SYMESZ_A sizeof(SYMENT_A)	#ifdef __GNUC__#pragma align 0			/* turn off alignment requirement */#endif/*  *  PECOFF symbol types and classes as macros * *   'sym' in the macro defintion must be defined as:   SYMENT *sym; */#define U_SYM_VALUE    n_value#define PECOFF_EXT(sym) \    ((sym)->n_sclass == C_EXT)/*  PECOFF Undefined External Symbol */#define PECOFF_UNDF(sym) \    (((sym)->n_sclass == C_EXT) && ((sym)->n_scnum == N_UNDEF))/*  PECOFF Common Symbol *    A common symbol type is denoted by undefined external *    with its value set to non-zero. */#define PECOFF_COMM(sym) ((PECOFF_UNDF(sym)) && ((sym)->n_value != 0))/* PECOFF Unassigned type *    An unassigned type symbol of class C_STAT generated by *    some assemblers */#define PECOFF_UNASSIGNED(sym) (((sym)->n_sclass == C_STAT) && ((sym)->n_type == T_NULL))/* misc defines */#define INSERT_HWORD(WORD,HWORD)        \    (((WORD) & 0xff00ff00) | (((HWORD) & 0xff00) << 8) | ((HWORD)& 0xff))#define EXTRACT_HWORD(WORD) \    (((WORD) & 0x00ff0000) >> 8) | ((WORD)& 0xff)#define SIGN_EXTEND_HWORD(HWORD) \    ((HWORD) & 0x8000 ? (HWORD)|0xffff0000 : (HWORD))#define SWAB_SHORT(s) \  ((((unsigned short) s & 0x00ff) << 8) | (((unsigned short) s & 0xff00) >> 8))#define MAX_SCNS        11              /* max sections supported */#define NO_SCNS         0#define MAX_ALIGNMENT	4		/* max boundary for architecture */char *addrScn[MAX_SCNS];                /* where each section is located */LOCAL int  max_scns = MAX_SCNS;		/* load with MAX */LOCAL char stringMemErrMsg [] =    "loadLib error: insufficient memory for strings table (need %d bytes).\n";LOCAL char extMemErrMsg [] =    "loadLib error: insufficient memory for externals table (need %d bytes).\n";LOCAL char cantConvSymbolType [] =    "loadLib error: can't convert '%s' symbol type - error = %#x.\n";LOCAL char cantAddSymErrMsg [] =    "loadLib error: can't add '%s' to system symbol table - error = %#x.\n";#ifndef MULTIPLE_LOADERSLOCAL char fileTypeUnsupported [] =    "loadLib error: File type with magic number %#x is not supported.\n";#endif/* forward declarations */LOCAL void pecoffFree ();LOCAL void pecoffSegSizes ();LOCAL STATUS pecoffReadSym ();LOCAL STATUS softSeek ();LOCAL STATUS fileRead ();LOCAL STATUS swabData ();LOCAL void swabLong ();LOCAL ULONG pecoffTotalCommons ();LOCAL ULONG dataAlign ();LOCAL STATUS pecoffHdrRead ();LOCAL STATUS pecoffOpthdrRead ();LOCAL STATUS pecoffSecHdrRead ();LOCAL STATUS pecoffLoadSections ();LOCAL STATUS pecoffReadRelocInfo ();LOCAL STATUS pecoffReadExtSyms ();LOCAL STATUS pecoffReadExtStrings ();LOCAL STATUS pecoffRelSegmentI386 ();LOCAL STATUS pecoffSymTab (int fd, struct filehdr *pHdr, SYMENT *pSymbols, 			 char ** *externals,                         int symFlag, SEG_INFO *pSeg, char *symStrings,                         SYMTAB_ID symTbl, char *pNextCommon,                         struct scnhdr *pScnHdrArray, char **pScnAddr,			 BOOL symsAbsolute, BOOL swapTables, UINT16 group,                         int imageBase);/******************************************************************************** ldPecoffModAtSym - load object module into memory with specified symbol table** This routine is the underlying routine to loadModuleAtSum().  This interface* allows specification of the the symbol table used to resolve undefined* external references and to which to add new symbols.** RETURNS:* MODULE_ID, or* NULL if can't read file or not enough memory or illegal file format** NOMANUAL*/MODULE_ID ldPecoffModAtSym    (    FAST int fd,	/* fd from which to read module */    int symFlag,	/* symbols to be added to table 			 *   ([NO | GLOBAL | ALL]_SYMBOLS) */    char **ppText,	/* load text segment at address pointed to by this			 * pointer, return load address via this pointer */    char **ppData,	/* load data segment at address pointed to by this			 * pointer, return load address via this pointer */    char **ppBss,	/* load bss segment at address pointed to by this			 * pointer, return load address via this pointer */    SYMTAB_ID symTbl	/* symbol table to use */    )    {    char *pText = (ppText == NULL) ? LD_NO_ADDRESS : *ppText;    char *pData = (ppData == NULL) ? LD_NO_ADDRESS : *ppData;    char *pBss  = (ppBss  == NULL) ? LD_NO_ADDRESS : *ppBss;    char **externalsBuf = NULL;         /* array of symbol absolute values */    char *externalSyms = NULL;          /* buffer for object file symbols */    char *stringsBuf = NULL;		/* string table pointer */    FILHDR hdr;				/* module's PECOFF header */    PEOPTION optHdr;             	/* module's PECOFF optional header */    SCNHDR scnHdr[MAX_SCNS];		/* module's PECOFF section headers */    char *scnAddr[MAX_SCNS];            /* array of section loaded address */    RELOC  *relsPtr[MAX_SCNS]; 		/* section relocation */    SEG_INFO seg;			/* file segment info */    BOOL tablesAreLE;			/* boolean for table sex */    BOOL symsAbsolute = FALSE;          /* TRUE if already absolutely located*/    int status;				/* return value */    int ix;				/* temp counter */    int nbytes;				/* temp counter */    char *pCommons;                     /* start of common symbols in bss */    char *addrBss;    char        fileName[255];    UINT16      group;    MODULE_ID   moduleId;    int hdrEnd;    /* initialization */    memset ((void *)&seg, 0, sizeof (seg));    /* Set up the module */    ioctl (fd, FIOGETNAME, (int) fileName);    moduleId = loadModuleGet (fileName, MODULE_ECOFF, &symFlag);    if (moduleId == NULL)        return (NULL);    group = moduleId->group;    /* init section pointers to NULL */    for (ix = 0; ix < MAX_SCNS; ix++)	{	scnAddr[ix] = NULL;	relsPtr[ix] = NULL;	bzero((char *) &scnHdr[ix], (int) sizeof(SCNHDR));	}    /* read object module header */    if (pecoffHdrRead (fd, &hdr, &tablesAreLE) != OK)	{	/*  Preserve errno value from subroutine. */winOut("Header Fail\n");	goto error;	}    hdrEnd = lseek(fd,0,SEEK_CUR);    /* read in optional header */    if (hdr.f_opthdr)                   /* if there is an optional header */        {        if (pecoffOpthdrRead (fd, &optHdr, tablesAreLE) != OK)            {/*            errnoSet(S_loadLib_OPTHDR_READ); */winOut("Opt Header Fail\n");            goto error;            }        }    lseek(fd,hdrEnd + hdr.f_opthdr,SEEK_SET);    /* read in section headers */    if (pecoffSecHdrRead (fd, &scnHdr[0], &hdr, tablesAreLE) != OK)	{/*	errnoSet(S_loadLib_SCNHDR_READ);  */winOut("Sec Header Fail\n");	goto error;	}    /* Determine segment sizes */    /*      * XXX seg.flagsXxx mustn't be used between coffSegSizes() and      * loadSegmentsAllocate().     */    pecoffSegSizes(&hdr, scnHdr, &seg);    /*  If object file is already absolutely located (by linker on host),     *  then override parameters pText, pData and pBss.     *//* XXX cym this should be && */    if (   (hdr.f_flags & F_EXEC)        || (hdr.f_flags & F_RELFLG))        {        if (hdr.f_opthdr)               /* if there is an optional header */            {            symsAbsolute = TRUE;            pText = (INT8 *)(optHdr.text_start + optHdr.image_base);            pData = (INT8 *)(optHdr.data_start + optHdr.image_base);            /* bss follows data segment */            pBss = (INT8 *) pData + optHdr.dsize;            pBss += dataAlign(MAX_ALIGNMENT, pBss);	    }	}    seg.addrText = pText;    seg.addrData = pData;    /*     * If pBss is set to LD_NO_ADDRESS, change it to something else.     * The pecoff loader allocates one large BSS segment later on, and     * loadSegmentsAllocate doesn't work correctly for it.     */    seg.addrBss = (pBss == LD_NO_ADDRESS ? LD_NO_ADDRESS + 1 : pBss);    /*      * SPR #21836: loadSegmentsAllocate() allocate memory aligned on      * the max value of sections alignement saved in seg.flagsText,     * seg.flagsData, seg.flagsBss.     */    if (loadSegmentsAllocate (&seg) != OK)        {        printErr ("Could not allocate segments\n");        goto error;        }    else        {        pText = seg.addrText;        pData = seg.addrData;        pBss = LD_NO_ADDRESS;        }    /*  Ensure that section starts on the appropriate alignment.     */    pText += dataAlign(MAX_ALIGNMENT, pText);    if (pData == LD_NO_ADDRESS)        {	pData = pText + seg.sizeText;        }    /*  Ensure that section starts on the appropriate alignment.     */    pData += dataAlign(MAX_ALIGNMENT, pData);    seg.addrText = pText;    seg.addrData = pData;    /* load text and data sections */    if(!symsAbsolute)        {    if (pecoffLoadSections (fd, &scnHdr[0], &scnAddr[0], pText, pData) != OK)	{/*	errnoSet (S_loadLib_LOAD_SECTIONS); */winOut("Load Section Fail\n");	goto error;	}    /* get section relocation info */        if (pecoffReadRelocInfo (fd, &scnHdr[0], &relsPtr[0], tablesAreLE)                 != OK)   	    {/*	    errnoSet (S_loadLib_RELOC_READ); */winOut("Read Reloc Fail\n");	    goto error;	    }        }    /* read symbols */    if (pecoffReadExtSyms (fd, &externalSyms, &externalsBuf, &hdr, tablesAreLE)        != OK)	{/*	errnoSet (S_loadLib_EXTSYM_READ); */winOut("Ext Syms Fail\n");	goto error;	}    /* read string table */    if (pecoffReadExtStrings (fd, &stringsBuf, tablesAreLE) != OK)	{/*	errnoSet (S_loadLib_EXTSTR_READ); */winOut("Ext String Fail\n");	goto error;	}    /*  Determine additional amount of memory required to append     *  common symbols on to the end of the BSS section.     */    nbytes = pecoffTotalCommons(externalSyms, hdr.f_nsyms, seg.sizeBss);    /* set up for bss */    seg.sizeBss += nbytes;    if (pBss == LD_NO_ADDRESS)        {        if (seg.sizeBss != 0)            {            if ((pBss = malloc (seg.sizeBss)) == NULL)                 goto error;            else                                 		seg.flagsBss |= SEG_FREE_MEMORY;              }        else            {            pBss = (char *) ((long) pData + (long) seg.sizeData);            }        }    pBss += dataAlign(MAX_ALIGNMENT, pBss);    seg.addrBss = pBss;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -