use of com.redhat.ceylon.model.typechecker.model.Constructor in project ceylon-compiler by ceylon.
the class CeylonDoc method getIcons.
protected final List<String> getIcons(Object obj) {
List<String> icons = new ArrayList<String>();
if (obj instanceof Declaration) {
Declaration decl = (Declaration) obj;
Annotation deprecated = Util.findAnnotation(decl, "deprecated");
if (deprecated != null) {
icons.add("icon-decoration-deprecated");
}
if (decl instanceof ClassOrInterface || decl instanceof Constructor) {
if (decl instanceof Interface) {
icons.add("icon-interface");
if (Util.isEnumerated((ClassOrInterface) decl)) {
icons.add("icon-decoration-enumerated");
}
}
if (decl instanceof Class) {
Class klass = (Class) decl;
if (klass.isAnonymous()) {
icons.add("icon-object");
} else {
icons.add("icon-class");
}
if (klass.isAbstract()) {
icons.add("icon-decoration-abstract");
}
if (klass.isFinal() && !klass.isAnonymous() && !klass.isAnnotation()) {
icons.add("icon-decoration-final");
}
if (Util.isEnumerated(klass)) {
icons.add("icon-decoration-enumerated");
}
}
if (decl instanceof Constructor) {
icons.add("icon-class");
}
if (!decl.isShared()) {
icons.add("icon-decoration-local");
}
}
if (decl instanceof TypedDeclaration) {
if (decl.isShared()) {
icons.add("icon-shared-member");
} else {
icons.add("icon-local-member");
}
if (decl.isFormal()) {
icons.add("icon-decoration-formal");
}
if (decl.isActual()) {
Declaration refinedDeclaration = decl.getRefinedDeclaration();
if (refinedDeclaration != null) {
if (refinedDeclaration.isFormal()) {
icons.add("icon-decoration-impl");
}
if (refinedDeclaration.isDefault()) {
icons.add("icon-decoration-over");
}
}
}
if (((TypedDeclaration) decl).isVariable()) {
icons.add("icon-decoration-variable");
}
}
if (decl instanceof TypeAlias || decl instanceof NothingType) {
icons.add("icon-type-alias");
}
if (decl.isAnnotation()) {
icons.add("icon-decoration-annotation");
}
}
if (obj instanceof Package) {
Package pkg = (Package) obj;
icons.add("icon-package");
if (!pkg.isShared()) {
icons.add("icon-decoration-local");
}
}
if (obj instanceof ModuleImport) {
ModuleImport moduleImport = (ModuleImport) obj;
icons.add("icon-module");
if (moduleImport.isExport()) {
icons.add("icon-module-exported-decoration");
}
if (moduleImport.isOptional()) {
icons.add("icon-module-optional-decoration");
}
}
if (obj instanceof Module) {
icons.add("icon-module");
}
return icons;
}
use of com.redhat.ceylon.model.typechecker.model.Constructor in project ceylon-compiler by ceylon.
the class ClassOrPackageDoc method doc.
protected final void doc(String name, Declaration d) throws IOException {
String declarationName = Util.getDeclarationName(d);
boolean alias = Util.nullSafeCompare(name, declarationName) != 0;
// put the id on the td because IE8 doesn't support id attributes on tr (yeah right)
open("tr");
open("td id='" + name + "' nowrap");
writeIcon(d);
if (!(d instanceof Constructor)) {
around("code class='decl-label'", name);
close("td");
open("td");
}
writeLinkOneSelf(d);
if (alias) {
writeTagged(d);
writeAlias(d);
} else {
writeLinkSource(d);
writeTagged(d);
if (d instanceof Functional) {
writeParameterLinksIfRequired((Functional) d);
}
open("code class='signature'");
around("span class='modifiers'", getModifiers(d));
write(" ");
if (!ModelUtil.isConstructor(d)) {
if (d instanceof Functional && ((Functional) d).isDeclaredVoid()) {
around("span class='void'", "void");
} else if (d instanceof TypedDeclaration) {
linkRenderer().to(((TypedDeclaration) d).getType()).useScope(d).write();
} else {
linkRenderer().to(d).useScope(d).write();
}
}
write(" ");
open("span class='identifier'");
write(name);
close("span");
if (isConstantValue(d)) {
writeConstantValue((Value) d);
}
if (d instanceof Generic) {
Generic f = (Generic) d;
writeTypeParameters(f.getTypeParameters(), d);
}
if (d instanceof Functional) {
writeParameterList((Functional) d, d);
}
if (d instanceof Generic) {
Generic f = (Generic) d;
writeTypeParametersConstraints(f.getTypeParameters(), d);
}
if (d instanceof Value) {
Setter setter = ((Value) d).getSetter();
if (setter != null && Util.getAnnotation(setter.getUnit(), setter.getAnnotations(), "doc") != null) {
tool.warningSetterDoc(d.getQualifiedNameString(), d);
}
}
close("code");
writeDescription(d);
}
close("td");
close("tr");
}
use of com.redhat.ceylon.model.typechecker.model.Constructor in project ceylon-compiler by ceylon.
the class ExpressionTransformer method appendDeclarationLiteralForAnnotation.
/**
* Appends into the given builder a String representation of the given
* declaration, suitable for parsing my the DeclarationParser.
*/
private static void appendDeclarationLiteralForAnnotation(Declaration decl, StringBuilder sb) {
Scope container = decl.getContainer();
while (true) {
if (container instanceof Declaration) {
appendDeclarationLiteralForAnnotation((Declaration) container, sb);
sb.append(".");
break;
} else if (container instanceof Package) {
appendDeclarationLiteralForAnnotation((Package) container, sb);
sb.append(":");
break;
}
container = container.getContainer();
}
if (decl instanceof Class) {
sb.append("C").append(decl.getName());
} else if (decl instanceof Interface) {
sb.append("I").append(decl.getName());
} else if (decl instanceof TypeAlias) {
sb.append("A").append(decl.getName());
} else if (decl instanceof Value) {
sb.append("V").append(decl.getName());
} else if (decl instanceof Function) {
sb.append("F").append(decl.getName());
} else if (decl instanceof TypeParameter) {
sb.append("P").append(decl.getName());
} else if (decl instanceof Constructor) {
sb.append("c").append(decl.getName());
} else {
throw BugException.unhandledDeclarationCase(decl);
}
}
use of com.redhat.ceylon.model.typechecker.model.Constructor in project ceylon-compiler by ceylon.
the class ExpressionTransformer method transformMemberExpression.
private JCExpression transformMemberExpression(Tree.StaticMemberOrTypeExpression expr, JCExpression primaryExpr, TermTransformer transformer) {
JCExpression result = null;
// do not throw, an error will already have been reported
Declaration decl = expr.getDeclaration();
if (decl == null) {
return makeErroneous(expr, "compiler bug: expression with no declaration");
}
// creating a tmp variable (in which case we have a substitution for it)
while (decl instanceof TypedDeclaration) {
TypedDeclaration typedDecl = (TypedDeclaration) decl;
if (!naming.isSubstituted(decl) && typedDecl.getOriginalDeclaration() != null) {
decl = ((TypedDeclaration) decl).getOriginalDeclaration();
} else {
break;
}
}
// (the header might look like a field while the implementation is a getter)
if (decl.isNativeHeader()) {
Declaration d = ModelUtil.getNativeDeclaration(decl, Backend.Java);
if (d != null) {
decl = d;
}
}
// Explanation: primaryExpr and qualExpr both specify what is to come before the selector
// but the important difference is that primaryExpr is used for those situations where
// the result comes from the actual Ceylon code while qualExpr is used for those situations
// where we need to refer to synthetic objects (like wrapper classes for toplevel methods)
JCExpression qualExpr = null;
String selector = null;
// true for Java interop using fields, and for super constructor parameters, which must use
// parameters rather than getter methods
boolean mustUseField = false;
// true for default parameter methods
boolean mustUseParameter = false;
if (decl instanceof Functional && (!(decl instanceof Class) || ((Class) decl).getParameterList() != null) && (!(decl instanceof Function) || !decl.isParameter() || functionalParameterRequiresCallable((Function) decl, expr)) && isFunctionalResult(expr.getTypeModel())) {
result = transformFunctional(expr, (Functional) decl);
} else if (Decl.isGetter(decl)) {
// invoke the getter
if (decl.isToplevel()) {
primaryExpr = null;
qualExpr = naming.makeName((Value) decl, Naming.NA_FQ | Naming.NA_WRAPPER | Naming.NA_MEMBER);
selector = null;
} else if (Decl.withinClassOrInterface(decl) && !Decl.isLocalToInitializer(decl)) {
selector = naming.selector((Value) decl);
} else {
// method local attr
if (!isRecursiveReference(expr)) {
primaryExpr = naming.makeQualifiedName(primaryExpr, (Value) decl, Naming.NA_Q_LOCAL_INSTANCE);
}
selector = naming.selector((Value) decl);
}
} else if (Decl.isValueOrSharedOrCapturedParam(decl)) {
if (decl.isToplevel()) {
// ERASURE
if (isNullValue(decl)) {
result = makeNull();
} else if (isBooleanTrue(decl)) {
result = makeBoolean(true);
} else if (isBooleanFalse(decl)) {
result = makeBoolean(false);
} else {
// it's a toplevel attribute
primaryExpr = naming.makeName((TypedDeclaration) decl, Naming.NA_FQ | Naming.NA_WRAPPER);
selector = naming.selector((TypedDeclaration) decl);
}
} else if (Decl.isClassAttribute(decl) || Decl.isClassParameter(decl)) {
mustUseField = Decl.isJavaField(decl) || (isWithinSuperInvocation() && primaryExpr == null && withinSuperInvocation == decl.getContainer());
mustUseParameter = (primaryExpr == null && isWithinDefaultParameterExpression(decl.getContainer()));
if (mustUseField || mustUseParameter) {
if (decl instanceof FieldValue) {
selector = ((FieldValue) decl).getRealName();
} else if (isWithinSuperInvocation() && ((Value) decl).isVariable() && ((Value) decl).isCaptured()) {
selector = Naming.getAliasedParameterName(((Value) decl).getInitializerParameter());
} else {
selector = decl.getName();
}
} else {
// invoke the getter, using the Java interop form of Util.getGetterName because this is the only case
// (Value inside a Class) where we might refer to JavaBean properties
selector = naming.selector((TypedDeclaration) decl);
}
} else if (decl.isCaptured() || decl.isShared()) {
TypedDeclaration typedDecl = ((TypedDeclaration) decl);
TypeDeclaration typeDecl = typedDecl.getType().getDeclaration();
mustUseField = Decl.isBoxedVariable((TypedDeclaration) decl);
if (Decl.isLocalNotInitializer(typeDecl) && typeDecl.isAnonymous() && // we need the box if it's a captured object
!typedDecl.isSelfCaptured()) {
// accessing a local 'object' declaration, so don't need a getter
} else if (decl.isCaptured() && !((TypedDeclaration) decl).isVariable() && // captured objects are never variable but need the box
!typedDecl.isSelfCaptured()) {
// accessing a local that is not getter wrapped
} else {
primaryExpr = naming.makeQualifiedName(primaryExpr, (TypedDeclaration) decl, Naming.NA_Q_LOCAL_INSTANCE);
selector = naming.selector((TypedDeclaration) decl);
}
}
} else if (Decl.isMethodOrSharedOrCapturedParam(decl)) {
mustUseParameter = (primaryExpr == null && decl.isParameter() && isWithinDefaultParameterExpression(decl.getContainer()));
if (!decl.isParameter() && (Decl.isLocalNotInitializer(decl) || (Decl.isLocalToInitializer(decl) && ((Function) decl).isDeferred()))) {
primaryExpr = null;
int flags = Naming.NA_MEMBER;
if (!isRecursiveReference(expr)) {
// Only want to quote the method name
// e.g. enum.$enum()
flags |= Naming.NA_WRAPPER_UNQUOTED;
} else if (!isReferenceInSameScope(expr)) {
// always qualify it with this
flags |= Naming.NA_WRAPPER | Naming.NA_WRAPPER_WITH_THIS;
}
qualExpr = naming.makeName((Function) decl, flags);
selector = null;
} else if (decl.isToplevel()) {
primaryExpr = null;
qualExpr = naming.makeName((Function) decl, Naming.NA_FQ | Naming.NA_WRAPPER | Naming.NA_MEMBER);
selector = null;
} else if (!isWithinInvocation()) {
selector = null;
} else {
// not toplevel, not within method, must be a class member
selector = naming.selector((Function) decl);
}
}
boolean isCtor = decl instanceof Function && ((Function) decl).getTypeDeclaration() instanceof Constructor;
if (result == null) {
boolean useGetter = !(decl instanceof Function || isCtor) && !mustUseField && !mustUseParameter;
if (qualExpr == null && selector == null && !(isCtor)) {
useGetter = Decl.isClassAttribute(decl) && CodegenUtil.isErasedAttribute(decl.getName());
if (useGetter) {
selector = naming.selector((TypedDeclaration) decl);
} else {
selector = naming.substitute(decl);
}
}
if (qualExpr == null) {
qualExpr = primaryExpr;
}
// cases
if (!mustUseParameter) {
qualExpr = addQualifierForObjectMembersOfInterface(expr, decl, qualExpr);
qualExpr = addInterfaceImplAccessorIfRequired(qualExpr, expr, decl);
qualExpr = addThisOrObjectQualifierIfRequired(qualExpr, expr, decl);
if (qualExpr == null && needDollarThis(expr)) {
qualExpr = makeQualifiedDollarThis((Tree.BaseMemberExpression) expr);
}
}
if (qualExpr == null && (decl.isStaticallyImportable() || (decl instanceof Value && Decl.isEnumeratedConstructor((Value) decl))) && // and not classes
decl.getContainer() instanceof TypeDeclaration) {
qualExpr = naming.makeTypeDeclarationExpression(null, (TypeDeclaration) decl.getContainer(), DeclNameFlag.QUALIFIED);
}
if (Decl.isPrivateAccessRequiringUpcast(expr)) {
qualExpr = makePrivateAccessUpcast(expr, qualExpr);
}
if (transformer != null) {
if (decl instanceof TypedDeclaration && ((TypedDeclaration) decl).getType().isTypeConstructor()) {
// This is a bit of a hack, but we're "invoking a type constructor"
// so recurse to get the applied expression.
qualExpr = transformMemberExpression(expr, qualExpr, null);
selector = null;
}
result = transformer.transform(qualExpr, selector);
} else {
Tree.Primary qmePrimary = null;
if (expr instanceof Tree.QualifiedMemberOrTypeExpression) {
qmePrimary = ((Tree.QualifiedMemberOrTypeExpression) expr).getPrimary();
}
boolean safeMemberJavaArray = expr instanceof Tree.QualifiedMemberExpression && ((Tree.QualifiedMemberExpression) expr).getMemberOperator() instanceof Tree.SafeMemberOp && isJavaArray(qmePrimary.getTypeModel());
if ((safeMemberJavaArray || Decl.isValueTypeDecl(qmePrimary)) && // Safe operators always work on boxed things, so don't use value types
(safeMemberJavaArray || (expr instanceof Tree.QualifiedMemberOrTypeExpression == false) || ((Tree.QualifiedMemberOrTypeExpression) expr).getMemberOperator() instanceof Tree.MemberOp) && // We never want to use value types on boxed things, unless they are java arrays
(CodegenUtil.isUnBoxed(qmePrimary) || isJavaArray(qmePrimary.getTypeModel())) && // Java arrays length property does not go via value types
(!isJavaArray(qmePrimary.getTypeModel()) || (!"length".equals(selector) && !"hashCode".equals(selector)))) {
JCExpression primTypeExpr = makeJavaType(qmePrimary.getTypeModel(), JT_NO_PRIMITIVES | JT_VALUE_TYPE);
result = makeQualIdent(primTypeExpr, selector);
result = make().Apply(List.<JCTree.JCExpression>nil(), result, List.<JCTree.JCExpression>of(qualExpr));
} else if (expr instanceof Tree.QualifiedMemberOrTypeExpression && isThrowableMessage((Tree.QualifiedMemberOrTypeExpression) expr)) {
result = utilInvocation().throwableMessage(qualExpr);
} else if (expr instanceof Tree.QualifiedMemberOrTypeExpression && isThrowableSuppressed((Tree.QualifiedMemberOrTypeExpression) expr)) {
result = utilInvocation().suppressedExceptions(qualExpr);
} else {
result = makeQualIdent(qualExpr, selector);
if (useGetter) {
result = make().Apply(List.<JCTree.JCExpression>nil(), result, List.<JCTree.JCExpression>nil());
}
}
}
}
if (transformer == null && decl instanceof TypedDeclaration && ((TypedDeclaration) decl).getType().isTypeConstructor() && !expr.getTypeArguments().getTypeModels().isEmpty()) {
// applying a type constructor
ListBuffer<JCExpression> tds = ListBuffer.lb();
for (Type t : expr.getTypeArguments().getTypeModels()) {
tds.add(makeReifiedTypeArgument(t));
}
result = make().Apply(null, makeQualIdent(result, Naming.Unfix.apply.toString()), List.<JCExpression>of(make().NewArray(make().Type(syms().ceylonTypeDescriptorType), List.<JCExpression>nil(), tds.toList())));
}
return result;
}
use of com.redhat.ceylon.model.typechecker.model.Constructor in project ceylon-compiler by ceylon.
the class ExpressionTransformer method transformQualifiedMemberPrimary.
JCExpression transformQualifiedMemberPrimary(Tree.QualifiedMemberOrTypeExpression expr) {
if (expr.getTarget() == null)
return makeErroneous(expr, "compiler bug: " + // make sure we don't die of a missing declaration too
(expr.getDeclaration() != null ? expr.getDeclaration().getName() : expr) + " has a null target");
// do not consider the primary to be an invocation since in foo.x() we're invoking x, not foo.
boolean previousWithinInvocation = withinInvocation(false);
try {
// consider package qualifiers as non-prefixed, we always qualify them anyways, this is
// only useful for the typechecker resolving
Tree.Primary primary = expr.getPrimary();
if (Decl.isConstructor(expr.getDeclaration())) {
Constructor ctor = Decl.getConstructor(expr.getDeclaration());
if (primary instanceof Tree.QualifiedMemberOrTypeExpression) {
// foo.Class.Ctor => foo
primary = ((Tree.QualifiedMemberOrTypeExpression) primary).getPrimary();
} else if (primary instanceof Tree.BaseMemberExpression) {
// foo.member.Ctor => foo
} else if (primary instanceof Tree.BaseTypeExpression) {
// Class.Ctor => null
return null;
}
}
if (isPackage(primary))
return null;
Type type = expr.getTarget().getQualifyingType();
if (expr.getMemberOperator() instanceof Tree.SafeMemberOp && !isOptional(type)) {
Type optionalType = typeFact().getOptionalType(type);
optionalType.setUnderlyingType(type.getUnderlyingType());
type = optionalType;
}
BoxingStrategy boxing = expr.getMemberOperator() instanceof Tree.SafeMemberOp == false && Decl.isValueTypeDecl(primary) && CodegenUtil.isUnBoxed(primary) ? BoxingStrategy.UNBOXED : BoxingStrategy.BOXED;
JCExpression result;
if (isSuper(primary)) {
result = transformSuper(expr);
} else if (isSuperOf(primary)) {
result = transformSuperOf(expr, expr.getPrimary(), expr.getDeclaration().getName());
} else if (isThis(primary) && !expr.getDeclaration().isCaptured() && !expr.getDeclaration().isShared() && Decl.getDeclarationScope(expr.getScope()) instanceof Constructor) {
result = null;
} else if (Decl.isJavaStaticOrInterfacePrimary(primary)) {
// Java static field or method access
result = transformJavaStaticOrInterfaceMember((Tree.QualifiedMemberOrTypeExpression) primary, expr.getTypeModel());
} else {
result = transformExpression(primary, boxing, type);
}
return result;
} finally {
withinInvocation(previousWithinInvocation);
}
}
Aggregations