001 /* This file was generated with JastAdd2 (http://jastadd.org) version 2.1.13-12-g880e696 */ 002 package org.extendj.ast; 003 004 import java.util.HashSet; 005 import java.io.File; 006 import java.util.Set; 007 import java.util.Collections; 008 import java.util.Collection; 009 import java.util.ArrayList; 010 import beaver.*; 011 import java.util.*; 012 import java.io.ByteArrayOutputStream; 013 import java.io.PrintStream; 014 import java.lang.reflect.InvocationTargetException; 015 import java.lang.reflect.Method; 016 import org.jastadd.util.*; 017 import java.util.zip.*; 018 import java.io.*; 019 import org.jastadd.util.PrettyPrintable; 020 import org.jastadd.util.PrettyPrinter; 021 import java.io.FileNotFoundException; 022 import java.io.BufferedInputStream; 023 import java.io.DataInputStream; 024 /** 025 * @ast node 026 * @declaredat /home/jesper/git/extendj/java8/grammar/MethodReference.ast:1 027 * @production MethodReference : {@link Expr} ::= <span class="component">TypeArgument:{@link Access}*</span> <span class="component"><ID:String></span>; 028 029 */ 030 public abstract class MethodReference extends Expr implements Cloneable { 031 /** 032 * @aspect Java8NameCheck 033 * @declaredat /home/jesper/git/extendj/java8/frontend/NameCheck.jrag:512 034 */ 035 public void nameCheck() { 036 for (int i = 0; i < getNumTypeArgument(); i++) { 037 if (getTypeArgument(i) instanceof AbstractWildcard) { 038 error("Wildcard not allowed in method reference type argument lists"); 039 break; 040 } 041 } 042 } 043 /** 044 * @aspect TypeCheck 045 * @declaredat /home/jesper/git/extendj/java8/frontend/TypeCheck.jrag:227 046 */ 047 public void typeCheck() { 048 // 15.13.1 049 if (!assignmentContext() && !castContext() && !invocationContext()) { 050 error("Method references must target a functional interface"); 051 return; 052 } 053 054 // This means there was an error in the overload resolution, will be reported elsewhere. 055 if (invocationContext() && targetType() == unknownType()) { 056 return; 057 } 058 059 if (!targetType().isFunctionalInterface()) { 060 error("Method references must target a functional interface"); 061 return; 062 } 063 064 InterfaceDecl iDecl = targetInterface(); 065 066 if (!iDecl.isFunctional()) { 067 errorf("Interface %s is not functional and can therefore not be targeted by a method reference", 068 iDecl.typeName()); 069 return; 070 } 071 072 MethodDecl found = null; 073 FunctionDescriptor f = iDecl.functionDescriptor(); 074 // Lookup method here and check that one most specific can be found 075 if (this instanceof ExprMethodReference) { 076 ExprMethodReference ref = (ExprMethodReference)this; 077 found = ref.targetMethod(f); 078 if (unknownMethod() == found) { 079 // 15.13.1 080 errorf("No method %s that is compatible with the method %s in the interface %s was found", 081 name(), iDecl.functionDescriptor().method.fullSignature(), iDecl.typeName()); 082 } else if (found.isStatic()) { 083 errorf("The method %s in type %s must be accessed in a static way", 084 found.fullSignature(), found.hostType().typeName()); 085 } else if (ref.getExpr() instanceof Access && ((Access)ref.getExpr()).lastAccess() instanceof SuperAccess) { 086 // 15.13.2 087 if (found.isAbstract()) { 088 errorf("Cannot directly invoke the abstract method %s in type %s", 089 found.fullSignature(), found.hostType().typeName()); 090 } 091 092 SuperAccess superAccess = (SuperAccess)((Access)ref.getExpr()).lastAccess(); 093 if (superAccess.isQualified() && superAccess.decl() instanceof InterfaceDecl) { 094 if (hostType().isClassDecl()) { 095 ClassDecl classDecl = (ClassDecl)hostType(); 096 if (classDecl.hasOverridingMethodInSuper(found)) { 097 errorf("Cannot make a super reference to method %s, there is a more specific override", 098 found.fullSignature()); 099 } 100 } else if (hostType().isInterfaceDecl()) { 101 InterfaceDecl interfaceDecl = (InterfaceDecl)hostType(); 102 if (interfaceDecl.hasOverridingMethodInSuper(found)) { 103 errorf("Cannot make a super reference to method %s, there is a more specific override", 104 found.fullSignature()); 105 } 106 } 107 } 108 109 } 110 } else if (this instanceof TypeMethodReference) { 111 TypeMethodReference ref = (TypeMethodReference) this; 112 MethodDecl staticMethod = ref.targetStaticMethod(f); 113 MethodDecl instanceMethod = ref.targetInstanceMethod(f); 114 if (ref.validStaticMethod(f) && ref.validInstanceMethod(f)) { 115 errorf("Ambiguity error: two possible methods %s was found", staticMethod.name()); 116 return; 117 } else if (unknownMethod() == staticMethod && unknownMethod() == instanceMethod) { 118 errorf("No method %s that is compatible with the method %s in the interface %s was found", 119 name(), iDecl.functionDescriptor().method.fullSignature(), iDecl.typeName()); 120 return; 121 } else if (ref.validStaticMethod(f)) { 122 if (ref.getTypeAccess() instanceof ParTypeAccess) { 123 error("Parameterized qualifier is not allowed for static method references"); 124 } else { 125 found = staticMethod; 126 } 127 } else if (ref.validInstanceMethod(f)) { 128 found = instanceMethod; 129 } else if (unknownMethod() != staticMethod && !staticMethod.isStatic()) { 130 errorf("Cannot make a static reference to the non-static method %s in type %s", 131 staticMethod.fullSignature(), staticMethod.hostType().typeName()); 132 return; 133 } else if (instanceMethod.isStatic()) { 134 errorf("The method %s in type %s must be accessed in a static way", 135 instanceMethod.fullSignature(), instanceMethod.hostType().typeName()); 136 return; 137 } 138 } 139 140 if (found != null && unknownMethod() != found) { 141 // Check that found is compatible with the function descriptor 142 if (!iDecl.functionDescriptor().method.type().isVoid()) { 143 // 15.13.1 144 if (found.type().isVoid() 145 || !found.type().assignConversionTo(iDecl.functionDescriptor().method.type(), null)) { 146 errorf("Return type of referenced method %s is not compatible with method %s in interface %s", 147 found.fullSignature(), iDecl.functionDescriptor().method.fullSignature(), 148 iDecl.typeName()); 149 } 150 } 151 152 for (int i = 0; i < found.getNumException(); i++) { 153 TypeDecl exception = found.getException(i).type(); 154 if (exception.isUncheckedException()) { 155 continue; 156 } 157 158 boolean legalException = false; 159 for (TypeDecl descriptorThrows : iDecl.functionDescriptor().throwsList) { 160 if (exception.strictSubtype(descriptorThrows)) { 161 legalException = true; 162 break; 163 } 164 } 165 if (!legalException) { 166 // 15.13.1 167 errorf("Referenced method %s throws unhandled exception type %s", 168 found.name(), exception.typeName()); 169 } 170 } 171 } 172 } 173 /** 174 * @declaredat ASTNode:1 175 */ 176 public MethodReference() { 177 super(); 178 } 179 /** 180 * Initializes the child array to the correct size. 181 * Initializes List and Opt nta children. 182 * @apilevel internal 183 * @ast method 184 * @declaredat ASTNode:10 185 */ 186 public void init$Children() { 187 children = new ASTNode[1]; 188 setChild(new List(), 0); 189 } 190 /** 191 * @declaredat ASTNode:14 192 */ 193 public MethodReference(List<Access> p0, String p1) { 194 setChild(p0, 0); 195 setID(p1); 196 } 197 /** 198 * @declaredat ASTNode:18 199 */ 200 public MethodReference(List<Access> p0, beaver.Symbol p1) { 201 setChild(p0, 0); 202 setID(p1); 203 } 204 /** 205 * @apilevel low-level 206 * @declaredat ASTNode:25 207 */ 208 protected int numChildren() { 209 return 1; 210 } 211 /** 212 * @apilevel internal 213 * @declaredat ASTNode:31 214 */ 215 public boolean mayHaveRewrite() { 216 return false; 217 } 218 /** 219 * @apilevel internal 220 * @declaredat ASTNode:37 221 */ 222 public void flushAttrCache() { 223 super.flushAttrCache(); 224 isExact_reset(); 225 compatibleStrictContext_TypeDecl_reset(); 226 compatibleLooseContext_TypeDecl_reset(); 227 pertinentToApplicability_Expr_BodyDecl_int_reset(); 228 moreSpecificThan_TypeDecl_TypeDecl_reset(); 229 potentiallyCompatible_TypeDecl_BodyDecl_reset(); 230 isPolyExpression_reset(); 231 assignConversionTo_TypeDecl_reset(); 232 targetInterface_reset(); 233 type_reset(); 234 toParameterList_reset(); 235 } 236 /** 237 * @apilevel internal 238 * @declaredat ASTNode:54 239 */ 240 public void flushCollectionCache() { 241 super.flushCollectionCache(); 242 } 243 /** 244 * @apilevel internal 245 * @declaredat ASTNode:60 246 */ 247 public void flushRewriteCache() { 248 super.flushRewriteCache(); 249 } 250 /** 251 * @apilevel internal 252 * @declaredat ASTNode:66 253 */ 254 public MethodReference clone() throws CloneNotSupportedException { 255 MethodReference node = (MethodReference) super.clone(); 256 return node; 257 } 258 /** 259 * Create a deep copy of the AST subtree at this node. 260 * The copy is dangling, i.e. has no parent. 261 * @return dangling copy of the subtree at this node 262 * @apilevel low-level 263 * @deprecated Please use treeCopy or treeCopyNoTransform instead 264 * @declaredat ASTNode:77 265 */ 266 @Deprecated 267 public abstract MethodReference fullCopy(); 268 /** 269 * Create a deep copy of the AST subtree at this node. 270 * The copy is dangling, i.e. has no parent. 271 * @return dangling copy of the subtree at this node 272 * @apilevel low-level 273 * @declaredat ASTNode:85 274 */ 275 public abstract MethodReference treeCopyNoTransform(); 276 /** 277 * Create a deep copy of the AST subtree at this node. 278 * The subtree of this node is traversed to trigger rewrites before copy. 279 * The copy is dangling, i.e. has no parent. 280 * @return dangling copy of the subtree at this node 281 * @apilevel low-level 282 * @declaredat ASTNode:93 283 */ 284 public abstract MethodReference treeCopy(); 285 /** 286 * Replaces the TypeArgument list. 287 * @param list The new list node to be used as the TypeArgument list. 288 * @apilevel high-level 289 */ 290 public void setTypeArgumentList(List<Access> list) { 291 setChild(list, 0); 292 } 293 /** 294 * Retrieves the number of children in the TypeArgument list. 295 * @return Number of children in the TypeArgument list. 296 * @apilevel high-level 297 */ 298 public int getNumTypeArgument() { 299 return getTypeArgumentList().getNumChild(); 300 } 301 /** 302 * Retrieves the number of children in the TypeArgument list. 303 * Calling this method will not trigger rewrites. 304 * @return Number of children in the TypeArgument list. 305 * @apilevel low-level 306 */ 307 public int getNumTypeArgumentNoTransform() { 308 return getTypeArgumentListNoTransform().getNumChildNoTransform(); 309 } 310 /** 311 * Retrieves the element at index {@code i} in the TypeArgument list. 312 * @param i Index of the element to return. 313 * @return The element at position {@code i} in the TypeArgument list. 314 * @apilevel high-level 315 */ 316 public Access getTypeArgument(int i) { 317 return (Access) getTypeArgumentList().getChild(i); 318 } 319 /** 320 * Check whether the TypeArgument list has any children. 321 * @return {@code true} if it has at least one child, {@code false} otherwise. 322 * @apilevel high-level 323 */ 324 public boolean hasTypeArgument() { 325 return getTypeArgumentList().getNumChild() != 0; 326 } 327 /** 328 * Append an element to the TypeArgument list. 329 * @param node The element to append to the TypeArgument list. 330 * @apilevel high-level 331 */ 332 public void addTypeArgument(Access node) { 333 List<Access> list = (parent == null) ? getTypeArgumentListNoTransform() : getTypeArgumentList(); 334 list.addChild(node); 335 } 336 /** 337 * @apilevel low-level 338 */ 339 public void addTypeArgumentNoTransform(Access node) { 340 List<Access> list = getTypeArgumentListNoTransform(); 341 list.addChild(node); 342 } 343 /** 344 * Replaces the TypeArgument list element at index {@code i} with the new node {@code node}. 345 * @param node The new node to replace the old list element. 346 * @param i The list index of the node to be replaced. 347 * @apilevel high-level 348 */ 349 public void setTypeArgument(Access node, int i) { 350 List<Access> list = getTypeArgumentList(); 351 list.setChild(node, i); 352 } 353 /** 354 * Retrieves the TypeArgument list. 355 * @return The node representing the TypeArgument list. 356 * @apilevel high-level 357 */ 358 @ASTNodeAnnotation.ListChild(name="TypeArgument") 359 public List<Access> getTypeArgumentList() { 360 List<Access> list = (List<Access>) getChild(0); 361 return list; 362 } 363 /** 364 * Retrieves the TypeArgument list. 365 * <p><em>This method does not invoke AST transformations.</em></p> 366 * @return The node representing the TypeArgument list. 367 * @apilevel low-level 368 */ 369 public List<Access> getTypeArgumentListNoTransform() { 370 return (List<Access>) getChildNoTransform(0); 371 } 372 /** 373 * Retrieves the TypeArgument list. 374 * @return The node representing the TypeArgument list. 375 * @apilevel high-level 376 */ 377 public List<Access> getTypeArguments() { 378 return getTypeArgumentList(); 379 } 380 /** 381 * Retrieves the TypeArgument list. 382 * <p><em>This method does not invoke AST transformations.</em></p> 383 * @return The node representing the TypeArgument list. 384 * @apilevel low-level 385 */ 386 public List<Access> getTypeArgumentsNoTransform() { 387 return getTypeArgumentListNoTransform(); 388 } 389 /** 390 * Replaces the lexeme ID. 391 * @param value The new value for the lexeme ID. 392 * @apilevel high-level 393 */ 394 public void setID(String value) { 395 tokenString_ID = value; 396 } 397 /** 398 * @apilevel internal 399 */ 400 protected String tokenString_ID; 401 /** 402 */ 403 public int IDstart; 404 /** 405 */ 406 public int IDend; 407 /** 408 * JastAdd-internal setter for lexeme ID using the Beaver parser. 409 * @param symbol Symbol containing the new value for the lexeme ID 410 * @apilevel internal 411 */ 412 public void setID(beaver.Symbol symbol) { 413 if (symbol.value != null && !(symbol.value instanceof String)) 414 throw new UnsupportedOperationException("setID is only valid for String lexemes"); 415 tokenString_ID = (String)symbol.value; 416 IDstart = symbol.getStart(); 417 IDend = symbol.getEnd(); 418 } 419 /** 420 * Retrieves the value for the lexeme ID. 421 * @return The value for the lexeme ID. 422 * @apilevel high-level 423 */ 424 @ASTNodeAnnotation.Token(name="ID") 425 public String getID() { 426 return tokenString_ID != null ? tokenString_ID : ""; 427 } 428 /** 429 * @attribute syn 430 * @aspect MethodReference 431 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:212 432 */ 433 @ASTNodeAnnotation.Attribute 434 public abstract boolean congruentTo(FunctionDescriptor f); 435 /** 436 * @attribute syn 437 * @aspect MethodReference 438 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:253 439 */ 440 @ASTNodeAnnotation.Attribute 441 public abstract ArrayList<MethodDecl> potentiallyApplicableMethods(FunctionDescriptor f); 442 /** 443 * @attribute syn 444 * @aspect MethodReference 445 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:308 446 */ 447 @ASTNodeAnnotation.Attribute 448 public abstract MethodDecl exactCompileTimeDeclaration(); 449 /** 450 * @apilevel internal 451 */ 452 protected boolean isExact_computed = false; 453 /** 454 * @apilevel internal 455 */ 456 protected boolean isExact_value; 457 /** 458 * @apilevel internal 459 */ 460 private void isExact_reset() { 461 isExact_computed = false; 462 } 463 /** 464 * @attribute syn 465 * @aspect MethodReference 466 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:307 467 */ 468 @ASTNodeAnnotation.Attribute 469 public boolean isExact() { 470 ASTNode$State state = state(); 471 if (isExact_computed) { 472 return isExact_value; 473 } 474 boolean intermediate = state.INTERMEDIATE_VALUE; 475 state.INTERMEDIATE_VALUE = false; 476 int num = state.boundariesCrossed; 477 boolean isFinal = this.is$Final(); 478 isExact_value = exactCompileTimeDeclaration() != unknownMethod(); 479 if (isFinal && num == state().boundariesCrossed) { 480 isExact_computed = true; 481 } else { 482 } 483 state.INTERMEDIATE_VALUE |= intermediate; 484 485 return isExact_value; 486 } 487 /** 488 * @apilevel internal 489 */ 490 protected java.util.Map compatibleStrictContext_TypeDecl_values; 491 /** 492 * @apilevel internal 493 */ 494 private void compatibleStrictContext_TypeDecl_reset() { 495 compatibleStrictContext_TypeDecl_values = null; 496 } 497 /** 498 * @attribute syn 499 * @aspect MethodSignature18 500 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodSignature.jrag:32 501 */ 502 @ASTNodeAnnotation.Attribute 503 public boolean compatibleStrictContext(TypeDecl type) { 504 Object _parameters = type; 505 if (compatibleStrictContext_TypeDecl_values == null) compatibleStrictContext_TypeDecl_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 506 ASTNode$State state = state(); 507 if (compatibleStrictContext_TypeDecl_values.containsKey(_parameters)) { 508 return (Boolean) compatibleStrictContext_TypeDecl_values.get(_parameters); 509 } 510 boolean intermediate = state.INTERMEDIATE_VALUE; 511 state.INTERMEDIATE_VALUE = false; 512 int num = state.boundariesCrossed; 513 boolean isFinal = this.is$Final(); 514 boolean compatibleStrictContext_TypeDecl_value = compatibleStrictContext_compute(type); 515 if (isFinal && num == state().boundariesCrossed) { 516 compatibleStrictContext_TypeDecl_values.put(_parameters, compatibleStrictContext_TypeDecl_value); 517 } else { 518 } 519 state.INTERMEDIATE_VALUE |= intermediate; 520 521 return compatibleStrictContext_TypeDecl_value; 522 } 523 /** 524 * @apilevel internal 525 */ 526 private boolean compatibleStrictContext_compute(TypeDecl type) { 527 if (!type.isFunctionalInterface()) { 528 return false; 529 } 530 InterfaceDecl iDecl = (InterfaceDecl) type; 531 return congruentTo(iDecl.functionDescriptor()); 532 } 533 /** 534 * @apilevel internal 535 */ 536 protected java.util.Map compatibleLooseContext_TypeDecl_values; 537 /** 538 * @apilevel internal 539 */ 540 private void compatibleLooseContext_TypeDecl_reset() { 541 compatibleLooseContext_TypeDecl_values = null; 542 } 543 /** 544 * @attribute syn 545 * @aspect MethodSignature18 546 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodSignature.jrag:79 547 */ 548 @ASTNodeAnnotation.Attribute 549 public boolean compatibleLooseContext(TypeDecl type) { 550 Object _parameters = type; 551 if (compatibleLooseContext_TypeDecl_values == null) compatibleLooseContext_TypeDecl_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 552 ASTNode$State state = state(); 553 if (compatibleLooseContext_TypeDecl_values.containsKey(_parameters)) { 554 return (Boolean) compatibleLooseContext_TypeDecl_values.get(_parameters); 555 } 556 boolean intermediate = state.INTERMEDIATE_VALUE; 557 state.INTERMEDIATE_VALUE = false; 558 int num = state.boundariesCrossed; 559 boolean isFinal = this.is$Final(); 560 boolean compatibleLooseContext_TypeDecl_value = compatibleStrictContext(type); 561 if (isFinal && num == state().boundariesCrossed) { 562 compatibleLooseContext_TypeDecl_values.put(_parameters, compatibleLooseContext_TypeDecl_value); 563 } else { 564 } 565 state.INTERMEDIATE_VALUE |= intermediate; 566 567 return compatibleLooseContext_TypeDecl_value; 568 } 569 /** 570 * @apilevel internal 571 */ 572 protected java.util.Map pertinentToApplicability_Expr_BodyDecl_int_values; 573 /** 574 * @apilevel internal 575 */ 576 private void pertinentToApplicability_Expr_BodyDecl_int_reset() { 577 pertinentToApplicability_Expr_BodyDecl_int_values = null; 578 } 579 /** 580 * @attribute syn 581 * @aspect MethodSignature18 582 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodSignature.jrag:107 583 */ 584 @ASTNodeAnnotation.Attribute 585 public boolean pertinentToApplicability(Expr access, BodyDecl decl, int argIndex) { 586 java.util.List _parameters = new java.util.ArrayList(3); 587 _parameters.add(access); 588 _parameters.add(decl); 589 _parameters.add(argIndex); 590 if (pertinentToApplicability_Expr_BodyDecl_int_values == null) pertinentToApplicability_Expr_BodyDecl_int_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 591 ASTNode$State state = state(); 592 if (pertinentToApplicability_Expr_BodyDecl_int_values.containsKey(_parameters)) { 593 return (Boolean) pertinentToApplicability_Expr_BodyDecl_int_values.get(_parameters); 594 } 595 boolean intermediate = state.INTERMEDIATE_VALUE; 596 state.INTERMEDIATE_VALUE = false; 597 int num = state.boundariesCrossed; 598 boolean isFinal = this.is$Final(); 599 boolean pertinentToApplicability_Expr_BodyDecl_int_value = pertinentToApplicability_compute(access, decl, argIndex); 600 if (isFinal && num == state().boundariesCrossed) { 601 pertinentToApplicability_Expr_BodyDecl_int_values.put(_parameters, pertinentToApplicability_Expr_BodyDecl_int_value); 602 } else { 603 } 604 state.INTERMEDIATE_VALUE |= intermediate; 605 606 return pertinentToApplicability_Expr_BodyDecl_int_value; 607 } 608 /** 609 * @apilevel internal 610 */ 611 private boolean pertinentToApplicability_compute(Expr access, BodyDecl decl, int argIndex) { 612 if (!isExact()) { 613 return false; 614 } 615 if (decl instanceof MethodDecl 616 && decl.isGeneric() 617 && !(access instanceof ParMethodAccess) 618 && ((MethodDecl) decl).genericDecl().getParameter(argIndex).type().isTypeVariable()) { 619 GenericMethodDecl genericDecl = ((MethodDecl) decl).genericDecl(); 620 TypeVariable typeVar = (TypeVariable) genericDecl.getParameter(argIndex).type(); 621 for (int i = 0; i < genericDecl.getNumTypeParameter(); i++) { 622 if (typeVar == genericDecl.getTypeParameter(i)) { 623 return false; 624 } 625 } 626 } else if (decl instanceof ConstructorDecl 627 && decl.isGeneric() 628 && !(access instanceof ParConstructorAccess) 629 && !(access instanceof ParSuperConstructorAccess) 630 && !(access instanceof ParClassInstanceExpr) 631 && ((ConstructorDecl) decl).genericDecl().getParameter(argIndex).type().isTypeVariable()) { 632 GenericConstructorDecl genericDecl = ((ConstructorDecl) decl).genericDecl(); 633 TypeVariable typeVar = (TypeVariable) genericDecl.getParameter(argIndex).type(); 634 for (int i = 0; i < genericDecl.getNumTypeParameter(); i++) { 635 if (typeVar == genericDecl.getTypeParameter(i)) { 636 return false; 637 } 638 } 639 } 640 return true; 641 } 642 /** 643 * @apilevel internal 644 */ 645 protected java.util.Map moreSpecificThan_TypeDecl_TypeDecl_values; 646 /** 647 * @apilevel internal 648 */ 649 private void moreSpecificThan_TypeDecl_TypeDecl_reset() { 650 moreSpecificThan_TypeDecl_TypeDecl_values = null; 651 } 652 /** 653 * Computes which type is more specific for a specific argument, as defined in 15.12.2.5 654 * @param type1 655 * @param type2 656 * @return {@code true} if type1 is more specific than type2, {@code false} otherwise 657 * @attribute syn 658 * @aspect MethodSignature18 659 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodSignature.jrag:233 660 */ 661 @ASTNodeAnnotation.Attribute 662 public boolean moreSpecificThan(TypeDecl type1, TypeDecl type2) { 663 java.util.List _parameters = new java.util.ArrayList(2); 664 _parameters.add(type1); 665 _parameters.add(type2); 666 if (moreSpecificThan_TypeDecl_TypeDecl_values == null) moreSpecificThan_TypeDecl_TypeDecl_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 667 ASTNode$State state = state(); 668 if (moreSpecificThan_TypeDecl_TypeDecl_values.containsKey(_parameters)) { 669 return (Boolean) moreSpecificThan_TypeDecl_TypeDecl_values.get(_parameters); 670 } 671 boolean intermediate = state.INTERMEDIATE_VALUE; 672 state.INTERMEDIATE_VALUE = false; 673 int num = state.boundariesCrossed; 674 boolean isFinal = this.is$Final(); 675 boolean moreSpecificThan_TypeDecl_TypeDecl_value = moreSpecificThan_compute(type1, type2); 676 if (isFinal && num == state().boundariesCrossed) { 677 moreSpecificThan_TypeDecl_TypeDecl_values.put(_parameters, moreSpecificThan_TypeDecl_TypeDecl_value); 678 } else { 679 } 680 state.INTERMEDIATE_VALUE |= intermediate; 681 682 return moreSpecificThan_TypeDecl_TypeDecl_value; 683 } 684 /** 685 * @apilevel internal 686 */ 687 private boolean moreSpecificThan_compute(TypeDecl type1, TypeDecl type2) { 688 if (super.moreSpecificThan(type1, type2)) { 689 return true; 690 } 691 if (!type1.isFunctionalInterface() || !type2.isFunctionalInterface()) { 692 return false; 693 } 694 if (type2.instanceOf(type1)) { 695 return false; 696 } 697 InterfaceDecl iDecl1 = (InterfaceDecl) type1; 698 InterfaceDecl iDecl2 = (InterfaceDecl) type2; 699 700 if (!isExact()) { 701 return false; 702 } 703 704 FunctionDescriptor f1 = iDecl1.functionDescriptor(); 705 FunctionDescriptor f2 = iDecl2.functionDescriptor(); 706 707 if (f1.method.arity() != f2.method.arity()) { 708 return false; 709 } 710 711 for (int i = 0; i < f1.method.getNumParameter(); i++) { 712 if (f1.method.getParameter(i).type() != f2.method.getParameter(i).type()) { 713 return false; 714 } 715 } 716 717 // First bullet 718 if (f2.method.type().isVoid()) { 719 return true; 720 } 721 722 // Second bullet 723 if (f1.method.type().instanceOf(f2.method.type())) { 724 return true; 725 } 726 727 // Third bullet 728 if (f1.method.type().isPrimitiveType() && f2.method.type().isReferenceType()) { 729 return exactCompileTimeDeclaration().type().isPrimitiveType(); 730 } 731 732 // Fourth bullet 733 if (f1.method.type().isReferenceType() && f2.method.type().isPrimitiveType()) { 734 return exactCompileTimeDeclaration().type().isReferenceType(); 735 } 736 737 return false; 738 } 739 /** 740 * @apilevel internal 741 */ 742 protected java.util.Map potentiallyCompatible_TypeDecl_BodyDecl_values; 743 /** 744 * @apilevel internal 745 */ 746 private void potentiallyCompatible_TypeDecl_BodyDecl_reset() { 747 potentiallyCompatible_TypeDecl_BodyDecl_values = null; 748 } 749 /** 750 * @attribute syn 751 * @aspect MethodSignature18 752 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodSignature.jrag:466 753 */ 754 @ASTNodeAnnotation.Attribute 755 public boolean potentiallyCompatible(TypeDecl type, BodyDecl candidateDecl) { 756 java.util.List _parameters = new java.util.ArrayList(2); 757 _parameters.add(type); 758 _parameters.add(candidateDecl); 759 if (potentiallyCompatible_TypeDecl_BodyDecl_values == null) potentiallyCompatible_TypeDecl_BodyDecl_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 760 ASTNode$State state = state(); 761 if (potentiallyCompatible_TypeDecl_BodyDecl_values.containsKey(_parameters)) { 762 return (Boolean) potentiallyCompatible_TypeDecl_BodyDecl_values.get(_parameters); 763 } 764 boolean intermediate = state.INTERMEDIATE_VALUE; 765 state.INTERMEDIATE_VALUE = false; 766 int num = state.boundariesCrossed; 767 boolean isFinal = this.is$Final(); 768 boolean potentiallyCompatible_TypeDecl_BodyDecl_value = potentiallyCompatible_compute(type, candidateDecl); 769 if (isFinal && num == state().boundariesCrossed) { 770 potentiallyCompatible_TypeDecl_BodyDecl_values.put(_parameters, potentiallyCompatible_TypeDecl_BodyDecl_value); 771 } else { 772 } 773 state.INTERMEDIATE_VALUE |= intermediate; 774 775 return potentiallyCompatible_TypeDecl_BodyDecl_value; 776 } 777 /** 778 * @apilevel internal 779 */ 780 private boolean potentiallyCompatible_compute(TypeDecl type, BodyDecl candidateDecl) { 781 if (type.isTypeVariable()) { 782 if (candidateDecl.isGeneric()) { 783 boolean foundTypeVariable = false; 784 List<TypeVariable> typeParams = candidateDecl.typeParameters(); 785 for (int i = 0; i < typeParams.getNumChild(); i++) { 786 if (type == typeParams.getChild(i)) { 787 foundTypeVariable = true; 788 break; 789 } 790 } 791 return foundTypeVariable; 792 } else { 793 return false; 794 } 795 } 796 797 if (!type.isFunctionalInterface()) { 798 return false; 799 } 800 return true; 801 } 802 /** 803 * @apilevel internal 804 */ 805 protected boolean isPolyExpression_computed = false; 806 /** 807 * @apilevel internal 808 */ 809 protected boolean isPolyExpression_value; 810 /** 811 * @apilevel internal 812 */ 813 private void isPolyExpression_reset() { 814 isPolyExpression_computed = false; 815 } 816 /** 817 * @attribute syn 818 * @aspect PolyExpressions 819 * @declaredat /home/jesper/git/extendj/java8/frontend/PolyExpressions.jrag:80 820 */ 821 @ASTNodeAnnotation.Attribute 822 public boolean isPolyExpression() { 823 ASTNode$State state = state(); 824 if (isPolyExpression_computed) { 825 return isPolyExpression_value; 826 } 827 boolean intermediate = state.INTERMEDIATE_VALUE; 828 state.INTERMEDIATE_VALUE = false; 829 int num = state.boundariesCrossed; 830 boolean isFinal = this.is$Final(); 831 isPolyExpression_value = true; 832 if (isFinal && num == state().boundariesCrossed) { 833 isPolyExpression_computed = true; 834 } else { 835 } 836 state.INTERMEDIATE_VALUE |= intermediate; 837 838 return isPolyExpression_value; 839 } 840 /** 841 * @apilevel internal 842 */ 843 protected java.util.Map assignConversionTo_TypeDecl_values; 844 /** 845 * @apilevel internal 846 */ 847 private void assignConversionTo_TypeDecl_reset() { 848 assignConversionTo_TypeDecl_values = null; 849 } 850 /** 851 * @attribute syn 852 * @aspect PolyExpressions 853 * @declaredat /home/jesper/git/extendj/java8/frontend/PolyExpressions.jrag:142 854 */ 855 @ASTNodeAnnotation.Attribute 856 public boolean assignConversionTo(TypeDecl type) { 857 Object _parameters = type; 858 if (assignConversionTo_TypeDecl_values == null) assignConversionTo_TypeDecl_values = new org.jastadd.util.RobustMap(new java.util.HashMap()); 859 ASTNode$State state = state(); 860 if (assignConversionTo_TypeDecl_values.containsKey(_parameters)) { 861 return (Boolean) assignConversionTo_TypeDecl_values.get(_parameters); 862 } 863 boolean intermediate = state.INTERMEDIATE_VALUE; 864 state.INTERMEDIATE_VALUE = false; 865 int num = state.boundariesCrossed; 866 boolean isFinal = this.is$Final(); 867 boolean assignConversionTo_TypeDecl_value = assignConversionTo_compute(type); 868 if (isFinal && num == state().boundariesCrossed) { 869 assignConversionTo_TypeDecl_values.put(_parameters, assignConversionTo_TypeDecl_value); 870 } else { 871 } 872 state.INTERMEDIATE_VALUE |= intermediate; 873 874 return assignConversionTo_TypeDecl_value; 875 } 876 /** 877 * @apilevel internal 878 */ 879 private boolean assignConversionTo_compute(TypeDecl type) { 880 if (!type.isFunctionalInterface()) { 881 return false; 882 } 883 FunctionDescriptor f = ((InterfaceDecl) type).functionDescriptor(); 884 return congruentTo(f); 885 } 886 /** 887 * @attribute syn 888 * @aspect Names 889 * @declaredat /home/jesper/git/extendj/java8/frontend/QualifiedNames.jrag:30 890 */ 891 @ASTNodeAnnotation.Attribute 892 public String name() { 893 String name_value = getID(); 894 895 return name_value; 896 } 897 /** 898 * @apilevel internal 899 */ 900 protected boolean targetInterface_computed = false; 901 /** 902 * @apilevel internal 903 */ 904 protected InterfaceDecl targetInterface_value; 905 /** 906 * @apilevel internal 907 */ 908 private void targetInterface_reset() { 909 targetInterface_computed = false; 910 targetInterface_value = null; 911 } 912 /** 913 * @attribute syn 914 * @aspect TargetType 915 * @declaredat /home/jesper/git/extendj/java8/frontend/TargetType.jrag:152 916 */ 917 @ASTNodeAnnotation.Attribute 918 public InterfaceDecl targetInterface() { 919 ASTNode$State state = state(); 920 if (targetInterface_computed) { 921 return targetInterface_value; 922 } 923 boolean intermediate = state.INTERMEDIATE_VALUE; 924 state.INTERMEDIATE_VALUE = false; 925 int num = state.boundariesCrossed; 926 boolean isFinal = this.is$Final(); 927 targetInterface_value = targetInterface_compute(); 928 if (isFinal && num == state().boundariesCrossed) { 929 targetInterface_computed = true; 930 } else { 931 } 932 state.INTERMEDIATE_VALUE |= intermediate; 933 934 return targetInterface_value; 935 } 936 /** 937 * @apilevel internal 938 */ 939 private InterfaceDecl targetInterface_compute() { 940 if (targetType().isNull()) { 941 return null; 942 } else if (!(targetType() instanceof InterfaceDecl)) { 943 return null; 944 } else { 945 return (InterfaceDecl) targetType(); 946 } 947 } 948 /** 949 * @apilevel internal 950 */ 951 protected boolean type_computed = false; 952 /** 953 * @apilevel internal 954 */ 955 protected TypeDecl type_value; 956 /** 957 * @apilevel internal 958 */ 959 private void type_reset() { 960 type_computed = false; 961 type_value = null; 962 } 963 /** 964 * @attribute syn 965 * @aspect TypeCheck 966 * @declaredat /home/jesper/git/extendj/java8/frontend/TypeCheck.jrag:75 967 */ 968 @ASTNodeAnnotation.Attribute 969 public TypeDecl type() { 970 ASTNode$State state = state(); 971 if (type_computed) { 972 return type_value; 973 } 974 boolean intermediate = state.INTERMEDIATE_VALUE; 975 state.INTERMEDIATE_VALUE = false; 976 int num = state.boundariesCrossed; 977 boolean isFinal = this.is$Final(); 978 type_value = type_compute(); 979 if (isFinal && num == state().boundariesCrossed) { 980 type_computed = true; 981 } else { 982 } 983 state.INTERMEDIATE_VALUE |= intermediate; 984 985 return type_value; 986 } 987 /** 988 * @apilevel internal 989 */ 990 private TypeDecl type_compute() { 991 // 15.13.1 992 if (!assignmentContext() && !castContext() && !invocationContext()) { 993 return unknownType(); 994 } 995 if (targetInterface() == null) { 996 return unknownType(); 997 } 998 999 InterfaceDecl iDecl = targetInterface(); 1000 if (!iDecl.isFunctional()) { 1001 return unknownType(); 1002 } 1003 1004 if (congruentTo(iDecl.functionDescriptor())) { 1005 return iDecl; 1006 } else { 1007 return unknownType(); 1008 } 1009 } 1010 /** 1011 * @apilevel internal 1012 */ 1013 protected boolean toParameterList_computed = false; 1014 /** 1015 * @apilevel internal 1016 */ 1017 protected List<ParameterDeclaration> toParameterList_value; 1018 /** 1019 * @apilevel internal 1020 */ 1021 private void toParameterList_reset() { 1022 toParameterList_computed = false; 1023 toParameterList_value = null; 1024 } 1025 /** 1026 * @attribute syn 1027 * @aspect MethodReferenceToClass 1028 * @declaredat /home/jesper/git/extendj/java8/backend/MethodReferenceToClass.jrag:82 1029 */ 1030 @ASTNodeAnnotation.Attribute 1031 public List<ParameterDeclaration> toParameterList() { 1032 ASTNode$State state = state(); 1033 if (toParameterList_computed) { 1034 return toParameterList_value; 1035 } 1036 boolean intermediate = state.INTERMEDIATE_VALUE; 1037 state.INTERMEDIATE_VALUE = false; 1038 int num = state.boundariesCrossed; 1039 boolean isFinal = this.is$Final(); 1040 toParameterList_value = toParameterList_compute(); 1041 if (isFinal && num == state().boundariesCrossed) { 1042 toParameterList_computed = true; 1043 } else { 1044 } 1045 state.INTERMEDIATE_VALUE |= intermediate; 1046 1047 return toParameterList_value; 1048 } 1049 /** 1050 * @apilevel internal 1051 */ 1052 private List<ParameterDeclaration> toParameterList_compute() { 1053 List<ParameterDeclaration> list = new List<ParameterDeclaration>(); 1054 for (int i = 0; i < targetInterface().functionDescriptor().method.getNumParameter(); i++) { 1055 TypeDecl paramType = targetInterface().functionDescriptor().method.getParameter(i).type(); 1056 String paramName = targetInterface().functionDescriptor().method.getParameter(i).name(); 1057 list.add(new ParameterDeclaration(new SyntheticTypeAccess(paramType), paramName)); 1058 } 1059 return list; 1060 } 1061 /** 1062 * @attribute inh 1063 * @aspect MethodReference 1064 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:30 1065 */ 1066 /** 1067 * @attribute inh 1068 * @aspect MethodReference 1069 * @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:30 1070 */ 1071 @ASTNodeAnnotation.Attribute 1072 public MethodDecl unknownMethod() { 1073 MethodDecl unknownMethod_value = getParent().Define_unknownMethod(this, null); 1074 1075 return unknownMethod_value; 1076 } 1077 /** 1078 * @declaredat /home/jesper/git/extendj/java4/frontend/SyntacticClassification.jrag:36 1079 * @apilevel internal 1080 */ 1081 public NameType Define_nameType(ASTNode caller, ASTNode child) { 1082 if (caller == getTypeArgumentListNoTransform()) { 1083 // @declaredat /home/jesper/git/extendj/java8/frontend/MethodReference.jrag:194 1084 int childIndex = caller.getIndexOfChild(child); 1085 return NameType.TYPE_NAME; 1086 } 1087 else { 1088 return getParent().Define_nameType(this, caller); 1089 } 1090 } 1091 protected boolean canDefine_nameType(ASTNode caller, ASTNode child) { 1092 return true; 1093 } 1094 /** 1095 * @apilevel internal 1096 */ 1097 public ASTNode rewriteTo() { 1098 return super.rewriteTo(); 1099 } 1100 }