Package anvil.script.compiler

Source Code of anvil.script.compiler.NativeClass

/*
* $Id: NativeClass.java,v 1.4 2002/09/16 08:05:04 jkl Exp $
*
* Copyright (c) 2002 Njet Communications Ltd. All Rights Reserved.
*
* Use is subject to license terms, as defined in
* Anvil Sofware License, Version 1.1. See LICENSE
* file, or http://njet.org/license-1.1.txt
*/
package anvil.script.compiler;

import java.util.Enumeration;
import java.util.Hashtable;
import java.io.IOException;
import java.lang.reflect.Method;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import anvil.java.util.Hashlist;
import anvil.java.util.BindingEnumeration;
import anvil.core.Any;
import anvil.core.AnyClass;
import anvil.core.runtime.AnyType;
import anvil.doc.Doc;
import anvil.script.Context;
import anvil.script.ClassDispatcher;
import anvil.script.ConstantVariableType;
import anvil.script.Grammar;
import anvil.script.NativeJava;
import anvil.script.Type;
import anvil.script.CompilableFunction;
import anvil.script.Module;
import anvil.script.ScriptException;
import anvil.script.ClassType;
import anvil.script.ClassRef;
import anvil.script.InterfaceRef;
import anvil.script.Scope;
import anvil.server.ZoneClassLoader;

/**
* class NativeClass
*
* @author: Jani Lehtim�ki
*/
public class NativeClass implements ClassType, NativeJava
{

  protected Class              _class;
  protected String             _descriptor;
  protected NativeNamespace    _parent;
  protected String             _name;
  protected String             _qname;
  protected CompilableFunction _constructor;
  protected ClassRef           _base;
  protected Doc                _document;
  protected Hashlist           _types = new Hashlist();
  protected ClassDispatcher    _dispatcher;
  protected Any                _wrapper;


  public NativeClass(String classname, Class cls)
  {
    this(classname, cls, null, "");
  }


  public NativeClass(String classname, Class cls, String document)
  {
    this(classname, cls, null, document);
  }


  public NativeClass(String classname, Class cls, ClassType base, String document)
  {
    _class = cls;
    _descriptor = cls.getName().replace('.', '/');
    _name = classname;
    _document = anvil.doc.DocParser.parse(document);
   
    if (base != null) {
      _base = new ResolvedClassRef(base);
    }
   
    FunctionBase function;
    Object[] parameters;
    Doc doc;
    int n;
    boolean declare = true;
   
    try {

      Method[] methods = cls.getDeclaredMethods();
      n = methods.length;
      for(int i=0; i<n; i++) {
        Method method = methods[i];
        String name = method.getName();
        if (name.startsWith("m_")) {
          name = name.substring(2);
          parameters = (Object[]) Compiled.getstatic(cls, "p_"+name);
          if (_document != null) {
            doc = _document.findFirst(Doc.T_METHOD, name);
          } else {
            doc = null;
          }
          function = new NativeMethod(this, method, name, parameters, doc);
          _types.put(name, function);
         
        } else if (name.equals("newInstance")) {
          if (Modifier.isStatic(method.getModifiers())) {
            doc = _document.findFirst(Doc.T_CONSTRUCTOR, classname);
            parameters = (Object[])Compiled.getstatic(cls, "newInstance");
            _constructor = new NativeConstructor(this, method, _name, parameters, doc);
            _types.put(classname, _constructor);
          }
       
        }
      }
   
      if (cls != Any.class) {
        Field[] fields = cls.getDeclaredFields();
        Object obj;
        n = fields.length;
        for(int i=0; i<n; i++) {
          Field field = fields[i];
          String name = field.getName();
          int mod = field.getModifiers();
          if (name.startsWith("p_")) {
            continue;
          }
          if (name.startsWith("_")) {
            continue;
          }
          if (name.equals("newInstance")) {
            continue;
          }
          if (Modifier.isPublic(mod) && Modifier.isStatic(mod) && Modifier.isFinal(mod)) {
            try {
              obj = field.get(null);
              if (obj instanceof Any) {
                if (_document != null) {
                  doc = _document.findFirst(Doc.T_CONST, name);
                } else {
                  doc = null;
                }
                _types.put(name, new NativeConstantVariable(this, name, field, doc));
              }
            } catch (Exception e) {
              anvil.Log.log().error("Couldn't get field '"+field+"' from "+classname+"."+classname);
            }
          }
        }
      }
   
    } catch (Throwable t) {
      t.printStackTrace();
    }
   
    anvil.core.ObjectPool.register(cls);
  }

  /*package*/ void setParent(NativeNamespace parent)
  {
    _parent = parent;
    if (_base == null && this != anvil.core.Any.__class__) {
      _base = new ResolvedClassRef(anvil.core.Any.__class__);
    }
  }
 
 
  public String toString()
  {
    return "class "+getQualifiedName();
  }


  public String getName()
  {
    return _name;
  }

 
  public final String getQualifiedName()
  {
    if (_qname == null) {
      _qname = Grammar.buildQualifiedName(this);
    }
    return _qname;
  }


  public String getPathinfo()
  {
    return "";
  }

  public int getType()
  {
    return CLASS;
  }
  public Scope getParent()
  {
    return _parent;
  }
 

  private ClassType[] EMPTY_PARENTS = new ClassType[0]
 
  public ClassType[] getEnclosingClasses()
  {
    return EMPTY_PARENTS;
  }
 
 
  public Doc getDocument()
  {
    return _document;
  }


  public Enumeration getDeclarations()
  {
    return _types.elements();
  }


  public BindingEnumeration getMembers(AnyClass instnace)
  {
    return BindingEnumeration.EMPTY;
  }


  public Type lookupDeclaration(String name)
  {
    Type type = (Type)_types.get(name);
    if (type == null) {
      type = lookupInheritedDeclaration(name);
    }
    return type;
  }
 
 
  public Type lookupInheritedDeclaration(String name)
  {
    ClassType base = getBaseClass();
    return (base != null) ? base.lookupDeclaration(name) : null;
  }


  public boolean isInstanceOf(Type ofType)
  { 
    ClassType cls = this;
    while(cls != null) {
      if (cls == ofType) {
        return true;
      }
      cls = cls.getBaseClass();
    }
    return false;
  }


  public ClassRef getBase()
  {
    return _base;
  }
 

  public ClassType getBaseClass()
  {
    return (_base != null) ? _base.getClassType() : null;
 


  public InterfaceRef[] getInterfaces()
  {
    return new InterfaceRef[0];
  }


  public CompilableFunction getConstructor()
  {
    return _constructor;
  }


  public AnyClass newInstance()
  {
    return null;
  }

 
  public Any newInstance(Context context, Any[] parameters)
  {
    return _constructor.execute(context, parameters);
  }

 
  public ClassDispatcher getDispatcher(Context context)
  {
    ClassDispatcher dispatcher = _dispatcher;
    if (dispatcher == null) {
      synchronized(this) {
        if (_dispatcher != null) {
          return _dispatcher;
        }
        try {
          ZoneClassLoader loader = context.zone().getClassLoader();
          return (_dispatcher = DispatcherFactory.create(this, loader));
        } catch (Throwable t) {
          context.log().error("NativeClass.createDispatcher(" + this + ")", t);
          throw context.InternalError("Creation of dispatcher failed: "+t);
        }
      }
    }
    return dispatcher;
  }
 

  public String getDescriptor()
  {
    return _descriptor;
  }


  public int getTypeRef(anvil.codec.ConstantPool pool)
  {
    return pool.addClass(getDescriptor());
  }


  public int getConstructorReference(anvil.codec.ConstantPool pool)
  {
    return 0;
    // this should never be called
  }


  public Any getWrapper()
  {
    if (_wrapper == null) {
      _wrapper =  new AnyType(this);
    }
    return _wrapper;
  }
 

  public Any getMethod(Context context, String name)
  {
    Type type = (Type)_types.get(name);
    if (type != null) {
      return new AnyType(type);
    }
    throw context.NoSuchEntity(_qname + '.' + name);
  }
 

  public Type getDeclaration(Context context, String name)
  {
    Type type = (Type)_types.get(name);
    if (type != null) {
      return type;
    }
    throw context.NoSuchEntity(_qname + '.' + name);
  }

}
TOP

Related Classes of anvil.script.compiler.NativeClass

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.