示例#1
0
        public static SObject findCode(string module, string ns, int id, int number)
        {
            // First look in programAssembly

            CodeVector cv = findCodeInAssembly(Reg.programAssembly, ns, number);

            if (cv != null)
            {
                return(cv);
            }

            // Then look in external Assembly via module in name

            Assembly moduleAssembly;

            try {
                moduleAssembly = Assembly.LoadFrom(module + ".exe");
            }
            catch {
                try {
                    moduleAssembly = Assembly.LoadFrom(module + ".dll");
                }
                catch {
                    Exn.error("code not found (no EXE or DLL file): " + module);
                    return(Factory.Impossible);
                }
            }
            cv = findCodeInAssembly(moduleAssembly, ns, number);
            if (cv != null)
            {
                return(cv);
            }
            Exn.error("code not found: " + module + " " + ns + " " + number);
            return(Factory.False);
        }
示例#2
0
        public static Procedure getSupportProcedure(int index)
        {
            SObject support = Reg.globalValue("millicode-support");

            if (support is SVL)
            {
                SVL       procedures = (SVL)support;
                Procedure p          = procedures.elementAt(index) as Procedure;
                if (p != null)
                {
                    return(p);
                }
                else
                {
                    Exn.internalError("millicode support " + index + " not a procedure");
                    return(null);
                }
            }
            else if (support == Factory.Undefined)
            {
                Exn.internalError("millicode-support is not defined (index: " + index + ")");
                return(null);
            }
            else
            {
                Exn.internalError("millicode-support is not a vector");
                return(null);
            }
        }
示例#3
0
 public static void op1_round(SObject arg)
 {
     if (arg is SFixnum)
     {
         return;
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
         if (a.tag == Tags.RatnumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_RATNUM_ROUND, arg);
             return;
         }
     }
     else if (arg is SByteVL)
     {
         SByteVL a = (SByteVL)arg;
         if (a.tag == Tags.FlonumTag)
         {
             double d = a.unsafeAsDouble(0);
             Reg.Result = Factory.makeFlonum(System.Math.Round(d));
             return;
         }
         else if (a.tag == Tags.BignumTag)
         {
             return;
         }
     }
     Exn.fault(Constants.EX_ROUND, "round: expected real number");
 }
示例#4
0
        /* ===================================================== */
        /*   Utility                                             */
        /* ===================================================== */

        public static void expect1(bool b, SObject arg, int blame)
        {
            if (!b)
            {
                Exn.fault(blame, "bad argument: " + arg, arg);
            }
        }
示例#5
0
        // return new stream position,
        // -1 on error
        public static long LSeek(int fd, long offset, int whence_code)
        {
            SeekOrigin whence = SeekOrigin.Begin;

            if (whence_code == 0)
            {
                whence = SeekOrigin.Begin;
            }
            else if (whence_code == 1)
            {
                whence = SeekOrigin.Current;
            }
            else if (whence_code == 2)
            {
                whence = SeekOrigin.End;
            }
            else
            {
                Exn.fault(Constants.EX_ASSERT, "bad whence_code for lseek");
            }
            try {
                return(fd2stream(fd).Seek(offset, whence));
            } catch (Exception) {
                return(-1);
            }
        }
示例#6
0
        public static SObject op2_procedure_ref(SObject arg1, SObject arg2)
        {
            expect2(arg1.isProcedure(), arg1, arg2.isFixnum(), arg2, Constants.EX_PROCEDURE_REF);
            Procedure p = (Procedure)arg1;
            int       b = ((SFixnum)arg2).value;

            if (b == 0)
            {
                // Code vector
                return(p.getCode());
            }
            else if (b == 1)
            {
                // Constant vector
                return(p.constantvector);
            }
            else if (b > 1)
            {
                b = b - 2;
                if (b < p.rib.Length)
                {
                    return(p.rib[b]);
                }
            }
            Exn.fault(Constants.EX_PROCEDURE_REF, "procedure-ref: bad index", arg1, arg2);
            return(null);
        }
示例#7
0
 public static SObject op1_imag_part(SObject arg)
 {
     if (arg is SFixnum)
     {
         return(Factory.makeFixnum(0));
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
         if (a.tag == Tags.BignumTag
             | a.tag == Tags.RatnumTag)
         {
             return(Factory.makeFixnum(0));
         }
         else if (a.tag == Tags.RectnumTag)
         {
             return(Number.rectImagPart(a));
         }
     }
     else if (arg is SByteVL)
     {
         SByteVL a = (SByteVL)arg;
         if (a.tag == Tags.FlonumTag)
         {
             return(Factory.makeFixnum(0));
         }
         else if (a.tag == Tags.CompnumTag)
         {
             return(Number.compImagPart(a));
         }
     }
     Exn.fault(Constants.EX_IMAGPART,
               "not a number");
     return(Factory.Unspecified);
 }
示例#8
0
文件: Exn.cs 项目: zen3d/larceny
 public static CodeAddress fault(int blame, string m,
                                 SObject arg1, SObject arg2, SObject arg3)
 {
     Reg.Result = arg1;
     Reg.Second = arg2;
     Reg.Third  = arg3;
     return(Exn.fault(blame, m));
 }
示例#9
0
 public void checkPop(int lastslot, Procedure reg0)
 {
     if (this.lastslot != lastslot)
     {
         Exn.internalError("pop: wrong number of slots");
     }
     if (this.s0.entrypoint != reg0.entrypoint)
     {
         Exn.internalError("pop: can't pop someone else's frame!");
     }
 }
示例#10
0
        public static SObject op1_fxnegative(SObject arg)
        {
            expect1(arg.isFixnum(), arg, Constants.EX_FXNEG);
            int a = ((SFixnum)arg).value;

            if (!SFixnum.inFixnumRange(-a))
            {
                Exn.fault(Constants.EX_FXNEG, "result not a fixnum", arg);
            }
            return(Factory.makeNumber(-a));
        }
示例#11
0
 public static void ffi_syscall()
 {
     try
     {
         SObject scode = Reg.Register2;
         ffi_syscall_main(((SFixnum)scode).value);
     }
     catch (Exception e)
     {
         Exn.error("exception in ffi: " + e.ToString());
     }
 }
示例#12
0
        public static void op2_greater_or_equal(SObject arg1, SObject arg2)
        {
            if (arg1 is SFixnum & arg2 is SFixnum)
            {
                bool result =
                    ((SFixnum)arg1).value >= ((SFixnum)arg2).value;
                Reg.Result = Factory.makeBoolean(result);
                return;
            }
            else if (arg1 is SVL & arg2 is SVL)
            {
                SVL a = (SVL)arg1;
                SVL b = (SVL)arg2;
                if (a.tag == Tags.RatnumTag & b.tag == Tags.RatnumTag)
                {
                    Call.callMillicodeSupport2(Constants.MS_RATNUM_GREATEREQ, a, b);
                    return; // TAIL CALL
                }
                else if (a.tag == Tags.RectnumTag & b.tag == Tags.RectnumTag)
                {
                    Exn.fault(Constants.EX_GREATEREQP, ">= cannot compare rectnums");
                    return; // TAIL CALL
                }
            }
            else if (arg1 is SByteVL & arg2 is SByteVL)
            {
                SByteVL a = (SByteVL)arg1;
                SByteVL b = (SByteVL)arg2;
                if (a.tag == Tags.BignumTag & b.tag == Tags.BignumTag)
                {
                    Call.callMillicodeSupport2(Constants.MS_BIGNUM_GREATEREQ, a, b);
                    return; // TAIL CALL
                }
                else if (a.tag == Tags.FlonumTag & b.tag == Tags.FlonumTag)
                {
                    double av = a.unsafeAsDouble(0);
                    double bv = b.unsafeAsDouble(0);
                    Reg.Result = Factory.makeBoolean(av >= bv);
                    return;
                }
                else if (a.tag == Tags.CompnumTag & b.tag == Tags.CompnumTag)
                {
                    Exn.fault(Constants.EX_GREATEREQP, ">= cannot compare compnums");
                    return;
                }
            }
            Procedure generic
                = Call.getSupportProcedure(Constants.MS_GENERIC_GREATEREQ);

            Call.pcontagion(arg1, arg2, generic);
            return; // TAIL CALL
        }
示例#13
0
 public static void op1_disable_interrupts(SObject arg)
 {
     if (Reg.interruptsEnabled)
     {
         Reg.interruptsEnabled = false;
         Reg.Result            = Factory.makeFixnum((int)Reg.timer);
     }
     else
     {
         Reg.Result = Factory.makeBoolean(false);
     }
     Exn.checkSignals();
 }
示例#14
0
        public static SObject op2_fxmul(SObject arg1, SObject arg2)
        {
            expect2(arg1.isFixnum(), arg1, arg2.isFixnum(), arg2, Constants.EX_FXMUL);
            int a = ((SFixnum)arg1).value;
            int b = ((SFixnum)arg2).value;
            int c = a * b;

            if (!SFixnum.inFixnumRange(c))
            {
                Exn.fault(Constants.EX_FXMUL, "result not a fixnum", arg1, arg2);
            }
            return(Factory.makeNumber(c));
        }
示例#15
0
        public static void rangeCheckVL(SObject arg1, SObject arg2, SObject arg3, int blame)
        {
            SVL bv    = (SVL)arg1;
            int index = ((SFixnum)arg2).value;

            if (index >= 0 && index < bv.elements.Length)
            {
            }
            else
            {
                Exn.fault(blame, "index out of range", arg1, arg2, arg3);
            }
        }
示例#16
0
 public static void expect2(bool b1, SObject arg1,
                            bool b2, SObject arg2,
                            int blame)
 {
     if (!b1)
     {
         Exn.fault(blame, "bad argument 1: " + arg1, arg1, arg2);
     }
     if (!b2)
     {
         Exn.fault(blame, "bad argument 2: " + arg2, arg1, arg2);
     }
 }
示例#17
0
        private static Stream fd2output(int fd)
        {
            Stream s = fd2stream(fd);

            if (s == null || !s.CanWrite)
            {
                Exn.internalError("file descriptor " + fd + " not open for output");
                return(null);
            }
            else
            {
                return(s);
            }
        }
示例#18
0
        private static Stream fd2stream(int fd)
        {
            object s = open_files[fd];

            if (s is Stream)
            {
                return((Stream)s);
            }
            else
            {
                Exn.internalError("fd " + fd + " is not a stream: " + s);
                return(null);
            }
        }
示例#19
0
 private static object unwrapF(SObject s)
 {
     if (s is SFixnum)
     {
         return(((SFixnum)s).value);
     }
     else if (s is ForeignBox)
     {
         return(((ForeignBox)s).value);
     }
     else
     {
         Exn.error("cannot unwrap foreign argument");
         return(Factory.Impossible);
     }
 }
示例#20
0
        // Combines the effect of checkpop and pop.
        public void SafePop(int lastslot)
        {
            if (this.lastslot != lastslot)
            {
                Exn.internalError("pop: wrong number of slots.  Expected "
                                  + lastslot.ToString()
                                  + ", got "
                                  + this.lastslot.ToString());
            }

            if (this.s0.entrypoint != Reg.ProcRegister0.entrypoint)
            {
                Exn.internalError("pop: can't pop someone else's frame!");
            }

            Cont.pop();
        }
示例#21
0
 public static void op1_negative(SObject arg)
 {
     if (arg is SFixnum)
     {
         int a = ((SFixnum)arg).value;
         Reg.Result = Factory.makeNumber(-a);
         return;
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
         if (a.tag == Tags.RatnumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_RATNUM_NEGATE, a);
             return; // TAIL CALL
         }
         else if (a.tag == Tags.RectnumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_RECTNUM_NEGATE, a);
             return;
         }
     }
     else if (arg is SByteVL)
     {
         SByteVL a = (SByteVL)arg;
         if (a.tag == Tags.BignumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_BIGNUM_NEGATE, a);
             return;
         }
         else if (a.tag == Tags.FlonumTag)
         {
             Reg.Result = Factory.makeFlonum(-a.unsafeAsDouble(0));
             return;
         }
         else if (a.tag == Tags.CompnumTag)
         {
             double real = a.unsafeAsDouble(0);
             double imag = a.unsafeAsDouble(1);
             Reg.Result = Factory.makeCompnum(-real, -imag);
             return;
         }
     }
     Exn.fault(Constants.EX_NEG, "not a number");
     return;
 }
示例#22
0
        /* Misc */
        /* ---- */

        public static void op1_enable_interrupts(SObject arg)
        {
            Ops.expect1(arg.isFixnum(), arg, Constants.EX_EINTR);
            int time = ((SFixnum)arg).value;

            if (time > 0)
            {
                Reg.interruptsEnabled = true;
                Reg.timer             = time;
            }
            else
            {
                Exn.fault(Constants.EX_EINTR,
                          "enable-interrupts: expected positive value");
            }
            Reg.Result = Factory.Unspecified;
            Exn.checkSignals();
        }
示例#23
0
 public static void op2_quotient(SObject arg1, SObject arg2)
 {
     if (arg1 is SFixnum & arg2 is SFixnum)
     {
         int a = ((SFixnum)arg1).value;
         int b = ((SFixnum)arg2).value;
         if (b != 0)
         {
             int result = a / b;
             Reg.Result = Factory.makeFixnum(result);
             return;
         }
         else
         {
             Exn.fault(Constants.EX_QUOTIENT, "division by zero", arg1, arg2);
             return;
         }
     }
     else if (arg1 is SByteVL & arg2 is SFixnum)
     {
         SByteVL a = (SByteVL)arg1;
         int     b = ((SFixnum)arg2).value;
         if (b == 0)
         {
             Exn.fault(Constants.EX_QUOTIENT, "division by zero", arg1, arg2);
             return;
         }
         if (b > 0 &&
             a.tag == Tags.BignumTag &&
             Number.getBignumLength(a) == 1 &&
             Number.getBignumSign(a) == Number.BIGNUM_POSITIVE)
         {
             // Exn.msg.WriteLine("++++ doing bignum quotient in millicode");
             uint av     = a.getUInt32(1);
             uint result = av / (uint)b;
             Reg.Result = Factory.makeNumber(result);
             return;
         }
     }
     Call.callMillicodeSupport2(Constants.MS_HEAVY_QUOTIENT, arg1, arg2);
     return; // TAIL CALL
 }
示例#24
0
        /* fillCache
         */
        public static void fillCache()
        {
#if HAS_PERFORMANCE_COUNTERS
            if (stackReloadCounter != null)
            {
                stackReloadCounter.Increment();
            }
#endif
            cont = ROOT;
            SVL h = heap as SVL;

            if (h == null)
            {
                Exn.internalError("fillCache: Cont.heap is not a vector");
            }
            else
            {
                heap = h.elements[Cont.HC_DYNLINK];
                cont.fillFromVector(h);
            }
        }
示例#25
0
        public static SObject op3_procedure_set(SObject arg1, SObject arg2, SObject arg3)
        {
            expect3(arg1.isProcedure(), arg1, arg2.isFixnum(), arg2, true, arg3,
                    Constants.EX_PROCEDURE_SET);
            Procedure p = (Procedure)arg1;
            int       b = ((SFixnum)arg2).value;

            // System.Console.WriteLine("** (procedure-set! {0} {1} {2})", arg1, arg2, arg3);

            if (b == 0)
            {
                // "code vector"
                p.setCode(arg3);
                return(Factory.Unspecified);
            }
            else if (b == 1)
            {
                if (arg3.isVector())
                {
                    p.setConstants((SVL)arg3);
                    return(Factory.Unspecified);
                }
                else
                {
                    Exn.fault(Constants.EX_PROCEDURE_SET, "not a vector", arg1, arg2, arg3);
                    return(null);
                }
            }
            else if (b > 1)
            {
                int bb = b - 2;
                if (bb < p.rib.Length)
                {
                    p.rib[bb] = arg3;
                    return(Factory.Unspecified);
                }
            }
            Exn.fault(Constants.EX_PROCEDURE_SET, "procedure-set!: bad index " + b, arg1, arg2, arg3);
            return(null);
        }
示例#26
0
 public static void op1_truncate(SObject arg)
 {
     if (arg is SFixnum)
     {
         Reg.Result = arg;
         return;
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
         if (a.tag == Tags.RatnumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_RATNUM_TRUNCATE, arg);
             return;
         }
     }
     else if (arg is SByteVL)
     {
         SByteVL a = (SByteVL)arg;
         if (a.tag == Tags.FlonumTag)
         {
             double d = a.unsafeAsDouble(0);
             if (d < 0)
             {
                 Reg.Result = Factory.makeFlonum(System.Math.Ceiling(d));
                 return;
             }
             else
             {
                 Reg.Result = Factory.makeFlonum(System.Math.Floor(d));
                 return;
             }
         }
         else if (a.tag == Tags.BignumTag)
         {
             return;
         }
     }
     Exn.fault(Constants.EX_TRUNC, "truncate: expected real number");
 }
示例#27
0
 public static void op1_inexact2exact(SObject arg)
 {
     if (arg is SFixnum)
     {
         return;
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
     }
     else if (arg is SByteVL)
     {
         SByteVL a = (SByteVL)arg;
         if (a.tag == Tags.FlonumTag
             | a.tag == Tags.CompnumTag)
         {
             Call.callMillicodeSupport1(Constants.MS_GENERIC_INEXACT2EXACT, arg);
             return;
         }
         else if (a.tag == Tags.BignumTag)
         {
             return;
         }
     }
     else if (arg is SVL)
     {
         SVL a = (SVL)arg;
         if (a.tag == Tags.RatnumTag)
         {
             return;
         }
         else if (a.tag == Tags.RectnumTag)
         {
             return;
         }
     }
     Exn.fault(Constants.EX_I2E, "not a number");
     return;
 }
示例#28
0
        // file exists?
        private static void access()
        {
            string file      = ((SByteVL)Reg.Register2).asString();
            int    operation = ((SFixnum)Reg.Register3).value;
            int    result    = 2;  // WHY?

            if (operation == 0x01) // FILE EXISTS?
            {
                if (File.Exists(file) || Directory.Exists(file))
                {
                    result = 0;
                }
                else
                {
                    result = -1;
                }
            }
            else
            {
                Exn.internalError("access: read/write/execute checking not supported");
                return;
            }
            Reg.Result = Factory.makeNumber(result);
        }
示例#29
0
        public static bool handleProcedure(Procedure command, SObject[] args)
        {
            bool keepRunning   = true;
            bool errorOccurred = true;

            try {
                Reg.clearRegisters();
                for (int i = 0; i < args.Length; ++i)
                {
                    Reg.setRegister(i + 1, args[i]);
                }
                Call.trampoline(command, args.Length);
                errorOccurred = false;
            }
            catch (SchemeExitException see) {
                keepRunning   = false;
                errorOccurred = false;
                if (see.returnCode != 0)
                {
                    // Exn.msg.WriteLine ("Machine exited with error code "
                    //                    + see.returnCode);
                    Exn.fullCoreDump();
                    Environment.Exit(see.returnCode);
                }
            }
            finally {
                if (errorOccurred)
                {
                    Exn.fullCoreDump();
                }
            }
            //            if (reportResult) {
            //                Exn.msg.WriteLine ("  {0}", Reg.Result);
            //            }
            return(keepRunning);
        }
示例#30
0
 public static SObject op1_gc_counter(SObject arg)
 {
     Exn.fault(Constants.EX_UNSUPPORTED);
     return(Factory.Unspecified);
 }