Browse Source

Implemented release lock upon trap in exclusive region (and raise a trap again).

A trap within (particularly within an exclusive section) is considered a programming error and leaving the object in an inconsistent state is unacceptable.
However, leaving the object in an inconsistent state AND locked is usually worse. We choose the smaller of the two evils in order to keep the system (in particular the window manager) in a potentially recoverable state. This also leaves the possibility to patch bugs in a running system.

git-svn-id: https://svn.inf.ethz.ch/svn/lecturers/a2/trunk@7639 8c9fc860-2736-0410-a75d-ab315db34111
felixf 7 years ago
parent
commit
cd19ccf638
1 changed files with 9 additions and 2 deletions
  1. 9 2
      source/FoxIntermediateBackend.Mod

+ 9 - 2
source/FoxIntermediateBackend.Mod

@@ -45,7 +45,7 @@ CONST
 		NegativeDivisorTrap*=12;
 		NoReturnTrap*=16; (* indicates that a procedure marked no return did return *)
 		NilPointerTrap*=17; (* indicates that a nil pointer was being dereferenced *)
-
+		RethrowTrap* = 18; (* rethrow exception after unlock *)
 		Trace = FALSE;
 		TraceRegisterUsageCount=TRUE;
 
@@ -10942,7 +10942,7 @@ TYPE
 		END Lock;
 
 		PROCEDURE VisitStatementBlock*(x: SyntaxTree.StatementBlock);
-		VAR previouslyUnchecked, previouslyCooperativeSwitches: BOOLEAN;
+		VAR previouslyUnchecked, previouslyCooperativeSwitches: BOOLEAN; end: Label;
 		BEGIN
 			IF Trace THEN TraceEnter("VisitStatementBlock") END;
 			IF emitLabels THEN Emit(LabelInstruction(x.position)) END;
@@ -10961,6 +10961,13 @@ TYPE
 				IF (x(SyntaxTree.Body).finally # NIL) THEN
 					section.SetFinally(section.pc);
 					StatementSequence(x(SyntaxTree.Body).finally)
+				ELSIF x.isExclusive THEN
+					end := NewLabel();
+					BrL(end);
+					section.SetFinally(section.pc);
+					Lock(FALSE);
+					EmitTrap(position,RethrowTrap);
+					SetLabel(end);
 				END;
 			END;