- I want to use nasm language to achieve a high precision division, firstly, I have written a C file, according which to write my assembly file. It's the C file
#include <cstdio>
#include <cstring>
static const int LEN = 1004;
int a[LEN], b[LEN], c[LEN], d[LEN];
void clear(int a[])
{
for (int i = 0; i < LEN; ++i)
a[i] = 0;
}
void read(int a[])
{
static char s[LEN + 1];
int x=0;
int c=getchar();
while (c!='\n' && x<LEN-1)
{
s[x++] = c;
c = getchar();
}
s[x]='\0';
//scanf("%s", s);
clear(a);
int len = strlen(s);
for (int i = 0; i < len; ++i)
a[len - i - 1] = s[i] - '0';
}
void print(int a[])
{
int i;
for (i = LEN - 1; i >= 1; --i)
if (a[i] != 0)
break;
for (; i >= 0; --i)
putchar(a[i] + '0');
putchar('\n');
}
int greater_eq(int a[], int b[], int last_dg, int len)
{
if (a[last_dg + len] != 0){
printf("1!");
return 1;
}
for (int i = len - 1; i >= 0; --i)
{
if (a[last_dg + i] > b[i]){
printf("2!");
return 1;}
if (a[last_dg + i] < b[i]){
printf("3!");
return 0;}
}
printf("4!");
return 1;
}
void div(int a[], int b[], int c[], int d[])
{
clear(c);
clear(d);
int la, lb;
for (la = LEN - 1; la > 0; --la)
if (a[la - 1] != 0)
break;
for (lb = LEN - 1; lb > 0; --lb)
if (b[lb - 1] != 0)
break;
if (lb == 0)
{
puts("> <");
return;
}
for (int i = 0; i < la; ++i)
d[i] = a[i];
for (int i = la - lb; i >= 0; --i)
{
while (greater_eq(d, b, i, lb))
{
for (int j = 0; j < lb; ++j)
{
d[i + j] -= b[j];
if (d[i + j] < 0)
{
d[i + j + 1] -= 1;
d[i + j] += 10;
}
}
c[i] += 1;
}
}
}
int main()
{
read(a);
read(b);
div(a, b, c, d);
print(c);
print(d);
}
So, I try my best to write the nasm file, I have written the functions of reading,writing and reversing the string successfully, but some errors happened in other functions. To be specific,it's the functions geater_eq and div(ok,looks like i didn't do anything). There's no need to show successful functions,and it's my data declaratioin:
num1 times 100 db '0',0h num2 times 100 db '0',0h
Then it's the greater_eq
greater_eq:
;a[]:num1,b[]:num2,last_ag:eax,len:ebx
;return in eax
push ecx
push edx
push esi; preserve values
mov esi,num1
add esi,eax
add esi,ebx ;a[last+len]
cmp [esi],‘0’
je compare
jne greater
compare:
mov ecx,ebx ;i=len-1
dec ecx
.loop:
cmp ecx,0h
jl greater
mov esi,eax
add esi,ecx
mov edx,[num1+esi] ;a[last_eg+i]
cmp edx,[num2+ecx] ;b[i]
jg greater
jl lesser
dec ecx
jmp .loop
greater:
pop esi
pop edx
pop ecx
mov eax,1
ret
lesser:
pop esi
pop edx
pop ecx
mov eax,0
ret
I have changed a lot and still have problems, ao to function divisoin, it may occur more problems
mydiv:
mov eax,sinput
call strlen
mov ecx,eax
;la ecx
mov eax,dinput
call strlen
mov edx,eax
;lb edx
jz rerurn_diff
mov eax,sinput
mov ebx,dinput
mov esi,ecx ;i=0
sub esi,edx ;i=la-lb
div_loop:
cmp esi,0
jl return_n ; i<0结束循环
div_continue:
push eax
push ebx
mov eax,esi ;i
mov ebx,edx ;lb
call greater_eq
mov ebp,eax ;res
pop ebx
pop eax
cmp ebp,0
jne div_sub
dec esi ;i--
jmp div_loop
div_sub:
mov edi,0 ;j=0
div_sub_loop:
cmp edi,edx ;j>=lb 退出
jge div_sub_add
push ebp
mov ebp,eax
add ebp,esi
add ebp,edi; a[i+j] ->byte[eax+esi+edi]
;1
push ebx
add ebx,edi
push eax
mov ah,byte[ebp]
mov al,byte[ebx]
sub ah,al ;a[i+j] -= b[j]
mov byte[ebp],ah
pop eax
pop ebx
;2
cmp byte[ebp],0
jl div_loop_fix
div_sub_con:
pop ebp
inc edi ;j++
inc byte[c+esi] ;c[i]++
jmp div_continue
div_loop_fix:
dec byte[ebp+1]
add byte[ebp],10
jmp div_sub_con
div_sub_add:
inc byte[c+esi]
jmp div_continue
return_n:
ret
rerurn_diff:
mov eax,meg6
ret
So, nothing could be better if I can get a correct answer, I'm sure you don't want to modify my code which just like shit, and I would appreciate it if you could give me some good suggestions. (By the way, the day after tomorrow is the deadline, and I have written it for few days. I'm Chinese so please forgive me in my poor English, thanks,guys!)