IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C Discussion :

LKM et redirection de fonctions.


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 16
    Par défaut LKM et redirection de fonctions.
    Bonjour à tous.

    J'ai recemment découvert la programmation de LKM (modules kernel pour le noyau linux). Ainsi, il me semblait que l'on pouvait TOUT faire en kernel mode, c'est pourquoi j'avais essayé de rédiger un petit rootkit pour essayer de comprendre le hijacking de fonction.

    La théorie est plutot simple : je récupère l'adresse d'une fonction - qui est déjà exportée pour ne pas avoir à faire de recherches dans les fichiers systèmes - (j'ai choisi strstr ), puis j'écrase les 9 premiers octets de la fonction que je remplace par :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    mov eax, <adresse de ma fonction>
    jmp eax
    Cependant, lors de l'écriture de ces opcodes à la place des octets de strstr, mon kernel m'affiche une erreur et coupe le module. Voici le bout de code qui fait tout planter. J'ai indiqué l'étape qui causait une erreur.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    unsigned char hijack_backup[9]; /*Pour conserver les 9 premiers octets de la fonction*/
    unsigned char hijack_code[9];
     
    int start_hijack(void){
    	/*On vide le buffer*/
    	memset(hijack_code,0,9);
     
    	/*On y copie les informations nécessaires*/
     
    	hijack_code[0] = '\x66'; /*MOV*/
    	hijack_code[1] = '\xb8'; /*EAX*/
    	memcpy(hijack_code + 2, (unsigned char*) &HiJack_hook,4); //HiJack_hook est le nom de la fonction vers laquelle je détourne strstr()
    	hijack_code[6] = '\x66'; /*JMP EAX*/
    	hijack_code[7] = '\xff';
    	hijack_code[8] = '\xe0';
     
    	/*On sauvegarde ensuite les premiers octets de la fonction strstr(). */
    	memset(hijack_backup,0,9);
    	memcpy(hijack_backup,(char*)(strstr),9);
     
    	/*Puis on les remplace par notre saut inconditionnel vers la fonction
               de détournement.*/
    	memcpy((char*)(strstr),hijack_code,9); // [!] ERREUR [!]
     
    	return 1;
    }
    Voila, si l'un d'entre vous à une idée sur ce problème... Peut être qu'on ne peut pas tout faire dans l'espace noyau au final ! Ou peut être que je suis tout simplement mauvais programmeur (je débute).

    Merci d'avance pour le temps que vous m'accorderez.

    Cordialement, Sat.

  2. #2
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    27 119
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 27 119
    Billets dans le blog
    148
    Par défaut
    Bonjour,

    Pourriez vous montrer le message d'erreur envoyé par le kernel ( et peut être aussi les logs du kernels ). Je pense juste que c'est parce que vous provoquez une erreur de segmentation .
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  3. #3
    Membre averti
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 16
    Par défaut
    Bonjour, merci de votre réponse.

    En effet il me semble qu'il s'agit d'une erreur de segmentation, mais je n'arrive pas à comprendre comment je pourrais la corriger.

    Voici le log kernel (dmesg) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
     
    izy@izynumeric:~# insmod rootkit.ko
    Processus arrété
    izy@izynumeric:~$dmesg
    [  215.425192] Module chargé
    [  215.428089] BUG: unable to handle kernel paging request at c0352a30
    [  215.428089] IP: [<da6ed065>] start_hijack+0x65/0x80 [rootkit]
    [  215.428089] *pde = 008da067 *pte = 00352161 
    [  215.428089] Oops: 0003 [#1] SMP 
    [  215.428089] last sysfs file: /sys/devices/LNXSYSTM:00/LNXSYBUS:00/PNP0A03:00/PNP0C0A:00/power_supply/BAT0/energy_full
    [  215.428089] Modules linked in: rootkit(+) nls_utf8 isofs vboxvideo drm agpgart binfmt_misc vboxvfs snd_intel8x0 snd_ac97_codec ac97_bus snd_pcm_oss snd_mixer_oss snd_pcm snd_seq_dummy snd_seq_oss snd_seq_midi snd_rawmidi snd_seq_midi_event snd_seq snd_timer fbcon tileblit font snd_seq_device bitblit softcursor ppdev snd parport_pc psmouse vga16fb soundcore serio_raw vgastate snd_page_alloc i2c_piix4 vboxguest lp parport pcnet32 floppy mii
    [  215.428089] 
    [  215.428089] Pid: 1418, comm: insmod Not tainted (2.6.32-21-generic #32-Ubuntu) VirtualBox
    [  215.428089] EIP: 0060:[<da6ed065>] EFLAGS: 00010246 CPU: 0
    [  215.428089] EIP is at start_hijack+0x65/0x80 [rootkit]
    [  215.428089] EAX: 8955b866 EBX: fffffffc ECX: 00000000 EDX: 00000002
    [  215.428089] ESI: da6ed4c0 EDI: 00000000 EBP: d7ce3f5c ESP: d7ce3f4c
    [  215.428089]  DS: 007b ES: 007b FS: 00d8 GS: 00e0 SS: 0068
    [  215.428089] Process insmod (pid: 1418, ti=d7ce2000 task=ce7ad9b0 task.ti=d7ce2000)
    [  215.428089] Stack:
    [  215.428089]  da6ed15e da6ed436 d7ce3f78 c016c9f4 d7ce3f88 c0101131 da6ed4c0 c076d240
    [  215.428089] <0> fffffffc da6ed4c0 00384ff4 da6ed0d0 fffffffc da6ed4c0 00384ff4 d7ce3fac
    [  215.428089] <0> c0182340 c9100ab8 ce7ad9b0 c9100a80 00000004 0864b018 0864b018 00004000
    [  215.428089] Call Trace:
    [  215.428089]  [<da6ed15e>] ? init_module+0x8e/0xc0 [rootkit]
    [  215.428089]  [<c016c9f4>] ? __blocking_notifier_call_chain+0x54/0x70
    [  215.428089]  [<c0101131>] ? do_one_initcall+0x31/0x190
    [  215.428089]  [<da6ed0d0>] ? init_module+0x0/0xc0 [rootkit]
    [  215.428089]  [<c0182340>] ? sys_init_module+0xb0/0x210
    [  215.428089]  [<c01033ec>] ? syscall_call+0x7/0xb
    [  215.428089] Code: 0d 8a f6 6e da 89 d1 c6 05 8d f6 6e da ff f3 ab a1 30 2a 35 c0 5f 5d a3 80 f6 6e da a1 34 2a 35 c0 a3 84 f6 6e da a1 88 f6 6e da <a3> 30 2a 35 c0 a1 8c f6 6e da a3 34 2a 35 c0 b8 01 00 00 00 c3 
    [  215.428089] EIP: [<da6ed065>] start_hijack+0x65/0x80 [rootkit] SS:ESP 0068:d7ce3f4c
    [  215.428089] CR2: 00000000c0352a30
    [  215.428089] ---[ end trace b8233d8a6f74d875 ]---

    Auriez vous une idée ?

    Cordialement, Sat.

  4. #4
    Membre averti
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 16
    Par défaut
    Je me suis repenché sur le problème et je me suis permis de réactualiser ce sujet car je n'ai toujours pas trouvé de solutions.

    Le programme crash dès que j'essaie d'écraser les 9 premiers octets de strstr() et je n'arrive pas à comprendre pourquoi.

    Peut être qu'il s'agit d'une sorte de sécurité (l'erreur me rapelle celle causée quand on écrase le nxbit, car je suis sur ubuntu), ou peut être que tout simplement je ne peux pas écrire à cette emplacement, même en kernel mode.

    Je réitère donc ma question : peut on vraiment tout faire en mode noyau ? Auriez vous une idée sur ce qui peut causer cette erreur ?

    Merci d'avance.

    Cordialement, Sat.

  5. #5
    Invité de passage
    Inscrit en
    Juillet 2010
    Messages
    1
    Détails du profil
    Informations forums :
    Inscription : Juillet 2010
    Messages : 1
    Par défaut
    Bonjour,

    Je suis justement en plein travail sur les hooks dans le kernel unix dans le cadre d'un stage. J'espère pouvoir vous aider avec les maigres connaissances que j'ai accumulées en quelques semaines.

    Tout d'abord, il n'est pas possible de TOUT faire en mode noyau, et ce en fonction de la version de votre kernel. Un hook sur la sys_call sera nettement plus aisé en 2.6.15 qu'en 2.6.25 par exemple, les versions plus récentes du kernel amenant quand même quelques protections sur les droits d'écriture de certaines pages mémoire.

    Pour revenir sur votre hook, j'ai pu constater qu'il ne fallait jamais toucher aux trois premiers octets d'une fonction. En effet ils sont généralement utilisés pour initialiser la pile (en asm on a: push ebp; mov esp, ebp). Vous pourriez essayer de décaler votre jump, cela a marché pour moi.

    Je vous conseille aussi de jeter un oeil à la librairie lkh qui m'aide beaucoup dans mon travail, ainsi que sur le code de quelques rootkits.

    En espérant avoir pu vous aider, elenwel

  6. #6
    Membre averti
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 16
    Par défaut
    Bonjour.

    Merci de votre réponse.

    Même en décalant le jump, le processus est arrété. Auriez vous une alternative pour détourner l'appel d'une fonction exportée ?

    Cordialement, Sat.

  7. #7
    Membre expérimenté
    Homme Profil pro
    Ingénieur sécurité
    Inscrit en
    Juillet 2007
    Messages
    193
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Ingénieur sécurité
    Secteur : High Tech - Produits et services télécom et Internet

    Informations forums :
    Inscription : Juillet 2007
    Messages : 193
    Par défaut
    Cela vient surrement du bit NX de ton processeur, qui est activé de base sous ubuntu et pas sur debian par exemple.

    Je suis pratiquement certain que si tu test sur debian cela passera.
    Cependant, dans ton hook, quelque chose m'etonne, tu ne sauvegarde nul par les octets que tu as ecrasé pour les restituer par exemple ?

    Sinon, pour la discussion sur la syscall table, en effet des efforts sont fait pour empecher qu'elle soit modifié. Je ne sais plus depuis quel version cela à été fait, mais cette table n'est plus exporté.

    Cependant, il existe des petits "hack" simple afin de quand meme pouvoir la modifier.

    Pour revenir à la discution de base, il faut quand tu fais quelque chose de spécial, que tu t'assures que tu ais le droit de le faire.
    Si tu avais commencé ton LKM sur un systeme sans NX de base, et que quelqu'un d'autre le test sous ubuntu, le produit fini aurait segfaulté.

    Cela fait longtemps mais pour changer les droits sur ta page regarde du coté de la fonction mprotect, voir meme comment modifier les autorisation des tes PTE à la main.

  8. #8
    Membre averti
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 16
    Par défaut
    Bonjour et merci pour votre réponse.

    Il me semblait que le NX bit ne s'activait uniquement lors d'un dépassement de tampon. Or, je n'écrit que dans un tampon déjà alloué (en supposant que la fonction strstr fasse plus de 9 octets).

    Pensez vous que j'ai le droit de modifier les autorisations des pages mémoires en espace noyau avec les LKM ? Je jetterai un oeil sur la fonction ce soir, et je vous tiendrais au courant de l'avancement.

    Merci pour votre aide.

    Cordialement, Sat.

Discussions similaires

  1. Réponses: 4
    Dernier message: 14/11/2005, 11h59
  2. Redirection en fonction de l'extension de l'URL
    Par Mr Hyde dans le forum Web
    Réponses: 6
    Dernier message: 21/09/2005, 17h39
  3. Redirection en fonction de l'extension de l'URL
    Par Mr Hyde dans le forum Autres langages pour le Web
    Réponses: 3
    Dernier message: 20/09/2005, 14h01
  4. Redirection en fonction d'un formulaire
    Par kmayoyota dans le forum Général JavaScript
    Réponses: 6
    Dernier message: 11/03/2005, 11h14
  5. Redirection en fonction d'un critere Access
    Par alfigor dans le forum ASP
    Réponses: 4
    Dernier message: 23/04/2004, 09h34

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo