📄 check.java
字号:
/** * @(#)Check.java 1.70 03/02/26 * * Copyright 2003 Sun Microsystems, Inc. All rights reserved. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms. */package com.sun.tools.javac.v8.comp;import com.sun.tools.javac.v8.util.*;import com.sun.tools.javac.v8.code.*;import com.sun.tools.javac.v8.tree.*;import com.sun.tools.javac.v8.tree.Tree.*;import com.sun.tools.javac.v8.code.Type.*;import com.sun.tools.javac.v8.code.Symbol.*;/** * Type checking helper class for the attribution phase. */public class Check implements Kinds, Flags, TypeTags { private static final Context.Key checkKey = new Context.Key(); private Name.Table names; private Log log; private Symtab syms; private Infer infer; public static Check instance(Context context) { Check instance = (Check) context.get(checkKey); if (instance == null) instance = new Check(context); return instance; } private Check(Context context) { super(); context.put(checkKey, this); this.names = Name.Table.instance(context); this.log = Log.instance(context); this.syms = Symtab.instance(context); this.infer = Infer.instance(context); Options options = Options.instance(context); warnunchecked = options.get("-warnunchecked") != null; deprecation = options.get("-deprecation") != null; } /** * Switch: -warnunchecked option set? */ boolean warnunchecked; /** * Switch: -deprecation option set? */ boolean deprecation; /** * A table mapping flat names of all compiled classes in this run to their * symbols; maintained from outside. */ public Hashtable compiled = Hashtable.make(); /** * Output variable: the source file where deprecated symbols were * encountered. If deprecated symbols were encountered in more than one * input file, the variable is set to "*". */ public Name deprecatedSource; /** * Output variable: the source file where deprecated symbols were * encountered. If deprecated symbols were encountered in more than one * input file, the variable is set to "*". */ public Name uncheckedSource; /** * Warn about deprecated symbol. * @param pos Position to be used for error reporting. * @param sym The deprecated symbol. */ void warnDeprecated(int pos, Symbol sym) { if (deprecatedSource == null) deprecatedSource = log.currentSource(); else if (deprecatedSource != log.currentSource()) deprecatedSource = names.asterisk; if (deprecation) log.warning(pos, "has.been.deprecated", sym.toJava(), sym.javaLocation()); } /** * Warn about unchecked operation. * @param pos Position to be used for error reporting. * @param msg A string describing the problem. */ void warnUnchecked(int pos, String msg) { warnUnchecked(pos, msg, null, null, null, null); } void warnUnchecked(int pos, String msg, String arg0) { warnUnchecked(pos, msg, arg0, null, null, null); } void warnUnchecked(int pos, String msg, String arg0, String arg1) { warnUnchecked(pos, msg, arg0, arg1, null, null); } void warnUnchecked(int pos, String msg, String arg0, String arg1, String arg2) { warnUnchecked(pos, msg, arg0, arg1, arg2, null); } void warnUnchecked(int pos, String msg, String arg0, String arg1, String arg2, String arg3) { if (uncheckedSource == null) uncheckedSource = log.currentSource(); else if (uncheckedSource != log.currentSource()) uncheckedSource = names.asterisk; if (warnunchecked) log.warning(pos, msg, arg0, arg1, arg2, arg3); } /** * Report a failure to complete a class. * @param pos Position to be used for error reporting. * @param ex The failure to report. */ public Type completionError(int pos, CompletionFailure ex) { log.error(pos, "cant.access", ex.sym.toJava(), ex.errmsg); if (ex instanceof ClassReader.BadClassFile) throw new Abort(); else return syms.errType; } /** * Report a type error. * @param pos Position to be used for error reporting. * @param problem A string describing the error. * @param found The type that was found. * @param req The type that was required. */ Type typeError(int pos, String problem, Type found, Type req) { log.error(pos, "prob.found.req", problem, found.toJava(), req.toJava()); return syms.errType; } /** * Report an error that wrong type tag was found. * @param pos Position to be used for error reporting. * @param required An internationalized string describing the type tag * required. * @param found The type that was found. */ Type typeTagError(int pos, String required, Type found) { log.error(pos, "type.found.req", found.toJava(), required); return syms.errType; } /** * Report an error that symbol cannot be referenced before super * has been called. * @param pos Position to be used for error reporting. * @param sym The referenced symbol. */ void earlyRefError(int pos, Symbol sym) { log.error(pos, "cant.ref.before.ctor.called", sym.toJava()); } /** * Report an error that type parameter is not within its bound. * @param pos Position to be used for error reporting. * @param t The type parameter. * @param bound Its bound. * @param explanation An internationalized string giving an * additional explanation. */ void boundError(int pos, Type t, Type bound, String explanation) { if (explanation.equals("")) log.error(pos, "not.within.bounds", t.toJava()); else log.error(pos, "not.within.bounds.explain", t.toJava(), explanation); } /** * Return name of local class. * This is of the form <topname> $ n $ <classname> * where * topname is the fully qualified name of the enclosing toplevel class, * classname is the simple name of the local class */ Name localClassName(ClassSymbol c) { ClassSymbol topClass = c.outermostClass(); for (int i = 1; ; i++) { Name flatname = names.fromString(topClass.flatname + "$" + i + c.name); if (compiled.get(flatname) == null) return flatname; } } /** * Check that a given type is assignable to a given proto-type. * If it is, return the type, otherwise return errType. * @param pos Position to be used for error reporting. * @param found The type that was found. * @param req The type that was required. */ Type checkType(int pos, Type found, Type req) { if (req.tag == ERROR) { return req; } else if (req.tag == NONE) { return found; } else if (found.isAssignable(req)) { return found; } else { String problem; if (found.tag <= DOUBLE && req.tag <= DOUBLE) problem = log.getLocalizedString("possible.loss.of.precision"); else problem = log.getLocalizedString("incompatible.types"); return typeError(pos, problem, found, req); } } /** * Check that a given type can be cast to a given target type. * Return the result of the cast. * @param pos Position to be used for error reporting. * @param found The type that is being cast. * @param req The target type of the cast. */ Type checkCastable(int pos, Type found, Type req) { if (found.isCastable(req)) { checkCompatible(pos, found, req); return req; } else { return typeError(pos, log.getLocalizedString("inconvertible.types"), found, req); } } /** * Check that type is different from 'void'. * @param pos Position to be used for error reporting. * @param t The type to be checked. */ Type checkNonVoid(int pos, Type t) { if (t.tag == VOID) { log.error(pos, "void.not.allowed.here"); return syms.errType; } else { return t; } } /** * Check that type is a class or interface type. * @param pos Position to be used for error reporting. * @param t The type to be checked. */ Type checkClassType(int pos, Type t) { if (t.tag != CLASS && t.tag != ERROR) return typeTagError(pos, log.getLocalizedString("type.req.class"), t); else return t; } /** * Check that type is a class, interface or array type. * @param pos Position to be used for error reporting. * @param t The type to be checked. */ Type checkClassOrArrayType(int pos, Type t) { if (t.tag != CLASS && t.tag != ARRAY && t.tag != ERROR) return typeTagError(pos, log.getLocalizedString("type.req.class.array"), t); else return t; } /** * Check that type is a reference type, i.e. a class, interface or array type * or a type variable. * @param pos Position to be used for error reporting. * @param t The type to be checked. */ Type checkRefType(int pos, Type t) { if (t.tag != CLASS && t.tag != ARRAY && t.tag != ERROR) return typeTagError(pos, log.getLocalizedString("type.req.ref"), t); else return t; } /** * Check that flag set does not contain elements of two conflicting sets. s * Return true if it doesn't. * @param pos Position to be used for error reporting. * @param flags The set of flags to be checked. * @param set1 Conflicting flags set #1. * @param set2 Conflicting flags set #2. */ boolean checkDisjoint(int pos, long flags, long set1, long set2) { if ((flags & set1) != 0 && (flags & set2) != 0) { log.error(pos, "illegal.combination.of.modifiers", TreeInfo.flagNames(TreeInfo.firstFlag(flags & set1)), TreeInfo.flagNames(TreeInfo.firstFlag(flags & set2))); return false; } else return true; } /** * Check that given modifiers are legal for given symbol and * return modifiers together with any implicit modififiers for that symbol. * Warning: we can't use flags() here since this method * is called during class enter, when flags() would cause a premature * completion. * @param pos Position to be used for error reporting. * @param flags The set of modifiers given in a definition. * @param sym The defined symbol. */ long checkFlags(int pos, long flags, Symbol sym) { long mask; long implicit = 0; switch (sym.kind) { case VAR: if (sym.owner.kind != TYP) mask = LocalVarFlags; else if ((sym.owner.flags_field & INTERFACE) != 0) mask = implicit = InterfaceVarFlags; else mask = VarFlags; break; case MTH: if (sym.name == names.init) mask = ConstructorFlags; else if ((sym.owner.flags_field & INTERFACE) != 0) mask = implicit = InterfaceMethodFlags; else {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -