Package org.boris.xlloop.script

Source Code of org.boris.xlloop.script.LispFunctionHandler

/*******************************************************************************
* This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
*     Peter Smith
*******************************************************************************/
package org.boris.xlloop.script;

import java.io.EOFException;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;

import org.boris.xlloop.IFunctionContext;
import org.boris.xlloop.IFunctionHandler;
import org.boris.xlloop.RequestException;
import org.boris.xlloop.handler.FunctionInformation;
import org.boris.xlloop.util.IO;
import org.boris.xlloop.util.ObjectRegistry;
import org.boris.xlloop.util.XLList;
import org.boris.xlloop.xloper.XLArray;
import org.boris.xlloop.xloper.XLInt;
import org.boris.xlloop.xloper.XLMissing;
import org.boris.xlloop.xloper.XLNil;
import org.boris.xlloop.xloper.XLNum;
import org.boris.xlloop.xloper.XLString;
import org.boris.xlloop.xloper.XLoper;
import org.jatha.Jatha;
import org.jatha.dynatype.LispConsOrNil;
import org.jatha.dynatype.LispValue;
import org.jatha.dynatype.StandardLispCons;
import org.jatha.dynatype.StandardLispInteger;
import org.jatha.dynatype.StandardLispNIL;
import org.jatha.dynatype.StandardLispReal;
import org.jatha.dynatype.StandardLispString;
import org.jatha.dynatype.StandardLispSymbol;

public class LispFunctionHandler implements IFunctionHandler
{
    private Jatha jatha = new Jatha(false, false, false);
    private ObjectRegistry registry = new ObjectRegistry();

    public LispFunctionHandler() {
        jatha.init();
        jatha.start();
    }

    public XLoper execute(IFunctionContext context, String name, XLoper[] args) throws RequestException {
        try {
            LispValue inValue = makeList(args, findSize(args));
            LispValue result = jatha.eval(inValue);
            XLoper outValue = makeResult(result);
            return outValue;
        } catch (Exception e) {
            e.printStackTrace();
            throw new RequestException(e);
        }
    }

    public boolean hasFunction(String name) {
        return name.equals("Eval");
    }

    public FunctionInformation getInformation() {
        FunctionInformation fi = new FunctionInformation("Eval");
        fi.addArgument("args", "The arguments...");
        fi.setFunctionHelp("Evaluates a list of arguments as a lisp expression");
        return fi;
    }

    /**
     * Eval scripts in a directory tree.
     *
     * @param f
     * @param recurse
     */
    public void eval(File f, boolean recurse) {
        if (f == null)
            return;
        if (f.isDirectory() && recurse) {
            File[] fs = f.listFiles();
            for (int i = 0; i < fs.length; i++) {
                eval(fs[i], recurse);
            }
        } else if (f.isFile() && f.getName().endsWith(".lisp")) {
            try {
                String s = IO.toString(f);
                jatha.eval(s);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    private LispValue makeList(XLoper[] args, int size) throws EOFException {
        if (args == null || size == 0) {
            return new StandardLispNIL();
        } else if (size == 1) {
            return makeValue(args[0]);
        } else {
            ArrayList l = new ArrayList();
            boolean quote = false;
            for (int i = 0; i < size; i++) {
                LispValue v = makeValue(args[i]);
                if (v != null)
                    l.add(v);
                if (i == 0 && !(v instanceof StandardLispSymbol)) {
                    quote = true;
                }
            }
            LispConsOrNil res = jatha.makeList(l);
            if (quote)
                res = jatha.makeList(jatha.QUOTE, res);
            return res;
        }
    }

    private LispValue makeValue(XLoper value) throws EOFException {
        if (value instanceof XLString) {
            String str = ((XLString) value).str;
            LispValue l = (LispValue) registry.get(str);
            if (l != null) {
                return l;
            } else {
                return jatha.parse(str);
            }
        } else if (value instanceof XLInt) {
            return jatha.makeInteger(((XLInt) value).w);
        } else if (value instanceof XLNum) {
            return jatha.makeReal(((XLNum) value).num);
        } else if (value instanceof XLArray) {
            XLoper[] a = ((XLArray) value).array;
            return makeList(a, a.length);
        } else {
            return new StandardLispNIL();
        }
    }

    private XLoper makeResult(LispValue value) {
        if (value instanceof StandardLispString) {
            return new XLString(((StandardLispString) value).getValue());
        } else if (value instanceof StandardLispInteger) {
            return new XLInt((int) ((StandardLispInteger) value).getValue());
        } else if (value instanceof StandardLispReal) {
            return new XLNum(((StandardLispReal) value).getDoubleValue());
        } else if (value instanceof StandardLispCons) {
            StandardLispCons c = (StandardLispCons) value;
            XLList coll = new XLList();
            for (int i = 0; i < c.basic_length(); i++) {
                coll.add(makeResult(c.elt(i)));
            }
            return coll.toXLoper();
        } else if (value instanceof StandardLispNIL || value == null) {
            return XLNil.NIL;
        } else {
            return new XLString(registry.put(value));
        }
    }

    private int findSize(XLoper[] args) {
        int size;
        if (args == null || (size = args.length) == 0) {
            return 0;
        }
        while (size > 0) {
            XLoper v = args[--size];
            if (!(v instanceof XLMissing)) {
                return size + 1;
            }
        }
        return 0;
    }
}
TOP

Related Classes of org.boris.xlloop.script.LispFunctionHandler

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.