Browse Source

* patch by J. Gareth Moreton: handle register allocations correctly in MovMov2Mov 3, resolves #38703

git-svn-id: trunk@49128 -
florian 4 years ago
parent
commit
503fc85dff
3 changed files with 58 additions and 0 deletions
  1. 1 0
      .gitattributes
  2. 1 0
      compiler/x86/aoptx86.pas
  3. 56 0
      tests/webtbs/tw38703.pp

+ 1 - 0
.gitattributes

@@ -18773,6 +18773,7 @@ tests/webtbs/tw38642.pp svneol=native#text/pascal
 tests/webtbs/tw3865.pp svneol=native#text/plain
 tests/webtbs/tw38695.pp svneol=native#text/pascal
 tests/webtbs/tw3870.pp svneol=native#text/plain
+tests/webtbs/tw38703.pp svneol=native#text/pascal
 tests/webtbs/tw3893.pp svneol=native#text/plain
 tests/webtbs/tw3898.pp svneol=native#text/plain
 tests/webtbs/tw3899.pp svneol=native#text/plain

+ 1 - 0
compiler/x86/aoptx86.pas

@@ -2380,6 +2380,7 @@ unit aoptx86;
 
                                  mov mem, %reg"
                             }
+                            AllocRegBetween(taicpu(hp1).oper[1]^.reg,p,hp1,usedregs);
                             taicpu(p).loadreg(1, taicpu(hp1).oper[1]^.reg);
                             DebugMsg(SPeepholeOptimization + 'MovMov2Mov 3 done',p);
                             RemoveInstruction(hp1);

+ 56 - 0
tests/webtbs/tw38703.pp

@@ -0,0 +1,56 @@
+{ %opt=-O4 }
+{$mode objfpc}
+{$R+}
+program project1;
+
+const
+  MaxLoopDepth = 4;
+type
+  TES = record
+    LoopDepth: Integer;
+    Sums: array [1..MaxLoopDepth] of Double;
+  end;
+  PES = ^TES;
+  TE = class
+    ThreadStates: array of PES;
+  end;
+
+  TSF = class
+  public
+    function NI(Evaluator: TE; var a:array of Double): Double; virtual;
+  end;
+
+var
+  E: TE;
+  ES: TES;
+  D: Double;
+  SF: TSF;
+
+threadvar
+  ThreadIndex: Integer;
+
+function TSF.NI(Evaluator: TE; var a: array of Double): Double;
+begin
+  with Evaluator.ThreadStates[ThreadIndex-1]^ do begin
+    Sums[LoopDepth] := Sums[LoopDepth] + a[0];
+    Result := Sums[LoopDepth];
+  end;
+end;
+
+begin
+  ThreadIndex := 2;
+  SF := TSF.Create;
+  E := TE.Create;
+  SetLength(E.ThreadStates,2);
+  E.ThreadStates[1] := @ES;
+  ES.LoopDepth := 1;
+  ES.Sums[1] := 0;
+  D := 27;
+  SF.NI(E, D);
+  SF.NI(E, D);
+  WriteLn(ES.Sums[1]); { should write 54 }
+  if (ES.Sums[1]<53.999) or (ES.Sums[1]>54.001) then
+    halt(1);
+  writeln('ok');
+end.
+