[Fault-injection-developer] [RFC] [PATCH] general symbol replacement
Status: Alpha
Brought to you by:
rustyl
From: Louis Z. <lou...@li...> - 2003-03-04 01:13:38
|
Dear all, Following is a tiny tool used to change a symbol name in your module. So you can replace, for example, 'kmalloc' with 'fmalloc'. And then you can write fmalloc implementation yourself in a module. In this way, you can intercept any software API in kernel only if it is not a macro. Any comments? -- Yours truly, Louis Zhuang --------------- Fault Injection Test Harness Project BK tree: http://fault-injection.bkbits.net/linux-2.5 Home Page: http://sf.net/projects/fault-injection # This is a BitKeeper generated patch for the following project: # Project Name: Fault Injection Test Harness tools # This patch format is intended for GNU patch command version 2.5 or higher. # This patch includes the following deltas: # ChangeSet 1.22 -> 1.25 # fith_utility/Makefile.am 1.1 -> 1.2 # fith_utility/configure.in 1.1 -> 1.2 # (new) -> 1.2 fith_utility/replacesym/replacesym.c # (new) -> 1.1 fith_utility/replacesym/Makefile.am # # The following is the BitKeeper ChangeSet Log # -------------------------------------------- # 03/02/27 lo...@ha... 1.23 # Add replace symbol mechanism # -------------------------------------------- # 03/02/27 lo...@ha... 1.24 # add replacesym # -------------------------------------------- # 03/02/27 lo...@ha... 1.25 # Fix a bug -- Should seek in .strtab instead of .shstrtab # -------------------------------------------- # diff -Nru a/fith_utility/Makefile.am b/fith_utility/Makefile.am --- a/fith_utility/Makefile.am Tue Mar 4 09:06:35 2003 +++ b/fith_utility/Makefile.am Tue Mar 4 09:06:35 2003 @@ -1,4 +1,4 @@ AUTOMAKE_OPTIONS = foreign EXTRA_DIST = ./* -SUBDIRS = ficl +SUBDIRS = ficl replacesym diff -Nru a/fith_utility/configure.in b/fith_utility/configure.in --- a/fith_utility/configure.in Tue Mar 4 09:06:35 2003 +++ b/fith_utility/configure.in Tue Mar 4 09:06:35 2003 @@ -36,4 +36,5 @@ AC_OUTPUT([ Makefile - ficl/Makefile]) + ficl/Makefile + replacesym/Makefile]) diff -Nru a/fith_utility/replacesym/Makefile.am b/fith_utility/replacesym/Makefile.am --- /dev/null Wed Dec 31 16:00:00 1969 +++ b/fith_utility/replacesym/Makefile.am Tue Mar 4 09:06:35 2003 @@ -0,0 +1,8 @@ +AUTOMAKE_OPTIONS = foreign +sbin_PROGRAMS = replacesym + +include $(top_srcdir)/rules.mk + +replacesym_SOURCES = replacesym.c + + diff -Nru a/fith_utility/replacesym/replacesym.c b/fith_utility/replacesym/replacesym.c --- /dev/null Wed Dec 31 16:00:00 1969 +++ b/fith_utility/replacesym/replacesym.c Tue Mar 4 09:06:35 2003 @@ -0,0 +1,98 @@ +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <fcntl.h> +#include <sys/mman.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <unistd.h> +#include <errno.h> +#include <asm/unistd.h> + +#include <elf.h> + +typedef Elf32_Ehdr Elf_Ehdr; +typedef Elf32_Shdr Elf_Shdr; + +static int replace_symbol(void *map, int len, const char *old, const char *new) +{ + Elf_Ehdr *hdr; + Elf_Shdr *sechdrs; + char *strtab; + char *s; + int n; + + hdr = map; + if (len < sizeof(*hdr)) { + fprintf(stderr, "File is too short\n"); + return -1; + } + + /* Sanity checks against insmoding binaries or wrong arch, + * weird elf version */ + if (memcmp(hdr->e_ident, ELFMAG, 4) != 0 + || hdr->e_type != ET_REL + || hdr->e_shentsize != sizeof(*sechdrs)) { + fprintf(stderr, "File is weird\n"); + return -1; + } + + sechdrs = map + hdr->e_shoff; + strtab = map + sechdrs[hdr->e_shnum-1].sh_offset; + + n = sechdrs[hdr->e_shnum-1].sh_size; + s = strtab; + while (n) { + int len; + + len = strnlen(s, n); + if (len >= n) { + fprintf(stderr, "Bad string table\n"); + break; + } + printf("Symbol name:'%s'\n", s); + + if (!strcmp(s, old)) { + if (strlen(new) <= len) { + strncpy(s, new, len); + } else { + fprintf(stderr, + "New symbol name is too long\n"); + } + } + + s += len+1; + n -= len+1; + } + + return 0; +} + +int main(int argc, char *argv[]) +{ + int fd; + struct stat st; + void *map; + + if (argc != 4) { + printf("Usage: %s <module_file> <old_sym> <new_sym>\n", argv[0]); + exit(1); + } + + fd = open(argv[1], O_RDWR, 0); + if (fd < 0) { + perror("Unable to open file"); + exit(1); + } + + fstat(fd, &st); + map = mmap(NULL, st.st_size, PROT_WRITE|PROT_READ, MAP_SHARED, fd, 0); + if (MAP_FAILED == map) { + perror("Unable to mmap file"); + exit(1); + } + + replace_symbol(map, st.st_size, argv[2], argv[3]); + return 0; +} |