فهرست منبع

* optimized a_loadaddr_ref_reg() in cases where an offset is added to a
symbol or base register and the offset is a multiple of the def's size

git-svn-id: branches/hlcgllvm@27007 -

Jonas Maebe 11 سال پیش
والد
کامیت
abee66b611
1فایلهای تغییر یافته به همراه17 افزوده شده و 1 حذف شده
  1. 17 1
      compiler/llvm/hlcgllvm.pas

+ 17 - 1
compiler/llvm/hlcgllvm.pas

@@ -915,6 +915,7 @@ implementation
 
 
   function thlcgllvm.make_simple_ref(list: TAsmList; const ref: treference; def: tdef): treference;
   function thlcgllvm.make_simple_ref(list: TAsmList; const ref: treference; def: tdef): treference;
     var
     var
+      ptrindex: tcgint;
       hreg1,
       hreg1,
       hreg2: tregister;
       hreg2: tregister;
       tmpref: treference;
       tmpref: treference;
@@ -928,6 +929,22 @@ implementation
           result:=ref;
           result:=ref;
           exit;
           exit;
         end;
         end;
+
+      hreg2:=getaddressregister(list,getpointerdef(def));
+      { symbol+offset or base+offset with offset a multiple of the size ->
+        use getelementptr }
+      if (ref.index=NR_NO) and
+         (ref.offset mod def.size=0) then
+        begin
+          ptrindex:=ref.offset div def.size;
+          if assigned(ref.symbol) then
+            reference_reset_symbol(tmpref,ref.symbol,0,ref.alignment)
+          else
+            reference_reset_base(tmpref,ref.base,0,ref.alignment);
+          list.concat(taillvm.getelementptr_reg_size_ref_size_const(hreg2,getpointerdef(def),tmpref,ptruinttype,ptrindex,assigned(ref.symbol)));
+          reference_reset_base(result,hreg2,0,ref.alignment);
+          exit;
+        end;
       { for now, perform all calculations using plain pointer arithmetic. Later
       { for now, perform all calculations using plain pointer arithmetic. Later
         we can look into optimizations based on getelementptr for structured
         we can look into optimizations based on getelementptr for structured
         accesses (if only to prevent running out of virtual registers).
         accesses (if only to prevent running out of virtual registers).
@@ -963,7 +980,6 @@ implementation
           a_op_const_reg_reg(list,OP_ADD,ptruinttype,ref.offset,hreg1,hreg2);
           a_op_const_reg_reg(list,OP_ADD,ptruinttype,ref.offset,hreg1,hreg2);
           hreg1:=hreg2;
           hreg1:=hreg2;
         end;
         end;
-      hreg2:=getaddressregister(list,getpointerdef(def));
       a_load_reg_reg(list,ptruinttype,getpointerdef(def),hreg1,hreg2);
       a_load_reg_reg(list,ptruinttype,getpointerdef(def),hreg1,hreg2);
       reference_reset_base(result,hreg2,0,ref.alignment);
       reference_reset_base(result,hreg2,0,ref.alignment);
     end;
     end;