Linux Çekirdeği: Sistem çağrısı çengel örnek
Sistem tablosunu takma göstermek için, bazı basit test kodu yazmaya çalışıyorum.
< . p ^"sys_call_table" artık sadece sistemden adresini alıyorum o yüzden 2.6, ihraç edilir.göster dosya ve doğrudur (adreste bellek ile sistemin işaretçiler çağrıları görebiliyorum buldum Arayan) görebiliyorum.Bu tabloyu değiştirmek için çalışıyorum, ancak bir çekirdek "" sanal adres c061e4f4" ve makineyi yeniden. çekirdek belleği isteği işlemek için "mümkün olan Oops verir
Bu Otomotiv-5.4 2.6.18-164.10.1 çalışıyor.el5. Koruma falan mı var yoksa sadece bir hata var mı? SELinux ile geliyor biliyorum, ve buna izin modu koyarak denedim, ama bir şey fark etmez
İşte benim kod:
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/unistd.h>
void **sys_call_table;
asmlinkage int (*original_call) (const char*, int, int);
asmlinkage int our_sys_open(const char* file, int flags, int mode)
{
printk("A file was opened\n");
return original_call(file, flags, mode);
}
int init_module()
{
// sys_call_table address in System.map
sys_call_table = (void*)0xc061e4e0;
original_call = sys_call_table[__NR_open];
// Hook: Crashes here
sys_call_table[__NR_open] = our_sys_open;
}
void cleanup_module()
{
// Restore the original call
sys_call_table[__NR_open] = original_call;
}
CEVAP
Sonunda kendim çözüm buldum.
http://www.linuxforums.org/forum/linux-kernel/133982-cannot-modify-sys_call_table.html
Çekirdek sistem tablosunu okunur, böylece bir noktada değiştirildi.
cypherpunk:
Eğer geç değilse bile Çözüm ama başkalarının da: giriş.Göreceksiniz S dosyası: Kod:
.section .rodata,"a" #include "syscall_table_32.S"
sys_call_table ->Salt okunur var derlemek isterseniz Çekirdek yeni "sys_call_table... etrafta. "hack
Bağlantıyı da yazılabilir olması için hafıza değiştirme konusunda bir örnek vardır.
nasekomoe:
Herkese merhaba. Cevaplar için teşekkürler. Ben uzun zaman önce olan sorun çözüldü bellek sayfaları değiştirerek erişim. Ben bunu iki işlevi hayata geçirdik benim üst düzey için kod:
#include <asm/cacheflush.h> #ifdef KERN_2_6_24 #include <asm/semaphore.h> int set_page_rw(long unsigned int _addr) { struct page *pg; pgprot_t prot; pg = virt_to_page(_addr); prot.pgprot = VM_READ | VM_WRITE; return change_page_attr(pg, 1, prot); } int set_page_ro(long unsigned int _addr) { struct page *pg; pgprot_t prot; pg = virt_to_page(_addr); prot.pgprot = VM_READ; return change_page_attr(pg, 1, prot); } #else #include <linux/semaphore.h> int set_page_rw(long unsigned int _addr) { return set_memory_rw(_addr, 1); } int set_page_ro(long unsigned int _addr) { return set_memory_ro(_addr, 1); } #endif // KERN_2_6_24
İşte benim için çalışan orijinal kodu değiştirilmiş bir versiyonu.
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/unistd.h>
#include <asm/semaphore.h>
#include <asm/cacheflush.h>
void **sys_call_table;
asmlinkage int (*original_call) (const char*, int, int);
asmlinkage int our_sys_open(const char* file, int flags, int mode)
{
printk("A file was opened\n");
return original_call(file, flags, mode);
}
int set_page_rw(long unsigned int _addr)
{
struct page *pg;
pgprot_t prot;
pg = virt_to_page(_addr);
prot.pgprot = VM_READ | VM_WRITE;
return change_page_attr(pg, 1, prot);
}
int init_module()
{
// sys_call_table address in System.map
sys_call_table = (void*)0xc061e4e0;
original_call = sys_call_table[__NR_open];
set_page_rw(sys_call_table);
sys_call_table[__NR_open] = our_sys_open;
}
void cleanup_module()
{
// Restore the original call
sys_call_table[__NR_open] = original_call;
}
Nasıl bir süreç bölümlendirme hatası a...
Arasındaki fark "sistem" ve ...
Neden Sistem çağrısı için kötü bir uyg...
() Özyineli / T Unıx sistem çağrısı...
Brk( ) sistem çağrısı mı?...