Мой цикл для поиска наименьшего элемента в массиве выводит 0 вместо правильного значения x86 Assembly? - PullRequest
0 голосов
/ 05 ноября 2018

Я пытаюсь создать программу для поиска второго наименьшего элемента в массиве. Прежде чем начать поиск второго наименьшего элемента, я пытаюсь найти первый наименьший элемент в массиве. В моей программе это правильно меняет нижний элемент массива в EAX. После того, как он читает следующий элемент в массиве, он заменяет 0 в eax, несмотря на то, что в моем массиве вообще нет 0. Я пробовал много разных комбинаций, но ни одна из них не имела значения. Вот код

INCLUDE io.h            ; header file for input/output

.STACK 4096

.DATA
 nbrArray dword 23, 45, 21, 78, 95 dup(?)
 smallest dword 7FFFFFFFh
 secondSmall dword 7FFFFFFFh


 string BYTE 40 DUP (?)
 resultLbl BYTE "The answer is : ", 0
 answer BYTE 40 DUP (?), 0

.CODE
_MainProc PROC
mov eax, smallest
mov edx, secondSmall
mov ebx,0
lea ebx, nbrArray
mov ecx, 5
jecxz end1

forLoop1:
cmp eax, [ebx]
mov edx,[ebx]
jg swap
jmp cont

cont:
 add ebx,4
 loop forLoop1

swap:
 mov eax,[ebx]
 add ebx,4
 loop forLoop1  

 dtoa answer, eax
 output resultLbl, answer
 end1:
    mov eax, 0
    ret

_MainProc ENDP
end               

1 Ответ

0 голосов
/ 06 ноября 2018

95 dup(?) означает 95 повторений 0. Используйте ваш отладчик для выгрузки памяти для вашего массива. Это так же, как dword 23, 45, 21, 78, 0, 0, 0, 0, 0, ...

Таким образом, последний счет делает своп 0 и падает до dtoa. В противном случае ваша программа потерпит крах.


У вас есть еще одна серьезная ошибка: если последний элемент не является новым наименьшим, значение loop forLoop1 падает с cont до swap с ECX = 0. Таким образом, инструкция loop в нижней части swap уменьшит ECX до 0xFFFFFFFF и прыгнет, потому что это не ноль. В конечном итоге вы будете виноваты в доступе за пределы памяти.

jmp cont бесполезен прямо перед меткой cont:: выполнение уже переходит к следующей инструкции. Что вам нужно, это jmp out_of_loop после ветви цикла в блоке cont:, чтобы вы не упали в swap:.

И кстати, loop инструкция медленная, вы никогда не должны ее использовать. Просто используйте cmp/jb на указателе, который вы уже увеличиваете, или dec ecx/jnz.

...