[OpenAFS-devel] System Call Stubs for IA64
Srikanth Vishwanathan
vsrikanth@in.ibm.com
Thu, 9 May 2002 20:20:20 -0400
Hi -
I see that the entry points for all system calls that AFS defines
or replaces is a stub written in assembler (for taking care of the
global pointer)
I don't think this is really necessary. I was thinking that instead,
we could have stubs written entirely in C that would fabricate function
pointers with the function descriptor initialized properly.
I tried the following and it worked. I believe it should work in the
kernel too.
# uname -m
ia64
# cat syscall.c
#include <stdio.h>
typedef long (*syscall_t)(unsigned long, unsigned long,
unsigned long, unsigned long,
unsigned long, unsigned long);
long call_syscall_gp(const syscall_t func,
unsigned long arg1, unsigned long arg2,
unsigned long arg3, unsigned long arg4,
unsigned long arg5, unsigned long arg6)
{
long rc;
void *newfunc;
unsigned long funcdesc[2];
funcdesc[0] = ((unsigned long *) func)[0];
funcdesc[1] = ((unsigned long *) func)[1];
newfunc = funcdesc;
rc = ((syscall_t) newfunc)(arg1, arg2, arg3, arg4, arg5, arg6);
return rc;
}
int main(void)
{
long rc1, rc2;
unsigned long main_gp = ((unsigned long *) main)[0];
unsigned long printf_gp = ((unsigned long *) printf)[0];
rc1 = call_syscall_gp((syscall_t) printf,
(unsigned long) "main_gp: 0x%016lx, ",
main_gp, 0, 0, 0, 0);
rc2 = call_syscall_gp((syscall_t) printf,
(unsigned long) "printf_gp: 0x%016lx\n",
printf_gp, 0, 0, 0, 0);
printf("rc1 = %d, rc2 = %d\n", (int) rc1, (int) rc2);
return 0;
}
# make
cc -Wall -O2 -S syscall.c
cc -Wall -O2 -o syscall syscall.c
# ./syscall
main_gp: 0x4000000000000750, printf_gp: 0x200000000011af20
rc1 = 29, rc2 = 30
#
If this works, the new system call stub can be changed to something
like:
extern long afs_syscall(unsigned long, unsigned long, unsigned long,
unsigned long, unsigned long, unsigned long);
asmlinkage long afs_syscall_stub(unsigned long arg1, unsigned long arg2,
unsigned long arg3, unsigned long arg4,
unsigned long arg5, unsigned long arg6)
{
return call_syscall_gp(afs_syscall, arg1, arg2, arg3,
arg4, arg5, arg6);
}
Am I missing anything here ?
Thanks,
Srikanth.