Browse Source

* i386: Somewhat optimized fpc_mul_qword routine, got rid from variable 'r', registers esi and edi. Also ignore overflow checking when both operands have their high dwords equal to zero, because in such case multiplication cannot overflow.

git-svn-id: trunk@26511 -
sergei 11 years ago
parent
commit
78e726b34f
1 changed files with 17 additions and 37 deletions
  1. 17 37
      rtl/i386/int64p.inc

+ 17 - 37
rtl/i386/int64p.inc

@@ -170,7 +170,6 @@
     }
     }
     function fpc_mul_qword(f1,f2 : qword;checkoverflow : longbool) : qword;[public,alias: 'FPC_MUL_QWORD']; compilerproc;
     function fpc_mul_qword(f1,f2 : qword;checkoverflow : longbool) : qword;[public,alias: 'FPC_MUL_QWORD']; compilerproc;
       var
       var
-        r : qword;
         overflowed : boolean;
         overflowed : boolean;
       begin
       begin
         overflowed:=false;
         overflowed:=false;
@@ -179,77 +178,58 @@
         asm
         asm
            movl f1+4,%edx
            movl f1+4,%edx
            movl f2+4,%ecx
            movl f2+4,%ecx
-           cmpl $0,checkoverflow
-           jnz .Loverflowchecked
-
            orl %ecx,%edx
            orl %ecx,%edx
            movl f2,%edx
            movl f2,%edx
            movl f1,%eax
            movl f1,%eax
            jnz .Lqwordmultwomul
            jnz .Lqwordmultwomul
+           { if both upper dwords are =0 then it cannot overflow }
            mull %edx
            mull %edx
            jmp .Lqwordmulready
            jmp .Lqwordmulready
         .Lqwordmultwomul:
         .Lqwordmultwomul:
+           cmpl $0,checkoverflow
+           jnz  .Loverflowchecked
            imul f1+4,%edx
            imul f1+4,%edx
            imul %eax,%ecx
            imul %eax,%ecx
            addl %edx,%ecx
            addl %edx,%ecx
            mull f2
            mull f2
            add %ecx,%edx
            add %ecx,%edx
         .Lqwordmulready:
         .Lqwordmulready:
-           movl %eax,r
-           movl %edx,r+4
+           movl %eax,__RESULT
+           movl %edx,__RESULT+4
            jmp .Lend
            jmp .Lend
 
 
         .Loverflowchecked:
         .Loverflowchecked:
            { if both upper dwords are <>0 then it overflows always }
            { if both upper dwords are <>0 then it overflows always }
            or %ecx,%ecx
            or %ecx,%ecx
            jz .Loverok1
            jz .Loverok1
-           or %edx,%edx
+           cmpl $0,f1+4
            jnz .Loverflowed
            jnz .Loverflowed
         .Loverok1:
         .Loverok1:
            { overflow checked code }
            { overflow checked code }
-           orl %ecx,%edx
-           movl f2,%edi
-           movl f1,%esi
-           jnz .Lqwordmultwomul2
-           movl %edi,%eax
-           mull %esi
-           movl %eax,%esi
-           movl %edx,%edi
-           jmp .Lqwordmulready2
-
-        .Lqwordmultwomul2:
            movl f1+4,%eax
            movl f1+4,%eax
-           mull %edi
-           movl %eax,%edi
-           jc  .Loverflowed
-
-           movl %esi,%eax
-           mull %ecx
+           mull f2
            movl %eax,%ecx
            movl %eax,%ecx
            jc  .Loverflowed
            jc  .Loverflowed
 
 
-           addl %edi,%ecx
+           movl f1,%eax
+           mull f2+4
            jc  .Loverflowed
            jc  .Loverflowed
 
 
-           movl f2,%eax
-           mull %esi
-           movl %eax,%esi
-           movl %edx,%edi
-
-           addl %ecx,%edi
+           addl %eax,%ecx
            jc  .Loverflowed
            jc  .Loverflowed
 
 
-        .Lqwordmulready2:
-           movl %esi,r
-           movl %edi,r+4
-           jmp .Lend
+           movl f2,%eax
+           mull f1
+           addl %ecx,%edx
+           movl %eax,__RESULT
+           movl %edx,__RESULT+4
+           jnc  .Lend
 
 
         .Loverflowed:
         .Loverflowed:
            movb $1,overflowed
            movb $1,overflowed
 
 
         .Lend:
         .Lend:
-        end [ 'eax','edx','ecx','edi','esi' ];
-        fpc_mul_qword:=r;
+        end [ 'eax','edx','ecx'];
 
 
         if overflowed then
         if overflowed then
           HandleErrorFrame(215,get_frame);
           HandleErrorFrame(215,get_frame);