vxworks_ddll_drv.c
来自「OTP是开放电信平台的简称」· C语言 代码 · 共 189 行
C
189 行
/* ``The contents of this file are subject to the Erlang Public License, * Version 1.1, (the "License"); you may not use this file except in * compliance with the License. You should have received a copy of the * Erlang Public License along with this software. If not, it can be * retrieved via the world wide web at http://www.erlang.org/. * * Software distributed under the License is distributed on an "AS IS" * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See * the License for the specific language governing rights and limitations * under the License. * * The Initial Developer of the Original Code is Ericsson Utvecklings AB. * Portions created by Ericsson are Copyright 1999, Ericsson Utvecklings * AB. All Rights Reserved.'' * * $Id$ *//* Purpose: Low level driver for dynamic driver loader/unloader and * linker for VxWorks. */#ifdef HAVE_CONFIG_H# include "config.h"#endif#include <vxWorks.h>#include <stdio.h>#include <string.h>#include <stdarg.h>#include <a_out.h>#include <symLib.h>#include <loadLib.h>#include <unldLib.h>#include <moduleLib.h>#include <sysSymTbl.h>#include "sys.h"#include "erl_vm.h"#include "erl_ddll.h"static char thismodname[] = "vxworks_ddll_drv";static char *curr_error = "No error";static MODULE_ID get_mid(char *);static FUNCPTR lookup(char *);static void drv_error(char*, ...);/* * ddll_open(full_name) * * full_name is the path to the file containing the driver. * The basename of full_name is the driver name. * * Returns the MODULE_ID of the module containing the driver. * */void *ddll_open(char *full_name){ char *path; char *drvname; char *cp; MODULE_ID mid; int len; if ((mid = get_mid(full_name)) == NULL) { if((path = malloc(strlen(full_name)+5)) == NULL) { curr_error = "ddll_open: Cannot malloc"; return NULL; } strcpy(path, full_name); len = strlen(path); strcpy(path + len, ".eld"); if(((mid = get_mid(path)) == NULL) && strcpy(path + len, ".o") && ((mid = get_mid(path)) == NULL)) { curr_error = "ddll_open: Module not found"; } free(path); } return (void *) mid;}static MODULE_IDget_mid(char* name) { int fd; MODULE_ID mid = NULL; if((fd = open(name, O_RDONLY, 0664)) >= 0) { mid = loadModule(fd, GLOBAL_SYMBOLS); close(fd); } return mid;}/* * Return pointer to function MODULENAME_init. * * n.b. func_name is ignored. * * The convention is that the module name of the driver is .eld (e.g. echo_drv.eld). * But if it has .o as suffix or no suffix it is also ok (e.g. echo_drv.o and echo_drv) * */void *ddll_sym(void *handle, char *func_name){ MODULE_ID mid = (MODULE_ID) handle; char *modname; char *cp; char *fname; char *suffix = "_init"; int len; FUNCPTR func; if((modname = moduleNameGet(mid)) == NULL) { curr_error = "ddll_sym: Module not found"; return 0; } if((cp = strrchr(modname, '.')) == NULL) { len = strlen(modname); } else { len = cp - modname; } if((fname = malloc(len + strlen(suffix) + 1)) == NULL) { curr_error = "ddll_sym: cannot malloc"; return 0; } strncpy(fname, modname, len); fname[len] = '\0'; strcat(fname, suffix); if((func = lookup(fname)) == NULL) curr_error = "ddll_sym: function NAME_init not found"; free(fname); return func;}int ddll_close(void *handle){ MODULE_ID mid = (MODULE_ID) handle; int ret; if((ret = unld(mid, 0)) < 0) curr_error = "ddll_close: Module not found"; return ret;}char *ddll_error(void){ return curr_error;}/* * Lookup and return global text symbol or NULL on failure * * ddll_drv.c looks for sym with and without a leading '_'. * (this is needed since gcc for PPC doesn't include the * leading '_' while gcc for e.g. 68k does so) */static FUNCPTR lookup(char *sym){ FUNCPTR entry; SYM_TYPE type; char buf[256]; char *u_score_sym = buf; int len; if (symFindByNameAndType(sysSymTbl, sym, (char **)&entry, &type, N_EXT | N_TEXT, N_EXT | N_TEXT) != OK) { len = strlen(sym); if (len > 254 && (u_score_sym = malloc(len+2)) == NULL) return(NULL); sprintf(u_score_sym, "_%s", sym); if (symFindByNameAndType(sysSymTbl, u_score_sym, (char **)&entry, &type, N_EXT | N_TEXT, N_EXT | N_TEXT) != OK) entry = NULL; if (u_score_sym != buf) free(u_score_sym); } return(entry);}static void drv_error(char* format, ...){ va_list va; fprintf(stdout, "%s: ", thismodname); va_start(va, format); vfprintf(stdout, format, va); va_end(va);}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?