Write 80387 ALP to find the roots of the quadratic equation.

Second Year Computer Engineering Microprocessor Programs:

Microprocessor Lab:

Practical 10:
Write 80387 ALP to find the roots of the quadratic equation. All the possible cases must be considered in calculating the roots:

Create three files :
1.Quad.asm 2.Rootmain.c 3.root.asm
----------------------------------------------------------------------------------------------------------------------------------
;quad.asm

section .data
msg1 db "Complex Root",10
msglen1 equ $-msg1

msg2 db "Root1: "
msglen2 equ $-msg2

msg3 db "Root2: "
msglen3 equ $-msg3

a dd 1.00
b dd -6.00
c dd 8.00
four dd 4.00
two dd 2.00

hdec dq 100
point db "."

section .bss

root1 resd 1
root2 resd 1
resbuff rest 1
temp resb 2
disc resd 1

%macro write 2 ;macro for display
mov rax,1
mov rdi,1
mov rsi,%1
mov rdx,%2
syscall
%endmacro

%macro read 2 ;macro for input
mov rax,0
mov rdi,0
mov rsi,%1
mov rdx,%2
syscall
%endmacro

%macro exit 0 ;macro for exit
mov rax,60
xor rdi,rdi
syscall
%endmacro

section .text
  global _start
  _start:

  finit ; initialise 80387 co-processor
  fld dword[b] ; stack: b

 
   
  fmul dword[b] ; stack: b*b

  fld dword[a] ; stack: a, b*b

  fmul dword[c] ; stack: a*c, b*b

  fmul dword[four] ; stack: 4*a*c,b*b

  fsub ; stack: b*b - 4*a*c

  ftst ; compares ST0 and 0
 
  fsqrt ; stack: sqrt(b*b - 4*a*c)
  fst dword[disc] ; store disc= sqrt(b*b - 4*a*c)

  fsub dword[b] ; stack: disc-b

  fdiv dword[a] ; stack: disc-b/2*a or (-b+disc)/2a


  fdiv dword[two]

  write msg2,msglen2

  call disp_proc

  fldz ;stack:0
  fsub dword[disc] ;stack:-disc
  fsub dword[b] ; stack: -disc - b
  fdiv dword[a] ; stack: (-b - disc)/(2*a)
  fdiv dword[two]

  write msg3,msglen3
  call disp_proc
  jmp exi

no_real_solutions:
write msg1,msglen1
exi :

mov rax,60
mov rdi,1
syscall
 

disp_proc:
FIMUL dword[hdec]
FBSTP tword[resbuff]
mov rsi,resbuff+9
mov rcx,09
  next1:
 
  push rcx
  push rsi
 
  mov bl,[rsi]
  call disp
 
  pop rsi
  pop rcx
 
    dec rsi
  loop next1

    push rsi
  write point,1
    pop rsi
  mov bl,[rsi]
  call disp
    ret


disp:
    mov rdi,temp ;mov dnum address into edi
    mov rcx,02 ;initialize ecx with 2
    dispup1:
       rol bl,4 ;rotate bl by 4 bits
            mov dl,bl ;move bl into dl
            and dl,0fh ;and of dl with 0fh
            add dl,30h ;add 30h into dl
            cmp dl,39h ;compare dl with 39h
            jbe dispskip1 ;jump if below and equal to dispskip1
            add dl,07h ;add 7h into dl
            dispskip1:
                mov [rdi],dl ;mov dl into dnum
                inc rdi ;increament edi by a byte
            loop dispup1 ;loop dispup1 while ecx not zero
            write temp,2 ;Display dnum by calling macro
          ret ;return from procedure

******************************************************************************************************************************************************************************
// rootsc.c
#include <stdio.h>

int main(void)
{
        double a,b,c,root1,root2;
        extern int _roots(double,double,double,double*,double*);
        printf("Enter coefficients: ");
        scanf("%lf %lf %lf",&a,&b,&c);
        if(_roots(a,b,c,&root1,&root2))
                printf("Root1 = %lf and root2 = %lf\n", root1, root2);
        else
                printf("Root1 = %lfi and root2 = %lfi\n", root1, root2);
        return 0;
}

******************************************************************************************************************************************************************************
;roots.asm

    ; roots.asm
segment .text
global  _roots

_roots:
        enter   0,0
        xor     EAX,EAX
        fld     qword[EBP+8]            ; a
        fadd    ST0                     ; 2a
        fld     qword[EBP+8]            ; a,2a
        fld     qword[EBP+24]           ; c,a,2a
        fmulp   ST1                     ; ac,2a
        fadd    ST0                     ; 2ac,2a
        fadd    st0                     ; 4ac,2a
        fchs                            ; -4ac,2a
        fld     qword[EBP+16]           ; b,-4ac,2a
        fld     qword[EBP+16]           ; b,b,-4ac,2a
        fmulp   ST1                     ; b*b,-4ac,2a
        faddp   ST1                     ; b*b-4ac,2a
        ftst                            ; cmp (b*b-4ac),0
        fstsw   AX                      ; result of test in AX
        sahf                            ; store AH in flag reg
        jb      no_real_roots           ; jb tests the carry flag
        fsqrt                           ; sqrt(b*b-4ac),2a
        fld     qword[EBP+16]           ; b,sqrt(b*b-4ac),2a
        fchs                            ; -b,sqrt(b*b-4ac),2a
        fadd    ST1                     ; -b+sqrt(b*b-4ac),sqrt(b*b-4ac),2a
        fdiv    ST2                     ; -b+sqrt(b*b-4ac)/2a,sqrt(b*b-4ac),2a
        mov     EAX,dword[EBP+32]       ; EAX = -b+sqrt(b*b-4ac)/2a
        fstp    qword[EAX]              ; Store and pop
        fchs                            ; -sqrt(b*b-4ac),2a
        fld     qword[EBP+16]           ; b,-sqrt(b*b-4ac),2a
        fchs                            ; -b,-sqrt(b*b-4ac),2a
        faddp   ST1                     ; -b-sqrt(b*b-4ac),2a
        fdivrp  ST1                     ; -b-sqrt(b*b-4ac)/2a
        mov     EAX,dword[EBP+36]       ; EAX = -b-sqrt(b*b-4ac)/2a
        fstp    qword[EAX]              ; Store and pop
        mov     EAX,1                   ; 1 means real roots
        jmp     short done
no_real_roots:
        fchs                            ; Make b*b-4ac positive
        fsqrt                           ; sqrt(b*b-4ac),2a
        fld     qword[EBP+16]           ; b,sqrt(b*b-4ac),2a
        fchs                            ; -b,sqrt(b*b-4ac),2a
        fadd    ST1                     ; -b+sqrt(b*b-4ac),sqrt(b*b-4ac),2a
        fdiv    ST2                     ; -b+sqrt(b*b-4ac)/2a,sqrt(b*b-4ac),2a
        mov     EAX,dword[EBP+32]       ; EAX = -b+sqrt(b*b-4ac)/2a
        fstp    qword[EAX]              ; Store and pop
        fchs                            ; -sqrt(b*b-4ac),2a
        fld     qword[EBP+16]           ; b,-sqrt(b*b-4ac),2a
        fchs                            ; -b,-sqrt(b*b-4ac),2a
        faddp   ST1                     ; -b-sqrt(b*b-4ac),2a
        fdivrp  ST1                     ; -b-sqrt(b*b-4ac)/2a
        mov     EAX,dword[EBP+36]       ; EAX = -b-sqrt(b*b-4ac)/2a
        fstp    qword[EAX]              ; Store and pop
        sub     EAX,EAX                 ; 0 means no real roots
done:
        leave
        ret

----------------------------------------------------------------------------------------------------------------------------------
output:
      ;gcc -c -m32 rootsc.c
      ;nasm -f elf -g -F stabs -o roots.o roots.asm
      ;gcc -m32 rootsc.o roots.o -o roots



Comments

Popular posts from this blog

Write C++ program to maintain club member‘s information using singly linked list. Store student PRN and Name.

Implement C++ program for expression conversion as infix to postfix and its evaluation using stack.

Write C++ program for simulating job queue. Write functions to add job and delete job from queue.