typeparser.scala

来自「JAVA 语言的函数式编程扩展」· SCALA 代码 · 共 507 行 · 第 1/2 页

SCALA
507
字号
      for (cmpName <- ENUM_CMP_NAMES) {	val enumCmpType: Type = JavaMethodType(List(clazz.tpe), definitions.BooleanClass.tpe);	val enumCmp: Symbol = clazz.newMethod(NoPosition, cmpName);	enumCmp.setFlag(flags).setInfo(enumCmpType)	instanceDefs.enter(enumCmp);      }      for (bitLogName <- ENUM_BIT_LOG_NAMES) {	val enumBitLogType = JavaMethodType(List(clazz.tpe), classInfo);	val enumBitLog = clazz.newMethod(NoPosition, bitLogName);	enumBitLog.setFlag(flags).setInfo(enumBitLogType);	instanceDefs.enter(enumBitLog);      }    }  } // parseClass  private def createMethod(method: MethodBase) {    val rettype = if (method.IsConstructor()) clazz.tpe                  else getCLSType(method.asInstanceOf[MethodInfo].ReturnType);    if (rettype == null) return;    val mtype = methodType(method, rettype);    if (mtype == null) return;    val flags = translateAttributes(method);    val owner = if (method.IsStatic()) statics else clazz;    val methodSym = owner.newMethod(NoPosition, getName(method)).setFlag(flags).    setInfo(mtype);    (if (method.IsStatic()) staticDefs else instanceDefs).enter(methodSym);    if (method.IsConstructor())      clrTypes.constructors(methodSym) = method.asInstanceOf[ConstructorInfo]    else clrTypes.methods(methodSym) = method.asInstanceOf[MethodInfo];  }  private def createMethod(name: Name, flags: Long, args: Array[MSILType], retType: MSILType, method: MethodInfo, statik: Boolean): Symbol = {    val mtype: Type = methodType(args, getCLSType(retType));    assert(mtype != null);    createMethod(name, flags, mtype, method, statik)  }  private def createMethod(name: Name, flags: Long, mtype: Type, method: MethodInfo, statik: Boolean): Symbol = {    val methodSym: Symbol = (if (statik)  statics else clazz).newMethod(NoPosition, name);    methodSym.setFlag(flags).setInfo(mtype);    (if (statik) staticDefs else instanceDefs).enter(methodSym);    if (method != null)      clrTypes.methods(methodSym)  = method;    methodSym  }  private def createDelegateView(typ: MSILType) = {    val invoke: MethodInfo = typ.GetMember("Invoke")(0).asInstanceOf[MethodInfo];    val invokeRetType: Type = getCLRType(invoke.ReturnType);    val invokeParamTypes: List[Type] =invoke.GetParameters().map(_.ParameterType).map(getCLSType).toList;    val funType: Type = definitions.functionType(invokeParamTypes, invokeRetType);    val typClrType: Type = getCLRType(typ);    val flags = Flags.JAVA | Flags.STATIC | Flags.IMPLICIT; // todo: static? think not needed    // create the forward view: delegate => function    val delegateParamTypes: List[Type] = List(typClrType);    // not ImplicitMethodType, this is for methods with implicit parameters (not implicit methods)    val forwardViewMethodType = JavaMethodType(delegateParamTypes, funType);    val fmsym = createMethod(nme.view_, flags, forwardViewMethodType, null, true);    // create the backward view: function => delegate    val functionParamTypes: List[Type] = List(funType);    val backwardViewMethodType = JavaMethodType(functionParamTypes, typClrType);    val bmsym = createMethod(nme.view_, flags, backwardViewMethodType, null, true);  }  private def createDelegateChainers(typ: MSILType) = {    val flags: Long = Flags.JAVA | Flags.FINAL    val args: Array[MSILType] = Array(typ)    var s = createMethod(encode("+="), flags, args, clrTypes.VOID, clrTypes.DELEGATE_COMBINE, false);    s = createMethod(encode("-="), flags, args, clrTypes.VOID, clrTypes.DELEGATE_REMOVE, false);    s = createMethod(nme.PLUS, flags, args, typ, clrTypes.DELEGATE_COMBINE, false);    s = createMethod(nme.MINUS, flags, args, typ, clrTypes.DELEGATE_REMOVE, false);  }  private def getName(method: MethodBase): Name = {    if (method.IsConstructor()) return nme.CONSTRUCTOR;    val name = method.Name;    if (method.IsStatic()) return newTermName(name);    val params = method.GetParameters();    name match {      case "GetHashCode" if (params.length == 0) => nme.hashCode_;      case "ToString" if (params.length == 0) => nme.toString_;      case "Finalize" if (params.length == 0) => nme.finalize_;      case "Equals" if (params.length == 1 && params(0).ParameterType == clrTypes.OBJECT) =>        nme.equals_;      case "Invoke" if (clrTypes.isDelegateType(method.DeclaringType)) => nme.apply;      case _ => newTermName(name);    }  }  //##########################################################################  private def methodType(method: MethodBase, rettype: MSILType): Type = {    val rtype = getCLSType(rettype);    if (rtype == null) null else methodType(method, rtype);  }  /** Return a method type for the given method. */  private def methodType(method: MethodBase, rettype: Type): Type =    methodType(method.GetParameters().map(_.ParameterType), rettype);  /** Return a method type for the provided argument types and return type. */  private def methodType(argtypes: Array[MSILType], rettype: Type): Type = {    def paramType(typ: MSILType): Type =      if (typ eq clrTypes.OBJECT) definitions.AnyClass.tpe      else getCLSType(typ);    val ptypes = argtypes.map(paramType).toList;    if (ptypes.contains(null)) null    else JavaMethodType(ptypes, rettype);  }    //##########################################################################  private def getClassType(typ: MSILType): Type = {    assert(typ != null);    val res = definitions.getClass(typ.FullName.replace('+', '.')).tpe;    //if (res.isError())    //  global.reporter.error("unknown class reference " + type.FullName);    res  }  private def getCLSType(typ: MSILType): Type = {    if (/*type == clrTypes.BYTE ||*/ typ == clrTypes.USHORT	|| typ == clrTypes.UINT || typ == clrTypes.ULONG	|| typ.IsNotPublic() || typ.IsNestedPrivate()	|| typ.IsNestedAssembly() || typ.IsNestedFamANDAssem()	|| typ.IsPointer()	|| (typ.IsArray() && getCLSType(typ.GetElementType()) == null))      null;    //Symbol s = clrTypes.getSymbol(type);    //scalac.symtab.Type t = s != null ? make.classType(s) : getCLRType(type);    else      getCLRType(typ)  }  private def getCLRType(typ: MSILType): Type =    if (typ == clrTypes.OBJECT)      definitions.ObjectClass.tpe;    else if (typ == clrTypes.VALUE_TYPE)      definitions.AnyValClass.tpe    else if (typ == clrTypes.STRING)      definitions.StringClass.tpe;    else if (typ == clrTypes.VOID)      definitions.UnitClass.tpe    else if (typ == clrTypes.BOOLEAN)      definitions.BooleanClass.tpe    else if (typ == clrTypes.CHAR)      definitions.CharClass.tpe    else if (typ == clrTypes.BYTE || typ == clrTypes.UBYTE)      definitions.ByteClass.tpe    else if (typ == clrTypes.SHORT || typ == clrTypes.USHORT)      definitions.ShortClass.tpe    else if (typ == clrTypes.INT || typ == clrTypes.UINT)      definitions.IntClass.tpe    else if (typ == clrTypes.LONG || typ == clrTypes.ULONG)      definitions.LongClass.tpe    else if (typ == clrTypes.FLOAT)      definitions.FloatClass.tpe    else if (typ == clrTypes.DOUBLE)      definitions.DoubleClass.tpe    else if (typ.IsArray())      appliedType(definitions.ArrayClass.tpe,                  List(getCLRType(typ.GetElementType())));    else {      val res = clrTypes.sym2type.get (typ) match {        case Some(sym) => sym.tpe        case None => getClassType(typ);      }      assert (res != null, typ)      res    }  // the values are Java-Box-Classes (e.g. Integer, Boolean, Character)  // java.lang.Number to get the value (if a number, not for boolean, character)  // see ch.epfl.lamp.compiler.msil.util.PEStream.java  def getConstant(constType: Type, value: Object): Constant = {    val typeClass = constType.typeSymbol    if (typeClass == definitions.BooleanClass)      Constant(value.asInstanceOf[java.lang.Boolean].booleanValue)    else if (typeClass == definitions.ByteClass)      Constant(value.asInstanceOf[java.lang.Number].byteValue)    else if (typeClass == definitions.ShortClass)      Constant(value.asInstanceOf[java.lang.Number].shortValue)    else if (typeClass == definitions.CharClass)      Constant(value.asInstanceOf[java.lang.Character].charValue)    else if (typeClass == definitions.IntClass)      Constant(value.asInstanceOf[java.lang.Number].intValue)    else if (typeClass == definitions.LongClass)      Constant(value.asInstanceOf[java.lang.Number].longValue)    else if (typeClass == definitions.FloatClass)      Constant(value.asInstanceOf[java.lang.Number].floatValue)    else if (typeClass == definitions.DoubleClass)      Constant(value.asInstanceOf[java.lang.Number].doubleValue)    else if (typeClass == definitions.StringClass)      Constant(value.asInstanceOf[java.lang.String])    else      abort("illegal value: " + value + ", class-symbol: " + typeClass)  }  private def translateAttributes(typ: MSILType): Long = {    var flags: Long = Flags.JAVA;    if (typ.IsNotPublic() || typ.IsNestedPrivate()	|| typ.IsNestedAssembly() || typ.IsNestedFamANDAssem())      flags = flags | Flags.PRIVATE;    else if (typ.IsNestedFamily() || typ.IsNestedFamORAssem())      flags = flags | Flags.PROTECTED;    if (typ.IsAbstract())      flags = flags | Flags.ABSTRACT;    if (typ.IsSealed())      flags = flags | Flags.FINAL;    if (typ.IsInterface())      flags = flags | Flags.INTERFACE | Flags.TRAIT | Flags.ABSTRACT;    flags  }  private def translateAttributes(field: FieldInfo): Long = {    var flags: Long = Flags.JAVA;    if (field.IsPrivate() || field.IsAssembly() || field.IsFamilyAndAssembly())      flags = flags | Flags.PRIVATE;    else if (field.IsFamily() || field.IsFamilyOrAssembly())      flags = flags | Flags.PROTECTED;    if (field.IsInitOnly())      flags = flags | Flags.FINAL;    else      flags = flags | Flags.MUTABLE;    if (field.IsStatic)      flags = flags | Flags.STATIC    flags  }  private def translateAttributes(method: MethodBase): Long = {    var flags: Long = Flags.JAVA;    if (method.IsPrivate() || method.IsAssembly() || method.IsFamilyAndAssembly())      flags = flags | Flags.PRIVATE;    else if (method.IsFamily() || method.IsFamilyOrAssembly())      flags = flags | Flags.PROTECTED;    if (method.IsAbstract())      flags = flags | Flags.DEFERRED;    if (method.IsStatic)      flags = flags | Flags.STATIC    flags  }}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?