Просмотр исходного кода

Register overlap protect

git-svn-id: https://svn.inf.ethz.ch/svn/lecturers/a2/trunk@6808 8c9fc860-2736-0410-a75d-ab315db34111
felixf 9 лет назад
Родитель
Сommit
a96cb393b1
1 измененных файлов с 36 добавлено и 8 удалено
  1. 36 8
      source/FoxARMBackend.Mod

+ 36 - 8
source/FoxARMBackend.Mod

@@ -348,6 +348,7 @@ TYPE
 		toVirtual: ARRAY InstructionSet.NumberRegisters OF Ticket; (* registers real register -> none / reserved / split / blocked / virtual register (>0) *)
 		reserved: ARRAY InstructionSet.NumberRegisters OF BOOLEAN;
 		unusable: Ticket;
+		blocked: Ticket; 
 		hint: LONGINT;
 		useFPU32:BOOLEAN;
 		useFPU64:BOOLEAN;
@@ -365,6 +366,7 @@ TYPE
 				reserved[i] := FALSE
 			END;
 			NEW(unusable);
+			NEW(blocked);
 
 			(* reserve special purpose registers *)
 			toVirtual[InstructionSet.RES] := unusable; (* low part result register *)
@@ -388,17 +390,13 @@ TYPE
 			IF ~useFPU32 THEN
 				(* disable single precision VFP registers *)
 				FOR i := InstructionSet.SR0 TO InstructionSet.SR31 DO toVirtual[i] := unusable END
-			ELSE (* disable upper 16 registers, because context is not saved *)
-				FOR i := InstructionSet.SR16 TO InstructionSet.SR31 DO toVirtual[i] := unusable END
 			END;
 
 			IF ~useFPU64 THEN
 				(* disable double precision VFP registers *)
 				FOR i := InstructionSet.DR0 TO InstructionSet.DR31 DO toVirtual[i] := unusable END;
-			ELSE (* disable upper 16 registers, because context is not saved *)
-				FOR i := InstructionSet.DR16 TO InstructionSet.DR31 DO toVirtual[i] := unusable END;
 			END; 
-			
+
 		END InitPhysicalRegisters;
 
 		(** the number of physical registers **)
@@ -408,10 +406,22 @@ TYPE
 
 		(** allocate, i.e., map, a physical register to a ticket **)
 		PROCEDURE Allocate(physicalRegisterNumber: LONGINT; ticket: Ticket);
+		VAR index: LONGINT;
 		BEGIN
 			ASSERT(~ticket.spilled);
 			Assert(toVirtual[physicalRegisterNumber] = NIL,"register already allocated");
-			toVirtual[physicalRegisterNumber] := ticket
+			toVirtual[physicalRegisterNumber] := ticket;
+			(* FP register overlap: *)
+			IF (InstructionSet.SR0 <= physicalRegisterNumber) & (physicalRegisterNumber <= InstructionSet.SR31) THEN
+				index := physicalRegisterNumber - InstructionSet.SR0;
+				toVirtual[InstructionSet.DR0 + index DIV 2] := blocked;
+			ELSIF (InstructionSet.DR0 <= physicalRegisterNumber) & (physicalRegisterNumber <= InstructionSet.DR31) THEN
+				index := physicalRegisterNumber - InstructionSet.DR0;
+				IF index*2 < 32 THEN
+					toVirtual[InstructionSet.SR0 + index *2] := blocked;
+					toVirtual[InstructionSet.SR0 + index *2 + 1] := blocked;				
+				END;
+			END; 
 		END Allocate;
 
 		(** set whether a certain physical register is reserved or not **)
@@ -426,9 +436,27 @@ TYPE
 
 		(** free a certain physical register **)
 		PROCEDURE Free(physicalRegisterNumber: LONGINT);
+		VAR index: LONGINT;
 		BEGIN
 			Assert((toVirtual[physicalRegisterNumber] # NIL), "register not reserved");
-			toVirtual[physicalRegisterNumber] := NIL
+			toVirtual[physicalRegisterNumber] := NIL;
+			(* FP register overlap: *)
+			IF (InstructionSet.SR0 <= physicalRegisterNumber) & (physicalRegisterNumber <= InstructionSet.SR31) THEN
+				index := physicalRegisterNumber - InstructionSet.SR0;
+				IF ODD(index) & (toVirtual[InstructionSet.SR0+index-1] = NIL) OR
+					~ODD(index) & (toVirtual[InstructionSet.SR0+index+1] = NIL) THEN
+					ASSERT(toVirtual[InstructionSet.DR0 + index DIV 2] = blocked);
+					toVirtual[InstructionSet.DR0 + index DIV 2] := NIL;
+				END;
+			ELSIF (InstructionSet.DR0 <= physicalRegisterNumber) & (physicalRegisterNumber <= InstructionSet.DR31) THEN
+				index := physicalRegisterNumber - InstructionSet.DR0;
+				IF index*2 < 32 THEN
+					ASSERT(toVirtual[InstructionSet.SR0 + index *2]  = blocked);
+					ASSERT(toVirtual[InstructionSet.SR0 + index *2+1]  = blocked);
+					toVirtual[InstructionSet.SR0 + index *2] := NIL;
+					toVirtual[InstructionSet.SR0 + index *2 + 1] := NIL;
+				END;
+			END; 
 		END Free;
 
 		(** get the number of the next free physical register for a certain data type
@@ -490,7 +518,7 @@ TYPE
 			w.String("---- registers ----"); w.Ln;
 			FOR i := 0 TO LEN(toVirtual)-1 DO
 				virtual := toVirtual[i];
-				IF virtual # unusable THEN
+				IF (virtual # unusable) & (virtual # blocked) THEN
 					w.String("reg "); w.Int(i,1); w.String(": ");
 					IF virtual = NIL THEN w.String("free")
 					ELSE	w.String(" r"); w.Int(virtual.register,1);