Commit e7973c09 authored by Michael Hanus 's avatar Michael Hanus
Browse files

Implementations of PAKCS/Prolog builtins updated

parent 3a007ad8
<?xml version="1.0" standalone="no"?>
<!DOCTYPE primitives SYSTEM "http://www.informatik.uni-kiel.de/~pakcs/primitives.dtd">
<primitives>
<primitive name="prim_readGlobal" arity="1">
<library>prim_global</library>
<entry>prim_readGlobal</entry>
</primitive>
<primitive name="prim_writeGlobal" arity="2">
<library>prim_global</library>
<entry>prim_writeGlobal</entry>
</primitive>
</primitives>
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% Definitions of builtins of module Global:
%
%:- module(prim_global,
% [initGlobalValue/4, prim_readGlobal/2, prim_writeGlobal/3]).
%:- (current_module(prologbasics) -> true ; use_module('../prologbasics')).
%:- (current_module(basics) -> true ; use_module('../basics')).
%:- (current_module(prim_readshowterm) -> true ; use_module(prim_readshowterm)).
:- installDir(PH), appendAtom(PH,'/src/readShowTerm',RST), use_module(RST).
% for term reading/showing
%:- (current_module(prim_standard) -> true ; ensure_loaded(user:prim_standard)). % for waitUntilGround
% initialize the predicate containing the global value if called for the
% first time:
initGlobalValue(GlobName,'Global.Temporary',Exp,Val) :-
evalToken(Eval),
user:nf(Exp,Val,Eval,E1),
user:waitUntilGround(Val,E1,_), % groundness required
GlobalHead =.. [GlobName,_],
user:retractClause(GlobalHead,_),
NewGlobalCall =.. [GlobName,Val],
% temporary globals directly contain its value:
assertz(user:NewGlobalCall),
!.
initGlobalValue(GlobName,'Global.Persistent'(FExp),Exp,FileName) :-
evalToken(Eval),
user:nf(FExp,FileString,Eval,E0),
user:waitUntilGround(FileString,E0,E1), % groundness required
string2Atom(FileString,FileName),
user:nf(Exp,Val,E1,E2),
user:waitUntilGround(Val,E2,_), % groundness required
GlobalHead =.. [GlobName,_],
user:retractClause(GlobalHead,_),
NewGlobalCall =.. [GlobName,FileName],
% persistent globals contain the file name where its value is stored:
assertz(user:NewGlobalCall),
(existsFile(FileName) -> true ; writeGlobalFile(FileName,Val)),
!.
% read a global value:
'Global.prim_readGlobal'('Global.GlobalDef'(GlobName,'Global.Temporary'),Val) :-
GlobalCall =.. [GlobName,Val],
call(user:GlobalCall), !.
'Global.prim_readGlobal'('Global.GlobalDef'(GlobName,'Global.Persistent'),
Val) :-
GlobalCall =.. [GlobName,FileName],
call(user:GlobalCall),
readGlobalFile(FileName,Val), !.
% update a global value:
'Global.prim_writeGlobal'('Global.GlobalDef'(GlobName,'Global.Temporary'),
NewVal,'Prelude.()') :-
GlobalCall =.. [GlobName,_],
(retract(user:GlobalCall) ; user:retractClause(GlobalCall,_)),
NewGlobalCall =.. [GlobName,NewVal],
assertz(user:NewGlobalCall), !.
'Global.prim_writeGlobal'('Global.GlobalDef'(GlobName,'Global.Persistent'),
NewVal,'Prelude.()') :-
GlobalCall =.. [GlobName,FileName],
call(user:GlobalCall),
writeGlobalFile(FileName,NewVal),
!.
% read the file with the persistent global value:
readGlobalFile(FileName,Val) :-
lockFileName(FileName,LockFile),
lockWithFile(LockFile),
on_exception(ErrorMsg,
(open(FileName,read,Stream),
readStreamLine(Stream,ValString),
close(Stream)),
ValString=[]),
unlockWithFile(LockFile),
readTerm(ValString,qualified,_Rest,Val).
% write the file with the persistent global value:
writeGlobalFile(FileName,Val) :-
lockFileName(FileName,LockFile),
lockWithFile(LockFile),
(existsFile(FileName)
-> appendAtom(FileName,'.bak',BakFileName),
renameFile(FileName,BakFileName)
; true),
open(FileName,write,Stream),
show_term(Val,qualified,ValString,[]),
writeChars(Stream,ValString),
put_code(Stream,10),
% the additional characters are necessary due to a bug in
% SWI-Prolog when reading short files:
put_code(Stream,10), put_code(Stream,10), put_code(Stream,10),
close(Stream),
% make files for storing globals only accessible for the user:
appendAtom('chmod 600 ',FileName,ChmodCmd),
shellCmd(ChmodCmd),
unlockWithFile(LockFile).
% lockfile for safe file reading/writing:
lockFileName(FName,LockFile) :- appendAtom(FName,'.LOCK',LockFile).
lockWithFile(LockFile) :-
appendAtom('lockfile-create --lock-name ',LockFile,LockCmd),
((existsFile(LockFile), pakcsrc(dynamicmessages,yes))
-> writeErr('>>> Waiting for removing lock file \''),
writeErr(LockFile), writeErr('\'...'),
nlErr ; true),
shellCmd(LockCmd), !.
unlockWithFile(LockFile) :-
appendAtom('lockfile-remove --lock-name ',LockFile,LockCmd),
shellCmd(LockCmd).
<?xml version="1.0" standalone="no"?>
<!DOCTYPE primitives SYSTEM "http://www.informatik.uni-kiel.de/~pakcs/primitives.dtd">
<primitives>
<primitive name="handle_eq" arity="2">
<library>prim_io</library>
<entry>handle_eq</entry>
</primitive>
<primitive name="stdin" arity="0">
<library>prim_io</library>
<entry>prim_stdin</entry>
</primitive>
<primitive name="stdout" arity="0">
<library>prim_io</library>
<entry>prim_stdout</entry>
</primitive>
<primitive name="stderr" arity="0">
<library>prim_io</library>
<entry>prim_stderr</entry>
</primitive>
<primitive name="prim_openFile" arity="2">
<library>prim_io</library>
<entry>prim_openFile</entry>
</primitive>
<primitive name="prim_hClose" arity="1">
<library>prim_io</library>
<entry>prim_hClose</entry>
</primitive>
<primitive name="prim_hFlush" arity="1">
<library>prim_io</library>
<entry>prim_hFlush</entry>
</primitive>
<primitive name="prim_hIsEOF" arity="1">
<library>prim_io</library>
<entry>prim_hIsEOF</entry>
</primitive>
<primitive name="prim_hSeek" arity="3">
<library>prim_io</library>
<entry>prim_hSeek</entry>
</primitive>
<primitive name="prim_hWaitForInput" arity="2">
<library>prim_io</library>
<entry>prim_hWaitForInput[raw]</entry>
</primitive>
<primitive name="prim_hWaitForInputs" arity="2">
<library>prim_io</library>
<entry>prim_hWaitForInputs[raw]</entry>
</primitive>
<primitive name="prim_hWaitForInputsOrMsg" arity="2">
<library>prim_io</library>
<entry>prim_hWaitForInputsOrMsg[raw]</entry>
</primitive>
<primitive name="prim_hGetChar" arity="1">
<library>prim_io</library>
<entry>prim_hGetChar</entry>
</primitive>
<primitive name="prim_hPutChar" arity="2">
<library>prim_io</library>
<entry>prim_hPutChar</entry>
</primitive>
<primitive name="prim_hIsReadable" arity="1">
<library>prim_io</library>
<entry>prim_hIsReadable</entry>
</primitive>
<primitive name="prim_hIsWritable" arity="1">
<library>prim_io</library>
<entry>prim_hIsWritable</entry>
</primitive>
<primitive name="prim_hIsTerminalDevice" arity="1">
<library>prim_io</library>
<entry>prim_hIsTerminalDevice</entry>
</primitive>
</primitives>
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% Prolog implementation of external functions of module IO:
%
% Note: the Prolog term '$stream'('$inoutstream'(In,Out)) represents a handle
% for a stream that is both readable (on In) and writable (on Out)
% Otherwise, handles are represented by Prolog terms of the form '$stream'(N).
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%:- (current_module(prim_ports) -> true ; ensure_loaded(prim_ports)). % to implement IO.prim_hWaitForInputsOrMsg
% equality of two handles:
'IO.handle_eq'(H1,H2,B) :- (H1=H2 -> B='Prelude.True' ; B='Prelude.False').
'IO.stdin'(Stream) :- stdInputStream(Stream).
'IO.stdout'(Stream) :- stdOutputStream(Stream).
'IO.stderr'(Stream) :- stdErrorStream(Stream).
'IO.prim_openFile'(A,Mode,Stream) :-
string2Atom(A,FName),
curryFileMode2plmode(Mode,PMode),
fileOpenOptions(Options),
open(FName,PMode,Stream,Options).
curryFileMode2plmode('IO.ReadMode',read).
curryFileMode2plmode('IO.WriteMode',write).
curryFileMode2plmode('IO.AppendMode',append).
'IO.prim_hClose'('$stream'('$inoutstream'(In,Out)),'Prelude.()') :- !,
flush_output(Out),
close(Out),
(In==Out -> true ; close(In)).
'IO.prim_hClose'(Stream,'Prelude.()') :-
(isOutputStream(Stream) -> flush_output(Stream) ; true),
close(Stream).
'IO.prim_hFlush'('$stream'('$inoutstream'(_,Out)),'Prelude.()') :- !,
flush_output(Out).
'IO.prim_hFlush'(Stream,'Prelude.()') :-
(isOutputStream(Stream) -> flush_output(Stream) ; true).
'IO.prim_hIsEOF'('$stream'('$inoutstream'(In,_)),B) :- !,
(atEndOfStream(In) -> B='Prelude.True' ; B='Prelude.False').
'IO.prim_hIsEOF'(Stream,B) :-
(atEndOfStream(Stream) -> B='Prelude.True' ; B='Prelude.False').
'IO.prim_hSeek'(Handle,SeekMode,Pos,'Prelude.()') :-
currySeekMode2plmode(SeekMode,PlSM),
seek(Handle,Pos,PlSM,_).
currySeekMode2plmode('IO.AbsoluteSeek',bof).
currySeekMode2plmode('IO.RelativeSeek',current).
currySeekMode2plmode('IO.SeekFromEnd',eof).
?- block prim_hWaitForInput(?,?,?,-,?).
prim_hWaitForInput(Hdl,TO,partcall(1,exec_hWaitForInput,[TO,Hdl]),E,E).
?- block exec_hWaitForInput(?,?,?,?,-,?).
exec_hWaitForInput(RStream,RTO,World,'$io'(B),E0,E) :-
exec_hWaitForInputs([RStream],RTO,World,'$io'(N),E0,E1),
(N=0 -> B='Prelude.True' ; B='Prelude.False'),
!, E1=E.
?- block prim_hWaitForInputs(?,?,?,-,?).
prim_hWaitForInputs(H,T,partcall(1,exec_hWaitForInputs,[T,H]),E,E).
?- block exec_hWaitForInputs(?,?,?,?,-,?).
exec_hWaitForInputs(RStreams,RTO,_,'$io'(N),E0,E) :-
user:derefAll(RStreams,Streams),
selectInstreams(Streams,InStreams),
user:derefRoot(RTO,TimeOut),
waitForInputDataOnStreams(InStreams,TimeOut,N),
!, E0=E.
selectInstreams([],[]).
selectInstreams(['$stream'('$inoutstream'(In,_))|Streams],[In|InStreams]) :- !,
selectInstreams(Streams,InStreams).
selectInstreams([Stream|Streams],[Stream|InStreams]) :-
selectInstreams(Streams,InStreams).
'IO.prim_hGetChar'('$stream'('$inoutstream'(In,_)),C) :- !,
get_code(In,N), char_int(C,N).
'IO.prim_hGetChar'(Stream,C) :-
get_code(Stream,N), char_int(C,N).
'IO.prim_hPutChar'('$stream'('$inoutstream'(_,Out)),C,'Prelude.()') :- !,
char_int(C,N), put_code(Out,N).
'IO.prim_hPutChar'(Stream,C,'Prelude.()') :-
char_int(C,N), put_code(Stream,N).
'IO.prim_hIsReadable'('$stream'('$inoutstream'(_,_)),'Prelude.True') :- !.
'IO.prim_hIsReadable'(Stream,B) :-
(isInputStream(Stream) -> B='Prelude.True' ; B='Prelude.False').
'IO.prim_hIsWritable'('$stream'('$inoutstream'(_,_)),'Prelude.True') :- !.
'IO.prim_hIsWritable'(Stream,B) :-
(isOutputStream(Stream) -> B='Prelude.True' ; B='Prelude.False').
'IO.prim_hIsTerminalDevice'('$stream'('$inoutstream'(_,S)),R) :- !,
'IO.prim_hIsTerminalDevice'(S,R).
'IO.prim_hIsTerminalDevice'(Stream,B) :-
(isTerminalDeviceStream(Stream) -> B='Prelude.True'
; B='Prelude.False').
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% choice on a stream and an external port message stream:
?- block prim_hWaitForInputsOrMsg(?,?,?,-,?).
prim_hWaitForInputsOrMsg(H,M,partcall(1,exec_hWaitForInputsOrMsg,[M,H]),E,E).
?- block exec_hWaitForInputsOrMsg(?,-,?,?,?,?),
exec_hWaitForInputsOrMsg(?,?,?,?,-,?).
exec_hWaitForInputsOrMsg(Handles,share(M),World,Result,E0,E) :-
!,
get_mutable(V,M),
(V='$eval'(R) % external message stream has been already evaluated
-> E0=E, Result='$io'('Prelude.Right'(R))
; exec_hWaitForInputsOrMsg(Handles,V,World,CResult,E0,E),
(CResult='$io'('Prelude.Left'(_))
-> Result=CResult
; CResult='$io'('Prelude.Right'(S)),
(compileWithSharing(variable) -> user:propagateShare(S,TResult)
; S=TResult),
Result='$io'('Prelude.Right'(TResult)),
update_mutable('$eval'(TResult),M))).
exec_hWaitForInputsOrMsg(_,[M|Ms],_,'$io'('Prelude.Right'([M|Ms])),E0,E) :-
!, E0=E. % stream already evaluated
exec_hWaitForInputsOrMsg(RHandles,[],_,'$io'('Prelude.Left'(N)),E0,E) :- !,
% message stream is empty, so anything must be received from the handles.
user:derefAll(RHandles,Handles),
selectInstreams(Handles,InStreams),
waitForInputDataOnStreams(InStreams,-1,N),
!, E0=E.
% exec_hWaitForInputsOrMsg(Handles,'Ports.basicServerLoop'(Port),World,
% Result,E0,E) :-
% Port='Ports.internalPort'(_,_,PNr,_),
% checkIncomingPortStreams(PNr,InPortStream,OutPortStream),
% !,
% readStreamUntilEndOfTerm(InPortStream,MsgString),
% (parse_received_message(InPortStream,OutPortStream,MsgString,Msg)
% -> ifTracePort((write(user_error,'TRACEPORTS: Received message: '),
% write(user_error,Msg), nl(user_error))),
% Result='$io'('Prelude.Right'([Msg|'Ports.basicServerLoop'(Port)])), E0=E
% ; write(user_error,'ERROR: Illegal message received (ignored): '),
% putChars(user_error,MsgString), nl(user_error),
% exec_hWaitForInputsOrMsg(Handles,'Ports.basicServerLoop'(Port),World,
% Result,E0,E)),
% !.
% exec_hWaitForInputsOrMsg(RHandles,'Ports.basicServerLoop'(Port),World,Result,E0,E):-
% user:derefAll(RHandles,Handles),
% selectInstreams(Handles,InStreams),
% Port='Ports.internalPort'(_,_,PNr,Socket),
% waitForSocketOrInputStreams(Socket,Client,InPortStream,OutPortStream,
% InStreams,Index),
% (Client=no
% -> % there is input on Handles:
% Result='$io'('Prelude.Left'(Index)), E0=E
% ; % there is a client connection:
% ifTracePort((write(user_error,'TRACEPORTS: Connection to client: '),
% write(user_error,Client), nl(user_error))),
% (readPortMessage(PNr,InPortStream,OutPortStream,MsgString)
% -> (parse_received_message(InPortStream,OutPortStream,MsgString,Msg)
% -> ifTracePort((write(user_error,'TRACEPORTS: Received message: '),
% write(user_error,Msg), nl(user_error))),
% Result='$io'('Prelude.Right'([Msg|'Ports.basicServerLoop'(Port)])), E0=E
% ; write(user_error,'ERROR: Illegal message received (ignored): '),
% putChars(user_error,MsgString), nl(user_error),
% exec_hWaitForInputsOrMsg(Handles,
% 'Ports.basicServerLoop'(Port),World,Result,E0,E))
% ; % try reading next message:
% exec_hWaitForInputsOrMsg(Handles,
% 'Ports.basicServerLoop'(Port),World,Result,E0,E))),
% !.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
<?xml version="1.0" standalone="no"?>
<!DOCTYPE primitives SYSTEM "http://www.informatik.uni-kiel.de/~pakcs/primitives.dtd">
<primitives>
<primitive name="prim_execCmd" arity="1">
<library>prim_ioexts</library>
<entry>prim_execCmd</entry>
</primitive>
<primitive name="prim_connectToCmd" arity="1">
<library>prim_ioexts</library>
<entry>prim_connectToCmd</entry>
</primitive>
<primitive name="prim_setAssoc" arity="2">
<library>prim_ioexts</library>
<entry>prim_setAssoc</entry>
</primitive>
<primitive name="prim_getAssoc" arity="1">
<library>prim_ioexts</library>
<entry>prim_getAssoc</entry>
</primitive>
<primitive name="newIORef" arity="1">
<library>prim_ioexts</library>
<entry>prim_newIORef[raw]</entry>
</primitive>
<primitive name="prim_readIORef" arity="1">
<library>prim_ioexts</library>
<entry>prim_readIORef[raw]</entry>
</primitive>
<primitive name="prim_writeIORef" arity="2">
<library>prim_ioexts</library>
<entry>prim_writeIORef[raw]</entry>
</primitive>
</primitives>
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% Prolog implementation of builtins of module IOExts:
%
:- dynamic globalAssoc/2.
'IOExts.prim_setAssoc'(Key,Val,'Prelude.()') :-
string2Atom(Key,KeyA),
(retract(globalAssoc(KeyA,_)) -> true ; true),
assertz(globalAssoc(KeyA,Val)),
!.
'IOExts.prim_getAssoc'(Key,R) :-
string2Atom(Key,KeyA),
(globalAssoc(KeyA,Val) -> R='Prelude.Just'(Val) ; R='Prelude.Nothing'),
!.
% shell command execution:
'IOExts.prim_execCmd'(CmdString,'Prelude.(,,)'(StdIn,StdOut,StdErr)) :-
string2Atom(CmdString,Cmd),
execCommand(Cmd,StdIn,StdOut,StdErr).
% shell command execution:
'IOExts.prim_connectToCmd'(CmdString,'$stream'('$inoutstream'(StdOut,StdIn))) :-
string2Atom(CmdString,Cmd),
execCommand(Cmd,StdIn,StdOut,std).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% primitives implementing IORefs:
% New IORefs are represented as mutable values. The "share" constructor
% is put around to be conform with the remaining implementation where
% all mutables are "marked" by this constructor.
?- block prim_newIORef(?,?,-,?).
prim_newIORef(V,partcall(1,exec_newIORef,[V]),E,E).
?- block exec_newIORef(?,?,?,-,?).
exec_newIORef(Val,_,'$io'('IOExts.IORef'(share(MutVal))),E0,E) :-
var(Val), !,
create_mutable('$eval'(Val),MutVal), E0=E.
exec_newIORef(Val,_,'$io'('IOExts.IORef'(share(MutVal))),E0,E) :-
create_mutable(Val,MutVal), E0=E.
% When an IORef is read and its value is not evaluated, the current value
% is wrapped into a new mutable in order to implement sharing
% of evaluations of IORefs. The current IORef is updated so that
% it refers to the new mutable (without this indirection, there is
% a risk of creating cyclic structures when the IORef itself is updated).
?- block prim_readIORef(?,?,-,?).
prim_readIORef(R,partcall(1,exec_readIORef,[R]),E,E).
?- block exec_readIORef(?,?,?,-,?).
exec_readIORef(RIORef,_,'$io'(V),E0,E) :-
user:derefRoot(RIORef,'IOExts.IORef'(share(MutVal))),
get_mutable(Val,MutVal),
(Val='$eval'(V) -> true
; create_mutable(Val,MutV),
update_mutable(share(MutV),MutVal),
V=share(MutV)),
E0=E.
% Assign a new value to an IORef:
?- block prim_writeIORef(?,?,?,-,?).
prim_writeIORef(R,V,partcall(1,exec_writeIORef,[V,R]),E,E).
?- block exec_writeIORef(?,?,?,?,-,?).
exec_writeIORef(RIORef,Val,_,R,E0,E) :-
user:derefRoot(RIORef,IORef),
prim_writeIORef_exec(IORef,Val,R), E0=E.
prim_writeIORef_exec('IOExts.IORef'(share(MutVal)),Val,'$io'('Prelude.()')) :-
var(Val), !,
update_mutable('$eval'(Val),MutVal).
prim_writeIORef_exec('IOExts.IORef'(share(MutVal)),Val,'$io'('Prelude.()')) :-
update_mutable(Val,MutVal).
......@@ -2,104 +2,72 @@
<!DOCTYPE primitives SYSTEM "http://www.informatik.uni-kiel.de/~pakcs/primitives.dtd">
<primitives>
<primitive name="$!" arity="2">
<library>prim_standard</library>
<entry>prim_applySeq[raw]</entry>
</primitive>
<primitive name="$!!" arity="2">
<library>prim_standard</library>
<entry>prim_applyNormalForm[raw]</entry>
</primitive>
<primitive name="$#" arity="2">
<library>prim_standard</library>
<entry>prim_applyNotFree[raw]</entry>
</primitive>
<primitive name="$##" arity="2">
<library>prim_standard</library>
<entry>prim_applyGroundNormalForm[raw]</entry>
</primitive>
<primitive name="seq" arity="2">
<library>prim_standard</library>
<entry>prim_seq[raw]</entry>
</primitive>
<primitive name="ensureNotFree" arity="1">
<library>prim_standard</library>
<entry>prim_ensureNotFree[raw]</entry>
</primitive>
<primitive name="prim_error" arity="1">
<library>prim_standard</library>
<entry>prim_error</entry>
</primitive>
<primitive name="failed" arity="0">
<library>prim_standard</library>
<entry>prim_failed[raw]</entry>
</primitive>
<primitive name="=:=" arity="2">
<library>prim_standard</library>
<entry>constrEq[raw]</entry>
</primitive>
<primitive name="=:&lt;=" arity="2">
<library>prim_standard</library>
<entry>unifEq[raw]</entry>
</primitive>
<primitive name="=:&lt;&lt;=" arity="2">
<library>prim_standard</library>
<entry>unifEqLinear[raw]</entry>
</primitive>
<primitive name="ifVar" arity="3">
<library>prim_standard</library>
<entry>prim_ifVar[raw]</entry>
</primitive>
<primitive name="&amp;" arity="2">
<library>prim_standard</library>
<entry>prim_concurrent_and[raw]</entry>
</primitive>
<primitive name="apply" arity="2">
<library>prim_standard</library>
<entry>prim_apply[raw]</entry>
</primitive>
<primitive name="cond" arity="2">
<library>prim_standard</library>
<entry>prim_cond[raw]</entry>
</primitive>
<primitive name="letrec" arity="2">
<library>prim_standard</library>
<entry>prim_letrec[raw]</entry>
</primitive>
<primitive name="failure" arity="2">
<library>prim_standard</library>
<entry>prim_failure[raw]</entry>
</primitive>
<primitive name="&gt;&gt;=$" arity="2">
<library>prim_standard</library>
<entry>prim_Monad_bind[raw]</entry>
</primitive>
<primitive name="&gt;&gt;$" arity="2">
<library>prim_standard</library>
<entry>prim_Monad_seq[raw]</entry>
</primitive>
<primitive name="returnIO" arity="1">
<library>prim_standard</library>
<entry>prim_return[raw]</entry>
</primitive>
<primitive name="prim_readFile" arity="1">
<library>prim_standard</library>
<entry>prim_readFile</entry>
</primitive>
<primitive name="prim_readFileContents" arity="1">
<library>prim_standard</library>
<entry>prim_readFileContents[raw]</entry>
</primitive>
<primitive name="prim_writeFile" arity="2">
<library>prim_standard</library>
<entry>prim_writeFile[raw]</entry>
</primitive>
<primitive name="prim_appendFile" arity="2">
<library>prim_standard</library>
<entry>prim_appendFile[raw]</entry>
</primitive>
<primitive name="catch" arity="2">
<library>prim_standard</library>
<entry>prim_catch[raw]</entry>
</primitive>
</primitives>
This diff is collapsed.
<?xml version="1.0" standalone="no"?>
<!DOCTYPE primitives SYSTEM "http://www.informatik.uni-kiel.de/~pakcs/primitives.dtd">
<primitives>