1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798type('a,'b)t=('a,'b)evalrefand('a,'b)eval=|Doneof'b|Raiseofexn|Thunkof'atypeundo=|Nil|Cons:('a,'b)t*'a*undo->undotypelog=undorefletforcefx=match!xwith|Donex->x|Raisee->raisee|Thunke->matchfewith|y->x:=Doney;y|exceptione->x:=Raisee;raiseeletget_argx=match!xwithThunka->Somea|_->Noneletget_contentsx=match!xwith|Thunka->Either.Lefta|Doneb->Either.Rightb|Raisee->raiseeletcreatex=ref(Thunkx)letcreate_forcedy=ref(Doney)letcreate_failede=ref(Raisee)letlog()=refNilletforce_loggedlogfx=match!xwith|Donex->x|Raisee->raisee|Thunke->matchfewith|(Error_aserr:_result)->x:=Doneerr;log:=Cons(x,e,!log);err|Ok_asres->x:=Doneres;res|exceptione->x:=Raisee;raiseeletbacktracklog=letrecloop=function|Nil->()|Cons(x,e,rest)->x:=Thunke;looprestinloop!log(* For compatibility with 4.02 and 4.03 *)letis_valt=match!twith|Done_->true|Raise_|Thunk_->falseletviewt=!t(* For compatibility with 4.08 and 4.09 *)letforce_logged_408logfx=match!xwith|Donex->x|Raisee->raisee|Thunke->matchfewith|None->x:=DoneNone;log:=Cons(x,e,!log);None|Some_asy->x:=Doney;y|exceptione->x:=Raisee;raisee