Coverage Report - com.sun.tools.javafx.code.JavafxTypes
 
Classes in this File Line Coverage Branch Coverage Complexity
JavafxTypes
91%
204/223
81%
152/188
0
JavafxTypes$1
100%
2/2
N/A
0
 
 1  
 /*
 2  
  * Copyright 1999-2007 Sun Microsystems, Inc.  All Rights Reserved.
 3  
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 4  
  *
 5  
  * This code is free software; you can redistribute it and/or modify it
 6  
  * under the terms of the GNU General Public License version 2 only, as
 7  
  * published by the Free Software Foundation.  Sun designates this
 8  
  * particular file as subject to the "Classpath" exception as provided
 9  
  * by Sun in the LICENSE file that accompanied this code.
 10  
  *
 11  
  * This code is distributed in the hope that it will be useful, but WITHOUT
 12  
  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 13  
  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 14  
  * version 2 for more details (a copy is included in the LICENSE file that
 15  
  * accompanied this code).
 16  
  *
 17  
  * You should have received a copy of the GNU General Public License version
 18  
  * 2 along with this work; if not, write to the Free Software Foundation,
 19  
  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 20  
  *
 21  
  * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
 22  
  * CA 95054 USA or visit www.sun.com if you need additional information or
 23  
  * have any questions.
 24  
  */
 25  
 
 26  
 package com.sun.tools.javafx.code;
 27  
 import com.sun.tools.javac.code.*;
 28  
 import com.sun.tools.javac.util.*;
 29  
 import com.sun.tools.javac.code.Type.*;
 30  
 import java.util.HashMap;
 31  
 import com.sun.tools.javafx.tree.*;
 32  
 import com.sun.tools.javac.code.Symbol.*;
 33  
 import static com.sun.tools.javac.code.Kinds.*;
 34  
 import static com.sun.tools.javac.code.Flags.*;
 35  
 import static com.sun.tools.javac.code.TypeTags.*;
 36  
 import java.util.HashSet;
 37  
 import java.util.Set;
 38  
 /**
 39  
  *
 40  
  * @author bothner
 41  
  */
 42  
 public class JavafxTypes extends Types {
 43  
     JavafxSymtab syms;
 44  
 
 45  
     private HashMap<ClassSymbol, JFXClassDeclaration> fxClasses;
 46  
 
 47  
     public static void preRegister(final Context context) {
 48  798
         context.put(typesKey, new Context.Factory<Types>() {
 49  
             public Types make() {
 50  399
                 return new JavafxTypes(context);
 51  
             }
 52  
         });
 53  399
     }
 54  
 
 55  
     public static JavafxTypes instance(Context context) {
 56  3192
         JavafxTypes instance = (JavafxTypes) context.get(typesKey);
 57  3192
         if (instance == null)
 58  0
             instance = new JavafxTypes(context);
 59  3192
         return instance;
 60  
     }
 61  
 
 62  
     protected JavafxTypes(Context context) {
 63  399
         super(context);
 64  399
         syms = (JavafxSymtab) JavafxSymtab.instance(context);
 65  399
     }
 66  
 
 67  
    public boolean isSequence(Type type) {
 68  52747
        return type != Type.noType && type != null 
 69  
                 && type.tag != TypeTags.ERROR 
 70  
                 && type.tag != TypeTags.METHOD && type.tag != TypeTags.FORALL
 71  
                 && erasure(type) == syms.javafx_SequenceTypeErasure;
 72  
     }
 73  
 
 74  
     public Type sequenceType(Type elemType) {
 75  1626
         return sequenceType(elemType, true);
 76  
     }
 77  
      public Type sequenceType(Type elemType, boolean withExtends) {
 78  1661
         if (elemType.isPrimitive())
 79  794
             elemType = boxedClass(elemType).type;
 80  1661
         if (withExtends)
 81  1626
             elemType = new WildcardType(elemType, BoundKind.EXTENDS, syms.boundClass);
 82  1661
         Type seqtype = syms.javafx_SequenceType;
 83  1661
         List<Type> actuals = List.of(elemType);
 84  1661
         Type clazzOuter = seqtype.getEnclosingType();
 85  1661
         return new ClassType(clazzOuter, actuals, seqtype.tsym);
 86  
     }
 87  
 
 88  
     public Type elementType(Type seqType) {
 89  1784
         Type elemType = seqType.getTypeArguments().head;
 90  1784
         if (elemType instanceof CapturedType)
 91  839
             elemType = ((CapturedType) elemType).wildcard;
 92  1784
         if (elemType instanceof WildcardType)
 93  1784
             elemType = ((WildcardType) elemType).type;
 94  1784
         if (elemType == null)
 95  0
             return syms.errType;
 96  1784
         Type unboxed = unboxedType(elemType);
 97  1784
         if (unboxed.tag != TypeTags.NONE)
 98  1044
             elemType = unboxed;
 99  1784
         return elemType;
 100  
     }
 101  
 
 102  
     public void getSupertypes(Symbol clazz, ListBuffer<Type> supertypes,Set<Type> dupSet) {
 103  74014
         if (clazz != null) {
 104  74014
             Type supType = supertype(clazz.type);
 105  74014
             if (supType != null && supType != Type.noType && !dupSet.contains(supType)) {
 106  38501
                 supertypes.append(supType);
 107  38501
                 dupSet.add(supType);
 108  38501
                 getSupertypes(supType.tsym, supertypes,dupSet);
 109  
             }
 110  
 
 111  74014
             if (clazz instanceof JavafxClassSymbol) {
 112  74008
                 for (Type superType : ((JavafxClassSymbol)clazz).getSuperTypes()) {
 113  8979
                     if (!dupSet.contains(superType)) {
 114  2541
                         supertypes.append(superType);
 115  2541
                         dupSet.add(superType);
 116  2541
                         getSupertypes(superType.tsym, supertypes,dupSet);
 117  
                     }
 118  
                 }
 119  
             }
 120  
         }
 121  74014
     }
 122  
     
 123  
     public boolean isSuperType (Type maybeSuper, ClassSymbol sym) {
 124  5503
         ListBuffer<Type> supertypes = ListBuffer.<Type>lb();
 125  5503
         Set superSet = new HashSet<Type>();
 126  5503
         supertypes.append(sym.type);
 127  5503
         superSet.add(sym.type);
 128  5503
         getSupertypes(sym, supertypes, superSet);
 129  5503
         return superSet.contains(maybeSuper);
 130  
     }
 131  
 
 132  
     @Override
 133  
     public Type asSuper(Type t, Symbol sym) {
 134  166813
         if (isCompoundClass(t.tsym)) {
 135  19146
             JavafxClassSymbol tsym = (JavafxClassSymbol) t.tsym;
 136  19146
             List<Type> supers = tsym.getSuperTypes();
 137  26190
             for (List<Type> l = supers; l.nonEmpty(); l = l.tail) {
 138  7980
                 Type x = asSuper(l.head, sym);
 139  7980
                 if (x != null)
 140  936
                     return x;
 141  
             }
 142  
         }
 143  165877
         return super.asSuper(t, sym);
 144  
     }
 145  
 
 146  
     @Override
 147  
     public boolean isConvertible (Type t, Type s, Warner warn) {
 148  18937
         if (super.isConvertible(t, s, warn))
 149  16711
             return true;
 150  2226
         if (isSequence(t) && isArray(s))
 151  3
             return isConvertible(elementType(t), elemtype(s), warn);
 152  2223
         if (isArray(t) && isSequence(s))
 153  0
             return isConvertible(elemtype(t), elementType(s), warn);
 154  
         
 155  
         // Allow lessening precision conversions.
 156  2223
         if (t == syms.javafx_NumberType) {
 157  41
             if (s == syms.javafx_IntegerType ||
 158  
                     s == syms.intType ||
 159  
                     s == syms.floatType ||
 160  
                     s == syms.shortType ||
 161  
                     s == syms.charType ||
 162  
                     s == syms.byteType ||
 163  
                     s == syms.longType) {
 164  37
                 return true;
 165  
             }
 166  
         }
 167  2182
         else if (t == syms.javafx_IntegerType) {
 168  76
             if (s == syms.javafx_NumberType ||
 169  
                     s == syms.intType ||
 170  
                     s == syms.floatType ||
 171  
                     s == syms.shortType ||
 172  
                     s == syms.charType ||
 173  
                     s == syms.byteType ||
 174  
                     s == syms.longType) {
 175  0
                 return true;
 176  
             }
 177  
         }
 178  
 
 179  2186
         return false;
 180  
     }
 181  
     
 182  
     public boolean isCompoundClass(Symbol sym) {
 183  188052
         if (! (sym instanceof JavafxClassSymbol))
 184  15733
             return false;
 185  172319
         sym.complete();
 186  172319
         return (sym.flags_field & JavafxFlags.COMPOUND_CLASS) != 0;
 187  
     }
 188  
 
 189  
     public boolean isJFXClass(Symbol sym) {
 190  5600
         if (! (sym instanceof JavafxClassSymbol))
 191  26
             return false;
 192  5574
         sym.complete();
 193  5574
         return (sym.flags_field & JavafxFlags.FX_CLASS) != 0;
 194  
     }
 195  
     
 196  
     public void addFxClass(ClassSymbol csym, JFXClassDeclaration cdecl) {
 197  993
         if (fxClasses == null) {
 198  373
             fxClasses = new HashMap<ClassSymbol, JFXClassDeclaration>();
 199  
         }
 200  993
         csym.flags_field |= JavafxFlags.FX_CLASS;
 201  993
         fxClasses.put(csym, cdecl);
 202  993
     }
 203  
     
 204  
     public JFXClassDeclaration getFxClass (ClassSymbol csym) {
 205  781
        return fxClasses.get(csym);
 206  
     }
 207  
     
 208  
     /** The implementation of this (abstract) symbol in class origin;
 209  
      *  null if none exists. Synthetic methods are not considered
 210  
      *  as possible implementations.
 211  
      *  Based on the Javac implementation method in MethodSymbol,
 212  
      *  but modified to handle multiple inheritance.
 213  
      */
 214  
     public MethodSymbol implementation(MethodSymbol msym, TypeSymbol origin, boolean checkResult) {
 215  2036
         if (origin instanceof JavafxClassSymbol && isCompoundClass(origin)) {
 216  1991
             JavafxClassSymbol c = (JavafxClassSymbol) origin;
 217  1991
             for (Scope.Entry e = c.members().lookup(msym.name);
 218  2222
                      e.scope != null;
 219  231
                      e = e.next()) {
 220  287
                 if (e.sym.kind == MTH) {
 221  287
                         MethodSymbol m = (MethodSymbol) e.sym;
 222  287
                         m.complete();
 223  287
                         if (m.overrides(msym, origin, this, checkResult) &&
 224  
                             (m.flags() & SYNTHETIC) == 0)
 225  56
                             return m;
 226  
                 }
 227  
             }
 228  1935
             List<Type> supers = c.getSuperTypes();
 229  3681
             for (List<Type> l = supers; l.nonEmpty(); l = l.tail) {
 230  1771
                 MethodSymbol m = implementation(msym, l.head.tsym, checkResult);
 231  1771
                 if (m != null)
 232  25
                     return m;
 233  
             }
 234  1910
             return null;
 235  
         }
 236  
         else
 237  45
             return msym.implementation(origin, this, checkResult);
 238  
     }
 239  
 
 240  
     public void clearCaches() {
 241  378
         fxClasses = null;
 242  378
     }
 243  
     
 244  
     public String toJavaFXString(Type type) {
 245  31
         StringBuilder buffer = new StringBuilder();
 246  
         try {
 247  31
             toJavaFXString(type, buffer);
 248  0
         } catch (java.io.IOException ioe) {
 249  0
             throw new RuntimeException(ioe);
 250  31
         }
 251  31
         return buffer.toString();
 252  
     }
 253  
     
 254  
     public String toJavaFXString(List<Type> ts) {
 255  6
         if (ts.isEmpty())
 256  0
             return "";
 257  6
         StringBuilder buffer = new StringBuilder();
 258  
         try {
 259  6
             toJavaFXString(ts.head, buffer);
 260  7
             for (List<Type> l = ts.tail; l.nonEmpty(); l = l.tail) {
 261  1
                 buffer.append(",");
 262  1
                 toJavaFXString(l.head, buffer);
 263  
             }
 264  0
         } catch (java.io.IOException ioe) {
 265  0
             throw new RuntimeException(ioe);
 266  6
         }
 267  6
         return buffer.toString();
 268  
     }
 269  
 
 270  
     private boolean isJavaFXBoolean(Type type) {
 271  47
         boolean result = false;
 272  47
         if (type.tag == BOOLEAN) {
 273  2
             result = true;
 274  
         }
 275  47
         return result;
 276  
     }
 277  
     
 278  
     private boolean isJavaFXInteger(Type type) {
 279  45
         boolean result = false;
 280  45
         if (type.tag == BYTE) {
 281  0
             result = true;
 282  45
         } else if (type.tag == SHORT) {
 283  0
             result = true;
 284  45
         } else if (type.tag == INT) {
 285  16
             result = true;
 286  29
         } else if (type.tag == LONG) {
 287  0
             result = true;
 288  
         }
 289  45
         return result;
 290  
     }
 291  
     
 292  
     private boolean isJavaFXNumber(Type type){
 293  29
         boolean result = false;
 294  29
         if (type.tag == FLOAT) {
 295  0
             result = true;
 296  29
         } else if (type.tag == DOUBLE) {
 297  6
             result = true;
 298  
         }
 299  29
         return result;
 300  
     }
 301  
     
 302  
     private boolean isJavaFXString(Type type) {
 303  23
         boolean result = false;
 304  23
         if ((type.tag == CLASS) && (type.toString().equals("java.lang.String"))) {
 305  6
             result = true;
 306  
         }
 307  23
         return result;
 308  
     }
 309  
     
 310  
     private boolean isJavaFXObject(Type type) {
 311  17
         boolean result = false;
 312  17
         if ((type.tag == CLASS) && (type.toString().equals("java.lang.Object"))) {
 313  1
             result = true;
 314  
         }
 315  17
         return result;
 316  
     }
 317  
     
 318  
     private boolean isJavaFXUnknown(Type type) {
 319  16
         boolean result = false;
 320  16
         if (type.tag == UNKNOWN) {
 321  2
             result = true;
 322  
         }
 323  16
         return result;
 324  
     }
 325  
     
 326  
     private boolean isJavaFXSequence(Type type) {
 327  14
         boolean result = false;
 328  14
         if (isSequence(type)) {
 329  3
             result = true;
 330  
         }
 331  14
         return result;
 332  
     }
 333  
     
 334  
     private boolean isJavaFXMethod(Type type) {
 335  11
         boolean result = false;
 336  11
         if ((type instanceof MethodType) || (type instanceof FunctionType)) {
 337  1
             result = true;
 338  
         }
 339  11
         return result;
 340  
     }
 341  
     
 342  
     private void sequenceToJavaFXString(Type type, Appendable buffer) throws java.io.IOException {
 343  3
         toJavaFXString(elementType(type), buffer);
 344  3
         buffer.append("[]");
 345  3
     }
 346  
     
 347  
     private void methodToJavaFXString(MethodType type, Appendable buffer) throws java.io.IOException {
 348  1
         if (type.getReturnType() == null) {
 349  0
             buffer.append("function(?):?");
 350  0
             return;
 351  
         }
 352  1
         buffer.append("function(");
 353  1
         List<Type> args = type.getParameterTypes();
 354  3
         for (List<Type> l = args; l.nonEmpty(); l = l.tail) {
 355  2
             if (l != args) {
 356  1
                 buffer.append(",");
 357  
             }
 358  2
             buffer.append(":");
 359  2
             toJavaFXString(l.head, buffer);
 360  
         }
 361  1
         buffer.append("):");
 362  1
         toJavaFXString(type.getReturnType(), buffer);
 363  1
     }
 364  
 
 365  
     private void toJavaFXString(Type type, Appendable buffer) throws java.io.IOException {
 366  47
         if (isJavaFXBoolean(type)) {
 367  2
             buffer.append("Boolean");
 368  45
         } else if (isJavaFXInteger(type)) {
 369  16
             buffer.append("Integer");
 370  29
         } else if (isJavaFXNumber(type)) {
 371  6
             buffer.append("Number");
 372  23
         } else if (isJavaFXString(type)) {
 373  6
             buffer.append("String");
 374  17
         } else if (isJavaFXObject(type)) {
 375  1
             buffer.append("Object");
 376  16
         } else if (isJavaFXUnknown(type)) {
 377  
             // Is this right?
 378  2
             buffer.append("Object");
 379  14
         } else if (isJavaFXSequence(type)) {
 380  3
             sequenceToJavaFXString(type, buffer);
 381  11
         } else if (isJavaFXMethod(type)) {
 382  1
             MethodType methodType = type.asMethodType();
 383  1
             methodToJavaFXString(methodType, buffer);
 384  1
         } else {
 385  10
             buffer.append(type.toString());
 386  
         }
 387  47
     }
 388  
 
 389  
     public String toJavaFXString(MethodSymbol sym, List<VarSymbol> params) {
 390  5
         StringBuilder builder = new StringBuilder();
 391  
         try {
 392  5
             toJavaFXString(sym, params, builder);
 393  0
         } catch (java.io.IOException ioe) {
 394  0
             throw new RuntimeException(ioe);
 395  5
         }
 396  5
         return builder.toString();
 397  
     }
 398  
 
 399  
     public void toJavaFXString(MethodSymbol sym, List<VarSymbol> params,
 400  
             Appendable buffer) throws java.io.IOException {
 401  5
         if ((sym.flags() & BLOCK) != 0)
 402  0
             buffer.append(sym.owner.name);
 403  
         else {
 404  5
             buffer.append(sym.name == sym.name.table.init ? sym.owner.name : sym.name);
 405  5
             if (sym.type != null) {
 406  5
                 buffer.append('(');
 407  
                 // FUTURE: check (flags() & VARARGS) != 0
 408  5
                 List<Type> args = sym.type.getParameterTypes();
 409  8
                 for (List<Type> l = args; l.nonEmpty(); l = l.tail) {
 410  3
                     if (l != args)
 411  0
                         buffer.append(",");
 412  3
                     if (params != null && params.nonEmpty()) {
 413  3
                         VarSymbol param = params.head;
 414  3
                         if (param != null)
 415  3
                             buffer.append(param.name);
 416  3
                         params = params.tail;
 417  
                     }
 418  3
                     buffer.append(":");
 419  3
                     toJavaFXString(l.head, buffer);
 420  
                 }
 421  5
                 buffer.append(')');
 422  
             }
 423  
         }
 424  5
     }
 425  
 
 426  
     public String location (Symbol sym, Type site) {
 427  8
         if (syms.isRunMethod(sym.owner))
 428  1
             sym = sym.owner;
 429  8
         return sym.location(site, this);
 430  
     }
 431  
 }