瀏覽代碼

* optimized ansistring compare with ''
* fixed 852

florian 25 年之前
父節點
當前提交
190ba4c78c
共有 2 個文件被更改,包括 90 次插入33 次删除
  1. 71 30
      compiler/cg386add.pas
  2. 19 3
      compiler/htypechk.pas

+ 71 - 30
compiler/cg386add.pas

@@ -189,35 +189,72 @@ implementation
                    equaln,unequaln:
                      begin
                         cmpop:=true;
-                        secondpass(p^.left);
-                        pushed:=maybe_push(p^.right^.registers32,p^.left,false);
-                        secondpass(p^.right);
-                        if pushed then
-                          restore(p^.left,false);
-                        { release used registers }
-                        del_location(p^.right^.location);
-                        del_location(p^.left^.location);
-                        { push the still used registers }
-                        pushusedregisters(pushedregs,$ff);
-                        { push data }
-                        case p^.right^.location.loc of
-                          LOC_REFERENCE,LOC_MEM:
-                            emit_push_mem(p^.right^.location.reference);
-                          LOC_REGISTER,LOC_CREGISTER:
-                            emit_reg(A_PUSH,S_L,p^.right^.location.register);
-                        end;
-                        case p^.left^.location.loc of
-                          LOC_REFERENCE,LOC_MEM:
-                            emit_push_mem(p^.left^.location.reference);
-                          LOC_REGISTER,LOC_CREGISTER:
-                            emit_reg(A_PUSH,S_L,p^.left^.location.register);
-                        end;
-                        emitcall('FPC_ANSISTR_COMPARE');
-                        emit_reg_reg(A_OR,S_L,R_EAX,R_EAX);
-                        popusedregisters(pushedregs);
-                        maybe_loadesi;
-                        ungetiftempansi(p^.left^.location.reference);
-                        ungetiftempansi(p^.right^.location.reference);
+                        if (p^.treetype in [equaln,unequaln]) and
+                           (p^.left^.treetype=stringconstn) and
+                           (p^.left^.length=0) then
+                          begin
+                             secondpass(p^.right);
+                             { release used registers }
+                             del_location(p^.right^.location);
+                             del_location(p^.left^.location);
+                             case p^.right^.location.loc of
+                               LOC_REFERENCE,LOC_MEM:
+                                 emit_const_ref(A_CMP,S_L,0,newreference(p^.right^.location.reference));
+                               LOC_REGISTER,LOC_CREGISTER:
+                                 emit_const_reg(A_CMP,S_L,0,p^.right^.location.register);
+                             end;
+                             ungetiftempansi(p^.left^.location.reference);
+                             ungetiftempansi(p^.right^.location.reference);
+                          end
+                        else if (p^.treetype in [equaln,unequaln]) and
+                          (p^.right^.treetype=stringconstn) and
+                          (p^.right^.length=0) then
+                          begin
+                             secondpass(p^.left);
+                             { release used registers }
+                             del_location(p^.right^.location);
+                             del_location(p^.left^.location);
+                             case p^.right^.location.loc of
+                               LOC_REFERENCE,LOC_MEM:
+                                 emit_const_ref(A_CMP,S_L,0,newreference(p^.left^.location.reference));
+                               LOC_REGISTER,LOC_CREGISTER:
+                                 emit_const_reg(A_CMP,S_L,0,p^.left^.location.register);
+                             end;
+                             ungetiftempansi(p^.left^.location.reference);
+                             ungetiftempansi(p^.right^.location.reference);
+                          end
+                        else
+                          begin
+                             secondpass(p^.left);
+                             pushed:=maybe_push(p^.right^.registers32,p^.left,false);
+                             secondpass(p^.right);
+                             if pushed then
+                               restore(p^.left,false);
+                             { release used registers }
+                             del_location(p^.right^.location);
+                             del_location(p^.left^.location);
+                             { push the still used registers }
+                             pushusedregisters(pushedregs,$ff);
+                             { push data }
+                             case p^.right^.location.loc of
+                               LOC_REFERENCE,LOC_MEM:
+                                 emit_push_mem(p^.right^.location.reference);
+                               LOC_REGISTER,LOC_CREGISTER:
+                                 emit_reg(A_PUSH,S_L,p^.right^.location.register);
+                             end;
+                             case p^.left^.location.loc of
+                               LOC_REFERENCE,LOC_MEM:
+                                 emit_push_mem(p^.left^.location.reference);
+                               LOC_REGISTER,LOC_CREGISTER:
+                                 emit_reg(A_PUSH,S_L,p^.left^.location.register);
+                             end;
+                             emitcall('FPC_ANSISTR_COMPARE');
+                             emit_reg_reg(A_OR,S_L,R_EAX,R_EAX);
+                             popusedregisters(pushedregs);
+                             maybe_loadesi;
+                             ungetiftempansi(p^.left^.location.reference);
+                             ungetiftempansi(p^.right^.location.reference);
+                          end;
                      end;
                 end;
                { the result of ansicompare is signed }
@@ -2240,7 +2277,11 @@ implementation
 end.
 {
   $Log$
-  Revision 1.94  2000-02-14 22:34:28  florian
+  Revision 1.95  2000-02-18 16:13:28  florian
+    * optimized ansistring compare with ''
+    * fixed 852
+
+  Revision 1.94  2000/02/14 22:34:28  florian
     * fixed another internalerror
 
   Revision 1.93  2000/02/09 13:22:45  peter

+ 19 - 3
compiler/htypechk.pas

@@ -63,7 +63,7 @@ implementation
        globtype,systems,tokens,
        cobjects,verbose,globals,
        symconst,
-       types,pass_1,
+       types,pass_1,cpubase,
 {$ifdef newcg}
        cgbase
 {$else}
@@ -595,6 +595,18 @@ implementation
               if (abs(p^.left^.registersmmx-p^.right^.registersmmx)<mmx) then
                inc(p^.registersmmx,mmx);
 {$endif SUPPORT_MMX}
+              { the following is a little bit guessing but I think }
+              { it's the only way to solve same internalerrors:    }
+              { if the left and right node both uses registers     }
+              { and return a mem location, but the current node    }
+              { doesn't use an integer register we get probably    }
+              { trouble when restoring a node                      }
+              if (p^.left^.registers32=p^.right^.registers32) and
+                 (p^.registers32=p^.left^.registers32) and
+                 (p^.registers32>0) and
+                (p^.left^.location.loc in [LOC_REFERENCE,LOC_MEM]) and
+                (p^.right^.location.loc in [LOC_REFERENCE,LOC_MEM]) then
+                inc(p^.registers32);
             end
            else
             begin
@@ -889,7 +901,11 @@ implementation
 end.
 {
   $Log$
-  Revision 1.58  2000-02-09 13:22:53  peter
+  Revision 1.59  2000-02-18 16:13:29  florian
+    * optimized ansistring compare with ''
+    * fixed 852
+
+  Revision 1.58  2000/02/09 13:22:53  peter
     * log truncated
 
   Revision 1.57  2000/02/05 12:11:50  peter
@@ -963,4 +979,4 @@ end.
     * arrayconstructor -> arrayofconst fixed when arraycosntructor was not
       variant.
 
-}
+}