Reported by Eugene Temirgaleev
The following sample program produce a TRAP 0, because the stack does not pass the actual ANYREC parameter.
Code: Select all
MODULE PrivTest;
IMPORT Meta, Services, Log, Files;
PROCEDURE LogTypeName* (IN rec: ANYREC);
VAR name: ARRAY 256 OF CHAR;
BEGIN
Services.GetTypeName(rec, name); Log.String(name); Log.Ln
END LogTypeName;
PROCEDURE Call*;
VAR i, res: Meta.Item; par: ARRAY 10 OF Meta.Item; ok: BOOLEAN;
BEGIN
Meta.LookupPath("PrivTest.LogTypeName", i); ASSERT(i.Valid());
Meta.GetItem(Files.dir, par[0]);
i.ParamCall(par, res, ok);
END Call;
PROCEDURE LogTypeName2* (IN rec1, rec2: ANYREC);
VAR name: ARRAY 256 OF CHAR;
BEGIN
Services.GetTypeName(rec1, name); Log.String(name); Log.Ln;
Services.GetTypeName(rec2, name); Log.String(name); Log.Ln
END LogTypeName2;
PROCEDURE Call2*;
VAR i, res: Meta.Item; par: ARRAY 10 OF Meta.Item; ok: BOOLEAN;
BEGIN
Meta.LookupPath("PrivTest.LogTypeName2", i); ASSERT(i.Valid());
Meta.GetItem(Files.dir, par[0]); Meta.GetItem(Files.dir, par[1]);
i.ParamCall(par, res, ok);
END Call2;
END PrivTest. (!)PrivTest.Call (!)PrivTest.Call2
Code: Select all
PROCEDURE Call* (adr: INTEGER; sig: Signature; IN par: ARRAY OF INTEGER; n: INTEGER): LONGINT;
VAR p, kind, sp, size: INTEGER; typ: Type; r: REAL;
BEGIN
p := sig.num;
WHILE p > 0 DO (* push parameters from right to left *)
DEC(p);
typ := sig.par[p].struct;
kind := sig.par[p].id MOD 16;
IF (S.VAL(INTEGER, typ) DIV 256 = 0) OR (typ.id MOD 4 IN {0, 3}) THEN (* scalar *)
IF (kind = 10) & ((S.VAL(INTEGER, typ) = 8) OR (S.VAL(INTEGER, typ) = 10)) THEN (* 64 bit *)
DEC(n); PUSH(par[n]) (* push hi word *)
(* adding this lines here ---------------------*)
ELSIF S.VAL(INTEGER, typ) = 11 THEN (* ANYREC *)
ASSERT(kind # 10);
DEC(n); PUSH(par[n]) (* push tag *)
(* end adding --------------------------- *)
END;
DEC(n); PUSH(par[n]) (* push value/address *)
ELSIF typ.id MOD 4 = 1 THEN (* record *)
- Helmut