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

x86 32-bits / 64-bits Assembleur Discussion :

Recode fonction strlen


Sujet :

x86 32-bits / 64-bits Assembleur

  1. #1
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    44
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 27
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 44
    Points : 42
    Points
    42
    Par défaut Recode fonction strlen
    Bonjour à tous,

    Je cherche a recoder la fonction strlen de la libc. Mon problème est lorsque je calcul la length de la chaine il me retourne toujours le même nombre alors que je push bien mon argument et mov bien mes registres et je n'arrive pas a comprendre pourquoi enfaite je renvoie toujours le même nombre.
    Voila ce que j'ai fais:
    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
     
    section .text
            global _start, my_strlen
     
    my_strlen:
            push rbp,               ; met rbp sur la stack                                                               
            mov rbp, rsp            ; met rsp dans rbp                                                                   
            mov rbx, [rbp + 8]      ; met le 1er argument dans rbx                                                       
            xor rax, rax            ; taille                                                                             
    loop:
            cmp byte [rbx], 0h      ; comparaison avec NULL                                                              
            jz end                  ; fin de la chain                                                                    
            inc rax                 ; incremente la taille de 1                                                          
            inc rbx                 ; prochain byte                                                                      
            jmp loop                ; rappel loop                                                                        
    end:
            pop rbp
            ret
    Est-ce que vous auriez une doc pour des explications ou une piste a me donner pour que je puisse corriger mon soucie.
    Merci d'avance

  2. #2
    Expert éminent Avatar de BufferBob
    Profil pro
    responsable R&D vidage de truites
    Inscrit en
    Novembre 2010
    Messages
    3 035
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : responsable R&D vidage de truites

    Informations forums :
    Inscription : Novembre 2010
    Messages : 3 035
    Points : 8 400
    Points
    8 400
    Par défaut
    salut,

    tu ne lis pas au bon endroit, en l'occurrence tu pointes sur argc au lieu de pointer sur argv[1]

  3. #3
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    44
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 27
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 44
    Points : 42
    Points
    42
    Par défaut
    Salut,

    merci pour ta réponse j'ai directement corrigé ma ligne mov rbp, [rsp + 8] si j'ai bien compris bien sur

    Mais j'ai toujours un soucie c'est que mon strlen me renvoie toujours la même valeur (6 en l'occurence).
    Je n'arrive aps a voir car cela me parait logique dans a manière ou je l'ai fait directement mais peut-être que je n'ai pas vue le soucie auxquelles je me confronte.

    Merci d'avance encore

  4. #4
    Expert éminent Avatar de BufferBob
    Profil pro
    responsable R&D vidage de truites
    Inscrit en
    Novembre 2010
    Messages
    3 035
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : responsable R&D vidage de truites

    Informations forums :
    Inscription : Novembre 2010
    Messages : 3 035
    Points : 8 400
    Points
    8 400
    Par défaut
    Citation Envoyé par budocay Voir le message
    j'ai directement corrigé ma ligne mov rbp, [rsp + 8] si j'ai bien compris bien sur
    raté, c'était rbp+24 ^^
    dans le cas présent changer rbp pour rsp ne servait à rien, puisque tu ne crées pas de stack (ou alors t'as oublié un sub rsp, xyz) et que les deux registres ont la même valeur

    tu devrais apprendre à utiliser gdb :
    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
    $ gdb -q ./pouet
    gdb$ break *_start+4                                                          # on pose un breakpoint
    Breakpoint 1 at 0x400084
    gdb$ run "hello"                                                              # on lance le programme, avec comme paramètre "hello"
    (...)
    Breakpoint 1, 0x0000000000400084 in _start ()
    gdb$ x/4gx $rbp                                                               # on dump la mémoire, 4 valeurs sur 64bits à partir de rbp
    0x7fffffffe128: 0x0000000000000000      0x0000000000000002
    0x7fffffffe138: 0x00007fffffffe40d      0x00007fffffffe444
    gdb$ x/d $rbp+8
    0x7fffffffe130: 2                                                             # argc, valeur contenue dans [rbp+8]
    gdb$ x/s 0x00007fffffffe40d
    0x7fffffffe40d:  "/home/gruik/Bureau/code/langages/asm/dvp/budocay/pouet"     # argv[0], pointeur contenu dans [rbp+16]
    gdb$ x/s 0x00007fffffffe444
    0x7fffffffe444:  "hello"                                                      # et argv[1], pointeur contenu dans [rbp+24]

  5. #5
    Membre confirmé Avatar de bifur
    passe le balais et l'aspirateur
    Inscrit en
    Mars 2008
    Messages
    314
    Détails du profil
    Informations personnelles :
    Âge : 38

    Informations professionnelles :
    Activité : passe le balais et l'aspirateur

    Informations forums :
    Inscription : Mars 2008
    Messages : 314
    Points : 550
    Points
    550
    Par défaut
    sinon il y a aussi la possibilité des passer les argument de la sous fonction via des registres processeur:

    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
    my_strlen:
    ;entrée RBX=adresse de la chaine
    ;sortie RBX=taille de la chaine
    push rax
    xor rax,rax
     
    loop:
            cmp byte [rbx], 0h      ; comparaison avec NULL                                                              
            jz end                  ; fin de la chain                                                                    
            inc rax                 ; incremente la taille de 1                                                          
            inc rbx                 ; prochain byte                                                                      
            jmp loop                ; rappel loop                                                                        
    end:
            mov rbx,rax
            pop rax
            ret
    c'est utilisable uniquement dans du code assembleur mais ça evite les erreurs d'oublie de libération de pile, et de faire des programme qui gache de plus en plus de mémoire
    .....faut pas oublier qu'avec le 64bit on a de plus en plus de registre pour faire ça

  6. #6
    Expert éminent Avatar de BufferBob
    Profil pro
    responsable R&D vidage de truites
    Inscrit en
    Novembre 2010
    Messages
    3 035
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : responsable R&D vidage de truites

    Informations forums :
    Inscription : Novembre 2010
    Messages : 3 035
    Points : 8 400
    Points
    8 400
    Par défaut
    @bifur, je crois que tu te marches sur le rax, tu push ligne 4, tu pop ligne 15, du coup ça retourne rien à priori ^^ fatigue... grosse fatigue...

    sinon tant qu'à proposer des améliorations, au delà de la convention d'appel on pourrait surtout éliminer la boucle explicite en jouant du rep scas :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    my_strlen:
       mov rdi, pointeur_chaine  ; on charge rdi avec le pointeur sur la string
       xor rax, rax              ; on met al à zéro pour scasb
       xor rcx, rcx              ; on met rcx à...
       dec rcx                   ; ... -1 , pour repnz
       cld                       ; on s'assure de pas être en marche arrière
       repnz scasb               ; et zou. "tant que [RDI] est différent de AL et que RCX est différent de 0, on incrémente RDI et on décrémente RCX"
       not rcx                   ; à la sortie on remet rcx à l'endroit
       lea rax, [rcx - 1]        ; et on stocke le résultat dans rax, par convention
       ret

Discussions similaires

  1. Fonction strlen (segmentation fault)
    Par Cathy dans le forum C
    Réponses: 10
    Dernier message: 22/07/2008, 20h22
  2. Résultat incohérent de la fonction strlen()
    Par kaayna dans le forum Langage
    Réponses: 2
    Dernier message: 23/05/2008, 17h35
  3. Trou de mémoire : fonction strlen()
    Par bit_o dans le forum C
    Réponses: 3
    Dernier message: 30/04/2007, 23h20
  4. Comportement bizarre de la fonction strlen
    Par clampin dans le forum C
    Réponses: 4
    Dernier message: 30/12/2006, 14h00
  5. [PHP-JS] Fonction strlen en php
    Par viny dans le forum Langage
    Réponses: 20
    Dernier message: 04/10/2006, 14h09

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