System call and kernel module..

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hello,

I learnt that the sys_call_table is no longer is exportable in 2.6+. I'm using 2.6.35.4 and trying to implement it in a LKM. I read the virtual addr of sys_call_table from the system map and made its physical page writable and added my syscall in place of Andrew Filesystem syscall and then made the page readonly again. But when I call my system call it is still calling AFS syscall and hence getting back ENOSYS error.  I printed the sys_call_table at AFS syscall index after making the change and it seems to have the addr of my syscall. I'm not understanding where did it go wrong. Any help on figuring this out would be appreciated. Below is my code...

I haven't yet implemented the sytem call. Its about encrypting and decrypting user specified files. I would do that later once have this infrastructure set. Now I'm just printing that "I was here!".

And is there a better way of implementing this? Like creating a system call stub in the kernel that calls my function which would be part of an LKM? I would really want a generic solution to this. 


[root]# grep sys_call_table System.map
c12ba180 R sys_call_table
-----------------------------------------------------------------------------------------
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/unistd.h>
#include <linux/mman.h>
#include <linux/sched.h>
#include <asm/uaccess.h>
#include <asm/pgtable.h>
#include <asm/processor.h>
#include <asm/atomic.h>
#include <asm/mman.h>
#include <linux/init.h>
#include <linux/mm.h>
#include <linux/syscalls.h>
#include <asm/cacheflush.h>
#include <asm/page.h>
#include <linux/linkage.h>

MODULE_LICENSE("GPL");
MODULE_AUTHOR("shetty");
MODULE_DESCRIPTION("sys_crypt implementation");

unsigned long *sys_call_table = (unsigned long *)0xc12ba180;
static asmlinkage int (*original_call) ();


#define __NR_afs_syscall 137

SYSCALL_DEFINE5(crypt,const char __user *, infile, const char __user *, outfile,
                         const char __user *, keybuf, int, keylen, char, flags)
{

printk(KERN_ALERT "I was here!\n");
return keylen;

}
EXPORT_SYMBOL(sys_crypt);

static int __init sys_crypt_init(void)
{

        unsigned long addr;
        struct page *page;
        printk(KERN_ALERT "Inserting hw1-module...\n");

        page_sys_call_table = virt_to_page(sys_call_table);
        addr = (unsigned long)page_address(page);
        set_memory_rw(addr, 1);
        original_call = sys_call_table[__NR_afs_syscall];
        sys_call_table[__NR_afs_syscall] = sys_crypt;

        printk(KERN_ALERT "sys_crypt = %X\n", sys_crypt);
        printk(KERN_ALERT "sys_call_table:sys_crypt =       %X",sys_call_table[__NR_new_syscall]);
        printk(KERN_ALERT "sys_call_table = %X\n", sys_call_table);
        printk(KERN_ALERT "&sys_call_table:sys_crypt = %X",&sys_call_table[__NR_new_syscall]);

        set_memory_ro(addr, 1);


        printk(KERN_ALERT "sys_call_table is exported\n");
        return 0;


}

static void __exit sys_crypt_exit(void)
{
    unsigned long addr;
        struct page *page;      
    page_sys_call_table = virt_to_page(sys_call_table);
        addr = (unsigned long)page_address(page);
       
    set_memory_rw(addr, 1);
    sys_call_table[__NR_afs_syscall] = original_call;
        set_memory_ro(addr, 1);   
   
    printk(KERN_ALERT "Removing hw1-module\n");
}

module_init(sys_crypt_init);
module_exit(sys_crypt_exit);

EXPORT_SYMBOL(sys_call_table);
-----------------------------------------------------------------------------------

/var/log/messages:

Sep 13 19:11:11 d136 kernel: Inserting hw1-module...
Sep 13 19:11:11 d136 kernel: sys_crypt = D084B000                            <<<<<
Sep 13 19:11:11 d136 kernel: sys_call_table:sys_crypt = D084B000       <<<<<
Sep 13 19:11:11 d136 kernel: original_call = X
Sep 13 19:11:11 d136 kernel: sys_call_table = C12BA180
Sep 13 19:11:11 d136 kernel: &sys_call_table:sys_crypt = C12BA38C
Sep 13 19:11:11 d136 kernel: sys_call_table is exported

***************From strace*****************************

afs_syscall(0x8049708, 0xbf8a5828, 0x8048462, 0x9d0ff4, 0x9cf208) = -1 ENOSYS (Function not implemented)
fstat64(1, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 1), ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7813000
write(1, "-1Error: 38, Function not implem"..., 38) = 38
exit_group(36) 
***********************************************************


Thanks..
-Pradeep

[Index of Archives]     [Newbies FAQ]     [Linux Kernel Mentors]     [Linux Kernel Development]     [IETF Annouce]     [Git]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux RAID]     [Linux SCSI]     [Linux ACPI]
  Powered by Linux