001    package org.mesopotamia.lang.java;
002    
003    import java.util.Iterator;
004    import java.util.List;
005    
006    import org.mesopotamia.MesopotamiaException;
007    import org.mesopotamia.NodeData;
008    import org.mesopotamia.RepositoryLanguage;
009    import org.mesopotamia.Scan;
010    import org.mesopotamia.lang.java.ref.MethodInfo;
011    import org.mesopotamia.lang.java.ref.Reference;
012    import org.mesopotamia.lang.java.ref.Scope;
013    import org.mesopotamia.lang.java.ref.TypeInfo;
014    import org.mesopotamia.lang.java.ref.TypeSpecInfo;
015    import org.w3c.dom.Element;
016    
017    import biz.hammurapi.util.CollectionVisitable;
018    import biz.hammurapi.util.Visitor;
019    
020    @SuppressWarnings("unchecked")
021    public class ExplicitSuperConstructorInvocation extends PostfixExpression implements Reference<MethodInfo> {
022    
023            public ExplicitSuperConstructorInvocation(NodeData xData, Class<?> context,
024                            Scan scan, RepositoryLanguage language, Object environment) throws MesopotamiaException {
025                    super(xData, context, scan, language, environment);
026    
027                    // Select attributes
028                    if (language.supportsTokenName("TYPE_ARGUMENTS")) {
029                            TypeArguments = select(TypeArgument.class, "TYPE_ARGUMENTS/TYPE_ARGUMENT");
030                    }
031                    Arguments = select(Expression.class, "ELIST/*");
032    
033            }
034    
035            public void toDom(Element holder) {
036                    super.toDom(holder);
037    
038                    // Serialize attributes
039                    setElement(holder, "TypeArguments", TypeArguments);
040                    setElement(holder, "Arguments", Arguments);
041            }
042    
043            // Attributes
044            private List<TypeArgument> TypeArguments = emptyList;
045    
046            private List<Expression> Arguments;
047    
048            // Accessors
049            public List<TypeArgument> getTypeArguments() {
050                    return TypeArguments;
051            }
052    
053            public List<Expression> getArguments() {
054                    return Arguments;
055            }
056    
057            protected void acceptChildren(Visitor visitor) {
058                    super.acceptChildren(visitor);
059                    // Visiting non-text attributes
060                    new CollectionVisitable(TypeArguments, false).accept(visitor);
061                    new CollectionVisitable(Arguments, false).accept(visitor);
062            }
063    
064            @Override
065            public TypeSpecInfo getTypeSpecInfo() {
066                    return new TypeSpecInfo() {
067    
068                            public int getDimensions() {
069                                    return 0;
070                            }
071    
072                            public TypeInfo getTypeInfo() {
073                                    return Void.VOID_INFO;
074                            }
075                            
076                    };
077            }
078    
079            /**
080             * Returns constructor info.
081             */
082            public MethodInfo getInfo() {           
083                    List<Expression> args = getArguments();
084                    String[] argumentTypes = new String[args.size()];
085                    Iterator<Expression> it = args.iterator();
086                    for (int i=0; it.hasNext(); ++i) {
087                            argumentTypes[i] = TypeSpecification.toString(it.next().getTypeSpecInfo());
088                    }
089                    
090                    ClassDefinition cd=findParent(ClassDefinition.class);
091                    if (cd==null) {
092                            return null;
093                    }
094                    
095                    String ext = cd.getExtends();
096                    if (ext == null) {
097                            return null;
098                    }
099                    
100                    Scope scope = cd.findParent(Scope.class);
101                    if (scope == null) {
102                            return null;
103                    }
104                    
105                    TypeInfo ti = scope.findType(ext);
106                    return ti==null ? null : ti.findConstructor(argumentTypes);             
107            }
108                    
109    }