wystąpienie znaku w zespole x86

  • Wprowadzenie
  • Kwestia
  • Rozwiązanie
  • Wyjaśnienie

Wprowadzenie

Poniższe małe ćwiczenie montażowe dotyczy 32-bitowych architektur x86 firmy Intel i AMD i używa składni NASM, asemblera, dostępnego za darmo i

które mogą być używane na różnych platformach, takich jak Windows lub Linux.

Zauważ, że używane funkcje zewnętrzne pochodzą ze standardowej biblioteki C.

Kwestia

Wyobraź sobie tablicę znaków (która niekoniecznie kończy się na 0). Ma swój rozmiar i chcielibyśmy przetestować obecność danej postaci

w tej tablicy. Celem będzie napisanie funkcji, która przyjmuje jako wejściowy tablicę znaków, rozmiaru i charakteru. Jeśli ta postać jest obecna w

tablica zwraca wartość niezerową, w przeciwnym razie zwraca zero.

Oto, co daje tę funkcję w C:

 / funkcja int to_in_array (char * tablica, int rozmiar, char c); // implementacja: karta char [] = {'n', 'e', ​​'u', 'e'}; is_in_array (tab, sizeof (tab), „u”); // Zwraca wartość inną niż 0 is_in_array (tab, sizeof (tab), 'a'); // Wartość zwracana 0 Po prostu wstaw swój kod w: extern printf section .data array db 'dadedidadedavivoufufifamasibifisaz' yes db 'oui', 10, 0 nie db 'non', 10, 0 sekcja. Global global is_in_array:; main: push ebp mov ebp, esp; Testuj, jeśli m znajduje się w tablicy push dword 'm'; Długość tablicy (tutaj 34) naciśnij dword 34; adres łańcucha w eax push array; Call is_in_array z adresem tablicy; rozmiar, a wartość, której szukasz, to is_in_array test eax, eax jnz is_there; if eax! = 0 display yes push no; następnie nie wyświetlaj jmp screendisplay; screendisplay łańcucha z printf is_there push tak screendisplay: call printf mov eax, 0 zostawić ret 

Z pewnością to nie wystarczy .....

Rozwiązanie

 is_in_array:; Pobiera adres tablicy (pierwszy parametr) w edi mov edi, [esp + 4]; Pobiera rozmiar tablicy (drugi parametr) w ecx mov ecx, [esp + 8]; Pobiera znak do znalezienia (trzeci parametr) w eax mov eax, [esp + 12]; Przeszukaj znak repne scasb; Jeśli flag ZERO (ZF) ma wartość 1, oznacza to, że znak został znaleziony; w innym przypadku nie został znaleziony; wystarczy dodać wartość ZF w eax mov eax, 0; Jeśli ZF = 1 to al = 1 (al będący 8 najmniej znaczącymi bitami eax) setz al ret 

Wyjaśnienie

 ZF = 0 ecx = długość eax = znak edi = tablica // Pętla definiująca „repne scasb” Podczas ecx! = 0 ET ZF = 0 Zrób, jeśli al == [edi] Następnie ZF = 1 FinSi ecx = ecx - 1 edi = edi + 1 EndWhile eax = 0 // Warunek definiujący „setz” Si ZF = 1 Alors eax = 1 EndIf 
Poprzedni Artykuł Następny Artykuł

Najważniejsze Wskazówki