(* ---------------------------------------------------------------------------- * $Id: MASLISPU.mi,v 1.3 1992/10/15 16:27:48 kredel Exp $ * ---------------------------------------------------------------------------- * This file is part of MAS. * ---------------------------------------------------------------------------- * Copyright (c) 1989 - 1992 Universitaet Passau * ---------------------------------------------------------------------------- * $Log: MASLISPU.mi,v $ * Revision 1.3 1992/10/15 16:27:48 kredel * Changed rcsid variable * * Revision 1.2 1992/02/12 17:32:24 pesch * Moved CONST definition to the right place * * Revision 1.1 1992/01/22 15:11:20 kredel * Initial revision * * ---------------------------------------------------------------------------- *) IMPLEMENTATION MODULE MASLISPU; (* MAS LISP Utility Implementation Module. *) (* Import lists and declarations. *) FROM SYSTEM IMPORT ADDRESS, ADR; FROM MASELEM IMPORT GAMMAINT; FROM MASSTOR IMPORT BETA, SIL, LIST, LENGTH, LIST1, ADV, FIRST; FROM MASERR IMPORT ERROR, harmless, severe; FROM MASBIOS IMPORT GWRITE, LISTS, BLINES, SWRITE; FROM SACLIST IMPORT FIRST3, LIST3, FIRST4, FIRST2, LIST2; FROM MASSYM2 IMPORT SYMBOL, ENTER, GET, PUT, SYMTB, STLST, SYWRIT; FROM MASSYM IMPORT UWRITE, UWRIT1, NOSHOW; CONST PIND = 0; FIND = -1; CONST rcsidi = "$Id: MASLISPU.mi,v 1.3 1992/10/15 16:27:48 kredel Exp $"; CONST copyrighti = "Copyright (c) 1989 - 1992 Universitaet Passau"; (* Procedure declarations. *) PROCEDURE CallCompiled(F, PI: LIST; VAR PO: LIST; VAR fu: BOOLEAN); (*Call compiled function or procedure. F is a function or procedure symbol. PI is the list of input parameters. fu is TRUE if F is a function and FALSE if F is a procedure. PO is a list of output parameters if F is a procedure and PO is the output parameter if F is a function. *) VAR L, PT, I, O, I1, I2, I3, I4, I5, O1, O2, O3, C: LIST; i, o: INTEGER; P: ADDRESS; F0: PROCF0; F1: PROCF1; F2: PROCF2; F3: PROCF3; F4: PROCF4; F5: PROCF5; P0: PROCP0; P1: PROCP1; P2: PROCP2; P3: PROCP3; P4: PROCP4; P5: PROCP5; P0V1: PROCP0V1; P0V2: PROCP0V2; P1V1: PROCP1V1; P1V2: PROCP1V2; P1V3: PROCP1V3; P2V1: PROCP2V1; P2V2: PROCP2V2; P2V3: PROCP2V3; P3V1: PROCP3V1; P3V2: PROCP3V2; P3V3: PROCP3V3; BEGIN (*1*) (*initialize*) fu:=FALSE; C:=GET(F,ARITY); L:=GET(F,SUBR); IF (L = SIL) OR (C <= SIL) THEN ERROR(severe,"CallCompiled: unbound compiled procedure "); UWRITE(F); RETURN END; ADV(L, PT,L); IF (L = SIL) OR (PT <> NOSHOW) THEN ERROR(severe,"CallCompiled: invalid code pointer "); UWRITE(F); RETURN END; (*2*) (*prepare parameters*) P:=ADDRESS(FIRST(L)); FIRST3(C,PT,I,O); IF LENGTH(PI) <> I THEN ERROR(severe,"CallCompiled: input parameter mismatch "); UWRITE(F); RETURN END; IF LENGTH(PO) <> O THEN ERROR(severe,"CallCompiled: output parameter mismatch "); UWRITE(F); RETURN END; i:=INTEGER(I); o:=INTEGER(O); (*3*) (*function case. *) IF PT = FIND THEN CASE i OF 0: F0:=PROCF0(P); PO:=F0(); | 1: F1:=PROCF1(P); I1:=FIRST(PI); PO:=F1(I1); | 2: F2:=PROCF2(P); FIRST2(PI,I1,I2); PO:=F2(I1,I2); | 3: F3:=PROCF3(P); FIRST3(PI,I1,I2,I3); PO:=F3(I1,I2,I3); | 4: F4:=PROCF4(P); FIRST4(PI,I1,I2,I3,I4); PO:=F4(I1,I2,I3,I4); | 5: F5:=PROCF5(P); ADV(PI, I1, PI); FIRST4(PI,I2,I3,I4,I5); PO:=F5(I1,I2,I3,I4,I5); | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; fu:=TRUE; RETURN END; (*4*) (*procedure case. *) IF PT = PIND THEN CASE i OF 0: CASE o OF 0: P0:=PROCP0(P); P0; | 1: P0V1:=PROCP0V1(P); O1:=FIRST(PO); P0V1(O1); PO:=LIST1(O1) | 2: P0V2:=PROCP0V2(P); FIRST2(PO,O1,O2); P0V2(O1,O2); PO:=LIST2(O1,O2) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; | 1: CASE o OF 0: P1:=PROCP1(P); I1:=FIRST(PI); P1(I1); | 1: P1V1:=PROCP1V1(P); I1:=FIRST(PI); O1:=FIRST(PO); P1V1(I1,O1); PO:=LIST1(O1) | 2: P1V2:=PROCP1V2(P); I1:=FIRST(PI); FIRST2(PO,O1,O2); P1V2(I1,O1,O2); PO:=LIST2(O1,O2) | 3: P1V3:=PROCP1V3(P); I1:=FIRST(PI); FIRST3(PO,O1,O2,O3); P1V3(I1,O1,O2,O3); PO:=LIST3(O1,O2,O3) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; | 2: CASE o OF 0: P2:=PROCP2(P); FIRST2(PI,I1,I2); P2(I1,I2) | 1: P2V1:=PROCP2V1(P); FIRST2(PI,I1,I2); O1:=FIRST(PO); P2V1(I1,I2,O1); PO:=LIST1(O1) | 2: P2V2:=PROCP2V2(P); FIRST2(PI,I1,I2); FIRST2(PO,O1,O2); P2V2(I1,I2,O1,O2); PO:=LIST2(O1,O2) | 3: P2V3:=PROCP2V3(P); FIRST2(PI,I1,I2); FIRST3(PO,O1,O2,O3); P2V3(I1,I2,O1,O2,O3); PO:=LIST3(O1,O2,O3) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; | 3: CASE o OF 0: P3:=PROCP3(P); FIRST3(PI,I1,I2,I3); P3(I1,I2,I3) | 1: P3V1:=PROCP3V1(P); FIRST3(PI,I1,I2,I3); O1:=FIRST(PO); P3V1(I1,I2,I3,O1); PO:=LIST1(O1) | 2: P3V2:=PROCP3V2(P); FIRST3(PI,I1,I2,I3); FIRST2(PO,O1,O2); P3V2(I1,I2,I3,O1,O2); PO:=LIST2(O1,O2) | 3: P3V3:=PROCP3V3(P); FIRST3(PI,I1,I2,I3); FIRST3(PO,O1,O2,O3); P3V3(I1,I2,I3,O1,O2,O3); PO:=LIST3(O1,O2,O3) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; | 4: CASE o OF 0: P4:=PROCP4(P); FIRST4(PI,I1,I2,I3,I4); P4(I1,I2,I3,I4) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; | 5: CASE o OF 0: P5:=PROCP5(P); ADV(PI,I1,PI); FIRST4(PI,I2,I3,I4,I5); P5(I1,I2,I3,I4,I5) | ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; ELSE ERROR(severe,"CallCompiled: unknown parameter number "); UWRITE(F) END; RETURN END; (*5*) (*not known.*) ERROR(severe,"CallCompiled: unknown procedure type "); UWRITE(F); RETURN; (*6*) END CallCompiled; PROCEDURE Compiled(P: ADDRESS; T: LIST; VAR S: ARRAY OF CHAR); (*Compiled function declaration. P is the code address of a compiled function or procedure. T is the signature of P and S is the print name of P. A symbol with name S is entered into the symbol table. *) VAR X, Y: LIST; L: GAMMAINT; BEGIN (*1*) (*intern. *) X:=ENTER(LISTS(S)); (*2*) (*arity. *) Y:=GET(X,ARITY); IF Y <> SIL THEN UWRITE(X); ERROR(harmless,"arity redefined"); END; PUT(X,ARITY,T); (*3*) (*function pointer, entry address. *) Y:=GET(X,SUBR); IF Y <> SIL THEN UWRITE(X); ERROR(harmless,"code pointer redefined"); END; L:=LIST2(NOSHOW,GAMMAINT(P)); PUT(X,SUBR,L); PUT(X,EXTYP,EXPR); (*4*) END Compiled; PROCEDURE Compiledp0(F: PROCP0; VAR S: ARRAY OF CHAR); (*Compiled function declaration p0. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,0,0); Compiled(P,TP,S); (*4*) END Compiledp0; PROCEDURE Compiledp1(F: PROCP1; VAR S: ARRAY OF CHAR); (*Compiled function declaration p1. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,1,0); Compiled(P,TP,S); (*4*) END Compiledp1; PROCEDURE Compiledp2(F: PROCP2; VAR S: ARRAY OF CHAR); (*Compiled function declaration p2. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,2,0); Compiled(P,TP,S); (*4*) END Compiledp2; PROCEDURE Compiledp3(F: PROCP3; VAR S: ARRAY OF CHAR); (*Compiled function declaration p3. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,3,0); Compiled(P,TP,S); (*4*) END Compiledp3; PROCEDURE Compiledp4(F: PROCP4; VAR S: ARRAY OF CHAR); (*Compiled function declaration p4. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,4,0); Compiled(P,TP,S); (*4*) END Compiledp4; PROCEDURE Compiledp5(F: PROCP5; VAR S: ARRAY OF CHAR); (*Compiled function declaration p5. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,5,0); Compiled(P,TP,S); (*4*) END Compiledp5; PROCEDURE Compiledf0(F: PROCF0; VAR S: ARRAY OF CHAR); (*Compiled function declaration f0. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,0,0); Compiled(P,TP,S); (*4*) END Compiledf0; PROCEDURE Compiledf1(F: PROCF1; VAR S: ARRAY OF CHAR); (*Compiled function declaration f1. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,1,0); Compiled(P,TP,S); (*4*) END Compiledf1; PROCEDURE Compiledf2(F: PROCF2; VAR S: ARRAY OF CHAR); (*Compiled function declaration f2. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,2,0); Compiled(P,TP,S); (*4*) END Compiledf2; PROCEDURE Compiledf3(F: PROCF3; VAR S: ARRAY OF CHAR); (*Compiled function declaration f3. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,3,0); Compiled(P,TP,S); (*4*) END Compiledf3; PROCEDURE Compiledf4(F: PROCF4; VAR S: ARRAY OF CHAR); (*Compiled function declaration f4. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,4,0); Compiled(P,TP,S); (*4*) END Compiledf4; PROCEDURE Compiledf5(F: PROCF5; VAR S: ARRAY OF CHAR); (*Compiled function declaration f5. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(FIND,5,0); Compiled(P,TP,S); (*4*) END Compiledf5; PROCEDURE Compiledp1v2(F: PROCP1V2; VAR S: ARRAY OF CHAR); (*Compiled function declaration p1v2. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,1,2); Compiled(P,TP,S); (*4*) END Compiledp1v2; PROCEDURE Compiledp1v3(F: PROCP1V3; VAR S: ARRAY OF CHAR); (*Compiled function declaration p1v3. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,1,3); Compiled(P,TP,S); (*4*) END Compiledp1v3; PROCEDURE Compiledp2v2(F: PROCP2V2; VAR S: ARRAY OF CHAR); (*Compiled function declaration p2v2. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,2,2); Compiled(P,TP,S); (*4*) END Compiledp2v2; PROCEDURE Compiledp2v3(F: PROCP2V3; VAR S: ARRAY OF CHAR); (*Compiled function declaration p2v3. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,2,3); Compiled(P,TP,S); (*4*) END Compiledp2v3; PROCEDURE Compiledp3v2(F: PROCP3V2; VAR S: ARRAY OF CHAR); (*Compiled function declaration p3v2. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,3,2); Compiled(P,TP,S); (*4*) END Compiledp3v2; PROCEDURE Compiledp3v3(F: PROCP3V3; VAR S: ARRAY OF CHAR); (*Compiled function declaration p3v3. F is a Modula-2 procedure, S is the print name of F. *) VAR TP: LIST; P: ADDRESS; BEGIN (*1*) (*function pointer. *) P:=ADDRESS(F); (*2*) (*declare. *) TP:=LIST3(PIND,3,3); Compiled(P,TP,S); (*4*) END Compiledp3v3; PROCEDURE CompSummary; (*Compiled function and procedure summary. Write out all compiled functions with their signature from symbol table SYMTB. *) VAR X, V, W, k, i, o: LIST; p, f: INTEGER; BEGIN (*1*) (*initialize. *) p:=0; f:=0; SWRITE("List of all compiled functions and procedures: "); BLINES(1); X:=STLST(SYMTB); (*2*) (*loop on symbol list. *) WHILE X <> SIL DO ADV(X,V,X); W:=GET(V,ARITY); IF W <> SIL THEN FIRST3(W, k,i,o); IF k = PIND THEN p:=p+1; SWRITE("PROCEDURE "); SYWRIT(V); IF i + o > 0 THEN SWRITE("("); WHILE i > 0 DO i:=i-1; SWRITE("LIST"); IF i > 0 THEN SWRITE(",") END; END; IF o > 0 THEN SWRITE("; ") END; WHILE o > 0 DO o:=o-1; SWRITE("LIST"); IF o > 0 THEN SWRITE(",") END; END; SWRITE(")") END ELSIF k = FIND THEN f:=f+1; SWRITE("FUNCTION "); SYWRIT(V); SWRITE("("); WHILE i > 0 DO i:=i-1; SWRITE("LIST"); IF i > 0 THEN SWRITE(",") END; END; IF o > 0 THEN SWRITE("; ") END; WHILE o > 0 DO o:=o-1; SWRITE("LIST"); IF o > 0 THEN SWRITE(",") END; END; SWRITE("): LIST") ELSE UWRIT1(W) END; BLINES(0); END; END; (*3*) (*summary. *) BLINES(1); GWRITE(GAMMAINT(f)); SWRITE(" functions and "); GWRITE(GAMMAINT(p)); SWRITE(" procedures accessible."); BLINES(0); (*9*) END CompSummary; PROCEDURE Declare(VAR X: LIST; VAR S: ARRAY OF CHAR); (*Declare. X is declared as symbol with print name S. *) BEGIN (*1*) (*intern. *) X:=ENTER(LISTS(S)); (*2*) END Declare; PROCEDURE PROCP(X: LIST): BOOLEAN; (*Procedure Pointer. Test if the symbol X is a compiled function. *) BEGIN (*1*) (*symbol. *) IF NOT SYMBOL(X) THEN RETURN(FALSE) END; (*2*) (*function pointer, entry address. *) IF GET(X,ARITY) <> SIL THEN RETURN(TRUE) END; RETURN(FALSE); (*4*) END PROCP; PROCEDURE Signature(F: LIST; VAR PI, PO: LIST; VAR def: BOOLEAN); (*Signature of a compiled function or procedure. F is a function or procedure symbol. PI is the number of input parameters. def is TRUE if F is defined as compiled function or procedure else def is FALSE. PO is the number of output parameters if F is a procedure, PO = -1 if F is a function. *) VAR L, C, PT: LIST; BEGIN (*1*) (*initialize*) PI:=0; PO:=0; def:=FALSE; C:=GET(F,ARITY); L:=GET(F,SUBR); IF (L = SIL) OR (C <= SIL) THEN RETURN END; def:=TRUE; (*2*) (*prepare parameters*) FIRST3(C,PT,PI,PO); IF PT = FIND THEN PO:=-1 END; (*3*) END Signature; (* Execution part. *) BEGIN Declare(EXTYP,"EXTYP"); Declare(ARITY,"ARITY"); Declare(SUBR,"SUBR"); END MASLISPU. (* -EOF- *)