From 6fe4e8795452651862c1e02994f434ec5f0d5832 Mon Sep 17 00:00:00 2001 From: "H.J. Lu" Date: Fri, 4 Oct 2013 10:03:17 -0700 Subject: [PATCH] Add an optional alias list to SYSCALLS.TXT This patch adds an optional alias list to SYSCALLS.TXT. It is used to create aliases for a syscall. For x86-64, lseek64 is an alias for lseek. Change-Id: Icb11fd2bb461ea4f5f0a26bfc585471d7d7cc468 Signed-off-by: H.J. Lu Signed-off-by: Pavel Chupin --- libc/SYSCALLS.TXT | 7 +++++-- libc/arch-x86_64/syscalls/lseek.S | 3 +++ libc/tools/bionic_utils.py | 14 +++++++++++++- libc/tools/gensyscalls.py | 13 +++++++++++-- 4 files changed, 32 insertions(+), 5 deletions(-) diff --git a/libc/SYSCALLS.TXT b/libc/SYSCALLS.TXT index b61340181..f926ad03b 100644 --- a/libc/SYSCALLS.TXT +++ b/libc/SYSCALLS.TXT @@ -2,7 +2,7 @@ # # Each non-blank, non-comment line has the following format: # -# return_type func_name[:syscall_name[:socketcall_id]]([parameter_list]) arch_list +# return_type func_name[|alias_list][:syscall_name[:socketcall_id]]([parameter_list]) arch_list # # where: # arch_list ::= "all" | "custom" | arch+ @@ -13,6 +13,8 @@ # the exported function name (example: the exit syscall is implemented by the _exit() # function, which is not the same as the standard C exit() function which calls it) # +# - alias_list is optional comma separated list of function aliases. +# # - The call_id parameter, given that func_name and syscall_name have # been provided, allows the user to specify dispatch style syscalls. # For example, socket() syscall on i386 actually becomes: @@ -109,7 +111,8 @@ int __open:open(const char*, int, mode_t) all int __openat:openat(int, const char*, int, mode_t) all int close(int) all int creat(const char*, mode_t) custom -off_t lseek(int, off_t, int) all +off_t lseek(int, off_t, int) arm,x86,mips +off_t lseek|lseek64(int, off_t, int) x86_64 int __llseek:_llseek(int, unsigned long, unsigned long, off64_t*, int) arm,x86,mips pid_t getpid() all void* mmap(void*, size_t, int, int, int, long) x86_64 diff --git a/libc/arch-x86_64/syscalls/lseek.S b/libc/arch-x86_64/syscalls/lseek.S index 97563157a..a237f8b6a 100644 --- a/libc/arch-x86_64/syscalls/lseek.S +++ b/libc/arch-x86_64/syscalls/lseek.S @@ -15,3 +15,6 @@ ENTRY(lseek) 1: ret END(lseek) + + .globl _C_LABEL(lseek64) + .equ _C_LABEL(lseek64), _C_LABEL(lseek) diff --git a/libc/tools/bionic_utils.py b/libc/tools/bionic_utils.py index a00080d62..0ca217826 100644 --- a/libc/tools/bionic_utils.py +++ b/libc/tools/bionic_utils.py @@ -49,7 +49,7 @@ class SysCallsTxtParser: """ parse a syscall spec line. line processing, format is - return type func_name[:syscall_name[:socketcall_id]] ( [paramlist] ) architecture_list + return type func_name[|alias_list][:syscall_name[:socketcall_id]] ( [paramlist] ) architecture_list """ pos_lparen = line.find('(') E = self.E @@ -93,6 +93,17 @@ class SysCallsTxtParser: socketcall_id = int(syscall_func[pos_colon2+1:]) syscall_func = syscall_func[:pos_colon] + alias_delim = syscall_func.find('|') + if alias_delim > 0: + alias_list = syscall_func[alias_delim+1:].strip() + syscall_func = syscall_func[:alias_delim] + alias_delim = syscall_name.find('|') + if alias_delim > 0: + syscall_name = syscall_name[:alias_delim] + syscall_aliases = string.split(alias_list, ',') + else: + syscall_aliases = [] + if pos_rparen > pos_lparen+1: syscall_params = line[pos_lparen+1:pos_rparen].split(',') params = string.join(syscall_params,',') @@ -103,6 +114,7 @@ class SysCallsTxtParser: t = { "name" : syscall_name, "func" : syscall_func, + "aliases" : syscall_aliases, "params" : syscall_params, "decl" : "%-15s %s (%s);" % (return_type, syscall_func, params), "socketcall_id" : socketcall_id diff --git a/libc/tools/gensyscalls.py b/libc/tools/gensyscalls.py index a3c84505e..386a8db92 100755 --- a/libc/tools/gensyscalls.py +++ b/libc/tools/gensyscalls.py @@ -37,6 +37,10 @@ syscall_stub_header = """/* autogenerated by gensyscalls.py */ ENTRY(%(fname)s) """ +function_alias = """ + .globl _C_LABEL(%(alias)s) + .equ _C_LABEL(%(alias)s), _C_LABEL(%(fname)s) +""" # # x86 assembler templates for each syscall stub @@ -210,7 +214,7 @@ class State: self.other_files = [] self.syscalls = [] - def x86_64_genstub(self, fname, numparams, idname): + def x86_64_genstub(self, fname, numparams, idname, aliases): t = { "fname" : fname, "idname" : idname } result = syscall_stub_header % t @@ -219,6 +223,10 @@ class State: result += " movq %rcx, %r10\n" result += x86_64_call % t + for alias in aliases: + t = { "fname" : fname, "alias" : alias } + result += function_alias % t + return result def x86_genstub(self, fname, numparams, idname): @@ -301,6 +309,7 @@ class State: for t in self.syscalls: syscall_func = t["func"] + syscall_aliases = t["aliases"] syscall_params = t["params"] syscall_name = t["name"] __NR_name = make__NR_name(t["name"]) @@ -324,7 +333,7 @@ class State: if t.has_key("x86_64"): num_regs = count_generic_param_registers64(syscall_params) - t["asm-x86_64"] = self.x86_64_genstub(syscall_func, num_regs, __NR_name) + t["asm-x86_64"] = self.x86_64_genstub(syscall_func, num_regs, __NR_name, syscall_aliases) # Scan a Linux kernel asm/unistd.h file containing __NR_* constants # and write out equivalent SYS_* constants for glibc source compatibility.