RSS Feed

O mica problema in ASM … de Craciun

December 26th, 2007

Pentru ca tot era Craciunul si nu aveam ce face, m-am apucat de o mica problema in ASM ... am apelat la un coleg de facultate,Alex D., care mi-a dat urmatoarea problema : Sa se ordoneze un vector de numere naturale dupa numarul de biti necesari pentru a le scrie in baza 2 ... aveam deja bubble sort-ul implementat in asm ... Am procedat in felul urmator: stiam ca bubble sort compara, la un moment dat cate 2 elemente si verifica daca unul e mai mare ca celalalt. In loc de aceasta condiitie, eu trebuia sa aflu daca numarul de biti al primului e mai mare ca numarul de biti al celui de-al doilea... ca sa evit o seara "plina", am scris o alta functie, tot in asm , care imi returneaza numarul de biti pentru un numar. De aici totul a fost simplu ... ba nu ! Am stat o ora intreaga, uitandu-ma dupa pop-uri, push-uri, unele adrese se pierdeau, o adevarata dezordine... noroc cu prietenul meu AndreiASM ( numele spune tot :) ), care m-a ajutat cu diverse chestii tehnice pe care nu aveam de unde sa le cunosc ( apelarea unei functii cu parametri, etc. ) . In cele din urma, a rezultat codul de mai jos, care "merge", dar nu am absolut niciun chef sa ma mai bag pe el in caz ca gasesc vreo eroare...

C++:
  1. #include <stdio.h>
  2. #include <iostream>
  3. using namespace std;
  4.  
  5.  
  6. int nr_biti(int)
  7. {
  8.     _asm
  9.     {
  10.         mov eax,[ebp+8]
  11.         cmp eax,0
  12.         je final
  13.         mov ebx,0
  14. bucla:
  15.         cmp eax,0
  16.         je stop
  17.         inc ebx
  18.         shr eax,1
  19.         jmp bucla
  20. stop:
  21.         mov eax,ebx
  22.         jmp stop2
  23. final:
  24.         mov ebx,1
  25.         jmp stop
  26. stop2:
  27.        
  28.     }
  29. }
  30.  
  31. void bubble_sort(int*,int)
  32. {
  33.     _asm
  34.     {
  35. bucla_mare:
  36.         mov ecx,0
  37.         mov eax,[ebp+8]
  38.         mov ebx,[ebp+12]
  39. bucla_mica:
  40.         mov edx,eax
  41.         add edx,4
  42.        
  43.         push dword ptr[eax]
  44.         push dword ptr[edx]
  45.  
  46.         push eax
  47.  
  48.         mov edi,eax
  49.  
  50.         push dword ptr[edx]
  51.         call nr_biti
  52.         mov  [edx],eax
  53.         add esp,4
  54.  
  55.         push dword ptr[edi]
  56.         call nr_biti
  57.         mov [edi],eax
  58.         add esp,4
  59.  
  60.         pop eax
  61.         push ecx
  62.         mov ecx,[edi]
  63.         mov [eax],ecx
  64.         pop ecx
  65.         mov esi,[eax]
  66.         cmp esi,[edx]
  67.         ja interschimbare
  68.         cmp esi,[edx]
  69.         jle nu_e
  70.        
  71. interschimbare:
  72.         pop dword ptr[edx]
  73.         pop dword ptr[eax]
  74.         push dword ptr [edx]
  75.         push dword ptr [eax]
  76.         pop dword ptr [edx]
  77.         pop dword ptr [eax]
  78.         mov ecx,1
  79.         jmp continua
  80. nu_e:   pop dword ptr[edx]
  81.         pop dword ptr[eax]
  82.         jmp continua
  83.  
  84. continua:
  85.  
  86.         add eax,4
  87.         dec ebx
  88.         cmp ebx,1
  89.         jne bucla_mica
  90.         cmp ecx,1
  91.         je bucla_mare
  92.     }
  93. }
  94.  
  95. int main()
  96. {
  97.     int v[100],n,i;
  98.     cin>>n;
  99.     for(i=0;i<n;i++) cin>>v[i];
  100.     bubble_sort(v,n);
  101.     for(i=0;i<n;i++) cout<<v[i]<<' ';
  102.     system("pause");
  103.     return 0;
  104. }

Leave a reply...