Я работаю над сборкой, высокотехнологичной HLA (High Level Assembly), программой. Мне нужно преобразовать этот код C в assemvbly. Вот задание. Запишите языковую программу ассемблера HLA, которая реализует следующую функцию:Программа рекурсивного отдела сборки
процедура recursiveModulo (a: int32; b: int32); @нет дисплея; @noframe;
Эта функция должна возвращать в EAX значение% b на основе рекурсивного подхода. Для простоты предположим, что и a, и b будут больше или равны нулю. Используя рекурсию, вы будете вынуждены манипулировать стеком времени выполнения. Стройте свои решения по следующим формулам:
Здесь предоставляется код C:
int recursiveModulo(int a, int b)
{
int result = 0;
if (a == 0 || b == 0)
{
result = 0;
}
else if (b == 1)
{
result = 0;
}
else if (a < b)
{
result = a;
}
else
{
result = recursiveModulo(a-b, b);
}
return(result);
}
Вот мой HLA-код:
program RecursiveDivision;
#include("stdlib.hhf");
static
iDataValue1 : int32 := 0;
iDataValue2 : int32 := 0;
procedure recursiveModulo(a: int32; b : int32); @nodisplay; @noframe;
static
returnAddress : dword;
begin recursiveModulo;
pop(returnAddress);
pop(a);
pop(b);
push(returnAddress);
push(ECX);
push(EBX);
cmp(a, 0);
je equal;
jmp checkb;
checkb:
cmp(b, 0);
je equal;
jmp b1;
b1:
cmp(b, 1);
je equal;
jmp alessb;
equal:
mov(0, EAX);
jmp ExitSequence;
alessb:
mov(a, EBX);
cmp(b, EBX);
jg resulta;
jmp recursive;
resulta:
mov(a, EAX);
jmp ExitSequence;
recursive:
mov(a, ECX);
sub(b, ECX);
push(ECX);
push(b);
call recursiveModulo;
jmp ExitSequence;
ExitSequence:
pop(ECX);
pop(EBX);
ret();
end recursiveModulo;
begin RecursiveDivision;
stdout.put("Give me A",nl);
stdin.get(iDataValue1);
stdout.put("Give me B",nl);
stdin.get(iDataValue2);
push(iDataValue1);
push(iDataValue2);
call recursiveModulo;
stdout.puti32(EAX);
end RecursiveDivision;
Так часть моего кода, который работает правильно это сначала если блок. Для второго блока if, где результат должен быть равен нулю, если b = 1, это то, что он просто возвращает 1 вместо 0. Для третьего условия, где, если a меньше, чем b, я получаю эти странные проблемы, где он работает для некоторых комбинаций чисел , но в другое время он просто возвращает ноль. для блока else, где он должен вызывать функцию рекурсивно, он просто возвращает параметр a. `
Я не знаю, все правила для HLA, но ваше решение выглядит смешно для меня. В частности, вы являетесь «pop (a)» ... где это происходит? Вообще, когда вы пишете рекурсивную процедуру сборки, вы хотите сохранить все в регистрах или поверх стека. Другая вещь, которая выглядит странно, - это нажатие ECX и EBX на вход в функцию, что означает, что вы всегда делаете это в процедуре «листа» вызова, где это, вероятно, вам не поможет. Если целью является использование ECX и EBX, вы можете сделать это на сайте вызова, избегая затрат на это в процедуре листа. –
Чтобы быть справедливым, то, как один управляет сохранением/восстановлением регистров, часто является вопросом * конвенции *. И если вы не заботитесь о производительности, вы должны использовать «предпочтительное соглашение», потому что это ожидают другие читатели вашего кода (ваш проф.). Тот факт, что вы пишете рекурсивное подразделение, уже говорит нам о том, что производительность не является целью, поэтому, возможно, предпочтительное соглашение - это то, что вы хотите. OTOH, обычная причина на практике, что один пишет ассемблер для производительности, поэтому мой персональный радар всегда сфокусирован именно так. –
Да, я согласен с тем, что вы говорите, но я просто следую за тем, что мне нужно сделать для задания. – ecain