📄 elfmodule.c
字号:
/******************************************************
Copyright(c) 版权所有,1998-2003微逻辑。保留所有权利。
******************************************************/
/*****************************************************
文件说明:dynlink loader模块
版本号:1.0.0
开发时期:2003-04-40
作者:ZB
修改记录:
1. 2003-08-26...ZB: 去处PAGE_NOCACHE标志,此标志降低了系统性能。
2. 2003-09-06...zb: 增加对加载的文件的判断:即如果文件有XIP属性,
而又不在\kingmos路径下,就不加载。
3. 2003-09-16...zb: 文件名比较不应用strstr, 应全匹配。
******************************************************/
#include <eframe.h>
#include <eprogram.h>
#include <efile.h>
#include <epalloc.h>
#include <epheap.h>
#include <edevice.h>
#include "diskio.h"
#include <eprocess.h>
#include <epcore.h>
#include <coresrv.h>
#include <elf.h>
#include <module.h>
#include "dlstruct.h"
typedef unsigned int (*LPSTART)();
#define MY_STATIC
typedef HANDLE HRSC;
MY_STATIC HANDLE ELF_CreateModule( LPCTSTR lpszFileName, HANDLE hProcess, UINT uiCreateFlag );
MY_STATIC BOOL ELF_FreeModule( HANDLE hModule );
MY_STATIC HANDLE ELF_GetModuleFileHandle( HANDLE hModule );
MY_STATIC LPVOID ELF_GetModuleProcAddress( HANDLE hModule, LPCSTR lpProcName );
MY_STATIC UINT ELF_LoadModule( HANDLE hModule, HANDLE hInst, LPCTSTR lpCmdLine, UINT uiLoadFlag );
MY_STATIC LPCTSTR ELF_GetModuleFileName( HANDLE hModule );
MY_STATIC DWORD ELF_GetModuleSectionOffset( HANDLE hModule, LPCTSTR lpcszSectionName );
//MY_STATIC HANDLE ELF_FindModuleRes(HANDLE hModule,LPCTSTR lpName, LPCTSTR lpType);
//MY_STATIC HANDLE ELF_LoadModuleRes(HANDLE hModule, HANDLE hResInfo);
MY_STATIC BOOL LoadModule(PMODULE_CLIENT pClient, UINT uLoadFlag, UINT *lpEntry);
//MY_STATIC BOOL GetModuleType(PMODULE_NODE pMod, UINT flag);
//MY_STATIC PMODULE_HANDLE GetNewModule(struct __dlmodule *__dl_module, HANDLE hProc, UINT flag);
MY_STATIC char *FormatModuleName(LPCTSTR lpszFileName);
PMODULE_NODE FindLoadedMod( LPCTSTR lpcszApName );
MY_STATIC BOOL SetModuleHandle(PMODULE_HANDLE lp, struct exe_module *pmod, struct __dlmodule *__dl_module, UINT flag );
//MY_STATIC BOOL GetDllSegInfo(HANDLE hFile, PMODULE_HANDLE lpHandle);
PMODULE_NODE FindOrCreateModule(LPCTSTR lpszFileName, UINT *uResult, UINT flag);
MY_STATIC PMODULE_CLIENT CreateModuleClient();
MY_STATIC PMODULE_HANDLE CreateModuleHandle(PMODULE_NODE pMod, UINT uMode, HANDLE hProcess);
MY_STATIC void InsertHandleList(PMODULE_CLIENT pmodule, PMODULE_HANDLE pModHandle);
MY_STATIC UINT CheckNewModule(struct __dlmodule *__dl_mod, PMODULE_CLIENT lp, UINT uLoadMode, struct __dlmodule *except_mod);
MY_STATIC void CleanLoadedDll();
MY_STATIC void InsertEmptyHandleList(PMODULE_CLIENT pmodule,PMODULE_HANDLE lpHandle);
PMODULE_HANDLE FindLoadedHandle(PMODULE_NODE pMod, UINT flag);
void ReleaseMapHandle(PMODULE_NODE pNode);
struct __dlmodule *LoadDllModule(PMODULE_CLIENT lp, struct exe_module *pmod, UINT uLoadMode, UINT *uReturn);
struct exe_module *LoadExeModule(PMODULE_CLIENT lp, UINT uLoadMode, UINT *uReturn);
void InsertClient(PMODULE_CLIENT pClient);
BOOL RemoveClient(PMODULE_CLIENT pClient);
UINT GetNewProcAddr(PMODULE_HANDLE pHandle, LPCSTR lpProcName);
BOOL ModuleInitFini(PMODULE_CLIENT lp, PMODULE_HANDLE ptemp, UINT flag );
//extern BOOL GetProcAddr(struct __dlmodule* module, PMODULE_HANDLE pHandle, LPCSTR lpProcName);
extern struct module_seg *GetSegInfo(HANDLE hFile);
extern struct __dlmodule* elf_load (PMODULE_HANDLE pHandle,const char * name, UINT flag);
extern struct __dlmodule *dldyn_start (void *args, char *AppName);
//note: 2003-09-04...zb
//extern unsigned int __dlclean_module (struct __dlmodule *module);
extern unsigned int __dlclean_module (struct __dlmodule *module, BOOL bNested);
//note: 2003-09-04...zb
extern struct exe_module * elf_exec (const char * name, PMODULE_HANDLE lpHandle, UINT flag);
extern unsigned int read_file (HANDLE hFile, char *buff, unsigned int size,
unsigned int offset);
extern unsigned int elf_find_binary(const char *name, char *lpszBin);
extern struct __dlmodule *__dl_loaded;
extern unsigned int __dl_nloaded;
//note: 2003-09-06...zb
BOOL IsLoadModule(LPCTSTR lpszFileName);
//note: 2003-09-06...zb
const MODULE_DRV ElfModule =
{
ELF_CreateModule,
ELF_FreeModule,
ELF_GetModuleFileHandle,
ELF_GetModuleFileName,
ELF_GetModuleProcAddress,
// ELF_FindModuleRes,
// ELF_LoadModuleRes,
ELF_GetModuleSectionOffset,
ELF_LoadModule
};
const char SECT_NAME_RES[] = ".res";
const char KING_PATH[] = "kingmos";
const char KINGMOS_PATH[] = "\\kingmos\\";
const char WORK_PATH[] = "\\system\\";
//2004-10-20, remove by lilin
//UINT bInitModule = 0;
//
MY_STATIC PMODULE_NODE lpElfModList = NULL;
MY_STATIC PMODULE_CLIENT lpClientList = NULL;
//CRITICAL_SECTION csModuleList; //临界段
//CRITICAL_SECTION csModuleLoad; //临界段
CRITICAL_SECTION csModuleList; //module list 临界段
CRITICAL_SECTION csClientList; //module list 临界段
//CRITICAL_SECTION csHandleList; //module handle 临界段
//CRITICAL_SECTION csLoadExe; //load exe 临界段
//CRITICAL_SECTION csLoadDll; //load dll 临界段
CRITICAL_SECTION csLoadModule; //load dll 临界段
//#undef __inline
//#define __inline
BOOL InitElfModuleMgr( void )
{
KL_InitializeCriticalSection( &csModuleList );
KL_InitializeCriticalSection( &csClientList );
// KL_InitializeCriticalSection( &csHandleList );
// KL_InitializeCriticalSection( &csLoadExe );
// KL_InitializeCriticalSection( &csLoadDll );
KL_InitializeCriticalSection( &csLoadModule );
//csDeviceObjList.lpcsName = "CS-DEV";
return TRUE;
}
//KL_EnterCriticalSection( &csLoadExe );
//KL_LeaveCriticalSection( &csModuleList );
//EXE file: MODULE_LOAD --> don't load code and data segment to memory, only save the info of module.
// MODULE_EXEC --> load code and date segment to memory, and save info.
//DLL file: MODULE_LOAD --> load code and date segment to memory, and save info.
// MODULE_EXEC --> not suport.
//
/*#define CREATE_EXE 0
#define CREATE_LIBRARY 1
#define LF_EXEC 0x0000001 // run .exe file or LoadLibrary with .dll
#define LF_LOAD_TO_MEM 0x0000002 // LoadLibrary with .exe file only
#define LF_DEFLOAD (LF_EXEC|LF_LOAD_TO_MEM)
#define LF_NOT_INIT_DLL 0x0000004 // LoadLibrary with .dll file but not call Dll_Init
*/
MY_STATIC void ReleaseModuleHandle(PMODULE_HANDLE lp)
{
PFUNCTION_SYM lpProcTmp;
if(lp->info){
//free(lp->info);
//if(lp->info->phdr)
// KHeap_Free(lp->info->phdr, sizeof( Elf32_Phdr) * lp->info->nphdr);
//2004-10-20
KHeap_Free( lp->info, sizeof( LOAD_MODULE ) );
//_kfree( lp->info );
//
}
while(lp->lpProc){
lpProcTmp = lp->lpProc;
lp->lpProc = lp->lpProc->lpNext;
{
UINT len = strlen( lpProcTmp->lpFuncName ) + 1;
//free(lpProcTmp);
//_kfree(lpProcTmp);
KHeap_Free((LPVOID)lpProcTmp->lpFuncName , len * sizeof( TCHAR ));
KHeap_Free(lpProcTmp, sizeof(FUNCTION_SYM));
}
}
//free(lp);
KHeap_Free( lp, sizeof( MODULE_HANDLE ) );
lp = NULL;
return ;
}
void ReleaseSegInfo(struct module_seg *seg)
{
struct module_seg *ptemp;
while(seg){
ptemp = seg;
seg = seg->lpNext;
if(ptemp->sh_name){
RETAILMSG(TONE_DEBUG, ("SEG4\r\n"));
_kfree(ptemp->sh_name);
}
RETAILMSG(TONE_DEBUG, ("SEG5\r\n"));
//2004-10-21
//_kfree(ptemp);
KHeap_Free( ptemp, sizeof(struct module_seg) );
//
}
return;
}
#define DEBUG_ReleaseModule 0
MY_STATIC void ReleaseModule(PMODULE_NODE lpMod)
{
BOOL find = FALSE;
// PMODULE_HANDLE lpHanlde;
PMODULE_NODE lpTmp;
// PMODULE_NODE lpMod;
// PFUNCTION_SYM lpProcTmp;
// BOOL bRefModule = FALSE;
RETAILMSG(TONE_MOD|DEBUG_ReleaseModule,("ReleaseModule: release module for %s\n", lpMod->lpszApName));
lpTmp = lpElfModList;
if(lpElfModList == lpMod){
lpElfModList = lpElfModList->lpNext;
find = TRUE;
}else{
while( lpTmp->lpNext )
{
if( lpTmp->lpNext == lpMod )
{
lpTmp->lpNext = lpMod->lpNext;
find = TRUE;
break;
}
lpTmp = lpTmp->lpNext;
}
}
if(find){
RETAILMSG(TONE_MOD|DEBUG_ReleaseModule, ( "ReleaseModule: find it, release module,lpMod->lpszApName=%s!.\r\n", lpMod->lpszApName) );
//RETAILMSG(TONE_TEST, ( "F3:%s\r\n", lpMod->lpszApName));
//2004-10-20
//KHeap_Free( lpMod->lpszApName, sizeof((strlen(lpMod->lpszApName) + 1) * sizeof(TCHAR)));
KHeap_FreeString( lpMod->lpszApName );//
//_kfree( lpMod->lpszApName );
//
RETAILMSG(TONE_MOD, ( "ReleaseModule1: release module!\r\n") );
ReleaseSegInfo(lpMod->seg_info);
RETAILMSG(TONE_MOD, ( "ReleaseModule2: release module!\r\n") );
//2004-10-20
KHeap_Free( lpMod, sizeof( MODULE_NODE ) );
//_kfree( lpMod );
//
//KL_LeaveCriticalSection( &csModuleList );
RETAILMSG(TONE_MOD|DEBUG_ReleaseModule, ( "ReleaseModule: leave: >\r\n") );
return;
}else{
//KL_LeaveCriticalSection( &csModuleList );
WARNMSG(TONE_MOD,( "ReleaseModule: leave: > don't find the module!\r\n" ));
return ;
}
}
#define DEBUG_ReleaseRef 0
MY_STATIC void ReleaseRef(PMODULE_CLIENT lpClient, PMODULE_HANDLE lp)
{
// PMODULE_HANDLE pHandle;
BOOL find = FALSE;
PMODULE_HANDLE lpHanlde;
PMODULE_HANDLE lpRefHandle;
PMODULE_NODE lpTmp;
PMODULE_NODE lpMod;
PFUNCTION_SYM lpProcTmp;
BOOL bRefModule = FALSE;
BOOL bEnter = FALSE;
RETAILMSG(TONE_MOD|DEBUG_ReleaseRef, ( "ReleaseRef: lp->uRef=%d entry.\r\n",lp->uRef) );
ASSERT(lp);
KL_EnterCriticalSection( &csModuleList );
//if(lp->uRef --){
if(-- lp->uRef ){
bEnter = TRUE;
KL_LeaveCriticalSection( &csModuleList );
RETAILMSG(TONE_CS, ( "1(-\n"));
RETAILMSG(TONE_CS, ( "===>1:%x\n", lp->uRef));
KL_EnterCriticalSection( &csLoadModule );
RETAILMSG(TONE_CS, ( "-)2\n"));
KL_EnterCriticalSection( &csModuleList );
ASSERT(lp->uRef == 0);
}
lpMod = lp->lpModule;
//RETAILMSG(TONE_TEST,("ReleaseRef: release handle for %s\n", lpMod->lpszApName));
RETAILMSG(TONE_TEST, ( "<=>%s\r\n", lpMod->lpszApName) );
lpHanlde = lpMod->lpHandle;
if(lp == lpMod->lpHandle){
RETAILMSG(TONE_MOD,("ReleaseRef: => 11\n"));
lpMod->lpHandle = lp->lpNext;
find = TRUE;
}else{
RETAILMSG(TONE_MOD,("ReleaseRef: => 12\n"));
while( lpHanlde->lpNext )
{
RETAILMSG(TONE_MOD,("ReleaseRef: => 13\n"));
if( lpHanlde->lpNext == lp )
{
RETAILMSG(TONE_MOD,("ReleaseRef: => 14\n"));
lpHanlde->lpNext = lp->lpNext;
find = TRUE;
break;
}
lpHanlde = lpHanlde->lpNext;
}
}
if(find){
ASSERT(lp->lpModule == lpMod);
RETAILMSG(TONE_MOD, ( "ELF_FreeModule: fini module \r\n") );
//ASSERT(ModuleInitFini(lpClient, lp, MODULE_FINI));
ModuleInitFini(lpClient, lp, MODULE_FINI);
RETAILMSG(TONE_MOD, ( "ELF_FreeModule: release module handle\r\n") );
//lpMod->uRef--;
ReleaseModuleHandle(lp);
}
else
{
WARNMSG(TONE_MOD, ( "ELF_FreeModule: find NO module handle\r\n") );
}
/* if(lpMod->lpHandle == NULL){ //The module has no handle...
RETAILMSG(TONE_MOD, ("Exec_module: ->20\r\n"));
ReleaseModule(lpMod);
}
*/
RETAILMSG(TONE_TEST|DEBUG_ReleaseRef, ("ReleaseRef:lpMod->uRef=%x.\r\n", lpMod->uRef));
lpMod->uRef --;
if(lpMod->uRef == 0){
RETAILMSG(TONE_MOD, ("Exec_module: ->20\r\n"));
ASSERT(lpMod->lpHandle == NULL);
ReleaseModule(lpMod);
}
KL_LeaveCriticalSection( &csModuleList );
RETAILMSG(TONE_CS, ( "2(-\n"));
if(bEnter){
KL_LeaveCriticalSection( &csLoadModule );
RETAILMSG(TONE_CS, ( "1<===\n"));
}
return ;
}
MY_STATIC HANDLE ELF_CreateModule( LPCTSTR lpszFileName, HANDLE hProcess, UINT uiCreateFlag )
{
PMODULE_NODE pMod ;
PMODULE_CLIENT pmodule;
UINT len;
// PMODULE_NODE ploadmod;
// char *modulename;
MODULE_HANDLE *pModHandle;
BOOL bIsLoaded = FALSE;
RETAILMSG(TONE_MOD, ( "ELF_CreateModule:< %s, %x\r\n", lpszFileName, uiCreateFlag) );
RETAILMSG(TONE_TEST, ( "->>2\r\n"));
//2004-10-20, remove by lilin
//if(bInitModule == 0){
// bInitModule = 1;
// InitModuleMgr();
//}
//
//note: 2003-09-06...zb
if(!IsLoadModule(lpszFileName)){
RETAILMSG(TONE_ERROR, ( "ELF_CreateModule: > can't load the module!\r\n") );
return NULL;
}
//note: 2003-09-06...zb
pmodule = CreateModuleClient(lpszFileName,hProcess, uiCreateFlag);
if(pmodule == NULL){
RETAILMSG(TONE_ERROR, ( "ELF_CreateModule: > create module client fail!\r\n") );
RETAILMSG(TONE_TEST, ( "->>6\r\n"));
return NULL;
}
RETAILMSG(TONE_MOD,( "create Success!\r\n" ));
RETAILMSG(TONE_MOD, ( "ELF_CreateModule:>\r\n") );
return (HANDLE)pmodule;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -