JavaDescriptorResolver.java 78.1 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
/*
 * Copyright 2010-2012 JetBrains s.r.o.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

17 18
package org.jetbrains.jet.lang.resolve.java;

19
import com.google.common.collect.Lists;
A
Andrey Breslav 已提交
20
import com.google.common.collect.Maps;
A
Andrey Breslav 已提交
21
import com.google.common.collect.Sets;
22
import com.intellij.openapi.project.Project;
23
import com.intellij.openapi.util.Pair;
24
import com.intellij.openapi.vfs.VirtualFile;
25
import com.intellij.psi.*;
26
import com.intellij.psi.impl.compiled.ClsClassImpl;
27
import com.intellij.psi.search.DelegatingGlobalSearchScope;
28
import com.intellij.psi.search.GlobalSearchScope;
29
import jet.typeinfo.TypeInfoVariance;
30 31
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
32
import org.jetbrains.jet.lang.descriptors.*;
A
Andrey Breslav 已提交
33
import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor;
34
import org.jetbrains.jet.lang.psi.JetPsiUtil;
35
import org.jetbrains.jet.lang.resolve.BindingContext;
36
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
S
Stepan Koltsov 已提交
37
import org.jetbrains.jet.lang.resolve.FqName;
38
import org.jetbrains.jet.lang.resolve.OverrideResolver;
39
import org.jetbrains.jet.lang.resolve.constants.*;
M
Maxim Shafirov 已提交
40
import org.jetbrains.jet.lang.resolve.java.alt.AltClassFinder;
41
import org.jetbrains.jet.lang.resolve.java.kt.JetClassAnnotation;
42
import org.jetbrains.jet.lang.types.*;
S
Stepan Koltsov 已提交
43
import org.jetbrains.jet.lang.types.lang.JetStandardClasses;
44
import org.jetbrains.jet.lang.types.lang.JetStandardLibrary;
45
import org.jetbrains.jet.plugin.JetFileType;
46
import org.jetbrains.jet.rt.signature.JetSignatureAdapter;
47 48 49
import org.jetbrains.jet.rt.signature.JetSignatureExceptionsAdapter;
import org.jetbrains.jet.rt.signature.JetSignatureReader;
import org.jetbrains.jet.rt.signature.JetSignatureVisitor;
50

51
import javax.inject.Inject;
52
import java.util.*;
53 54 55 56 57

/**
 * @author abreslav
 */
public class JavaDescriptorResolver {
58
    
S
Stepan Koltsov 已提交
59
    public static final String JAVA_ROOT = "<java_root>";
60

S
Stepan Koltsov 已提交
61 62
    public static final ModuleDescriptor FAKE_ROOT_MODULE = new ModuleDescriptor(JAVA_ROOT);

63 64
    /*package*/ static final DeclarationDescriptor JAVA_METHOD_TYPE_PARAMETER_PARENT = new DeclarationDescriptorImpl(null, Collections.<AnnotationDescriptor>emptyList(), "<java_generic_method>") {

65 66
        @Override
        public DeclarationDescriptor substitute(TypeSubstitutor substitutor) {
67
            throw new UnsupportedOperationException();
68 69
        }

70 71
        @Override
        public <R, D> R accept(DeclarationDescriptorVisitor<R, D> visitor, D data) {
72
            return visitor.visitDeclarationDescriptor(this, data);
73 74 75
        }
    };

A
Andrey Breslav 已提交
76
    /*package*/ static final DeclarationDescriptor JAVA_CLASS_OBJECT = new DeclarationDescriptorImpl(null, Collections.<AnnotationDescriptor>emptyList(), "<java_class_object_emulation>") {
A
Andrey Breslav 已提交
77 78 79
        @NotNull
        @Override
        public DeclarationDescriptor substitute(TypeSubstitutor substitutor) {
80
            throw new UnsupportedOperationException();
A
Andrey Breslav 已提交
81 82 83 84 85 86 87
        }

        @Override
        public <R, D> R accept(DeclarationDescriptorVisitor<R, D> visitor, D data) {
            return visitor.visitDeclarationDescriptor(this, data);
        }
    };
88 89 90 91 92
    
    private enum TypeParameterDescriptorOrigin {
        JAVA,
        KOTLIN,
    }
93

94 95
    public static class TypeParameterDescriptorInitialization {
        @NotNull
96
        private final TypeParameterDescriptorOrigin origin;
97 98 99
        @NotNull
        final TypeParameterDescriptor descriptor;
        final PsiTypeParameter psiTypeParameter;
100 101 102 103
        @Nullable
        private final List<JetType> upperBoundsForKotlin;
        @Nullable
        private final List<JetType> lowerBoundsForKotlin;
104

105
        private TypeParameterDescriptorInitialization(@NotNull TypeParameterDescriptor descriptor, @NotNull PsiTypeParameter psiTypeParameter) {
106
            this.origin = TypeParameterDescriptorOrigin.JAVA;
107
            this.descriptor = descriptor;
108
            this.psiTypeParameter = psiTypeParameter;
109 110 111 112
            this.upperBoundsForKotlin = null;
            this.lowerBoundsForKotlin = null;
        }

113
        private TypeParameterDescriptorInitialization(@NotNull TypeParameterDescriptor descriptor, @NotNull PsiTypeParameter psiTypeParameter,
114 115 116
                List<JetType> upperBoundsForKotlin, List<JetType> lowerBoundsForKotlin) {
            this.origin = TypeParameterDescriptorOrigin.KOTLIN;
            this.descriptor = descriptor;
117
            this.psiTypeParameter = psiTypeParameter;
118 119
            this.upperBoundsForKotlin = upperBoundsForKotlin;
            this.lowerBoundsForKotlin = lowerBoundsForKotlin;
120 121
        }
    }
122 123


124
    private static abstract class ResolverScopeData {
125
        protected boolean kotlin;
126 127
        
        private Map<String, NamedMembers> namedMembersMap;
128 129 130
        
        @NotNull
        public abstract List<TypeParameterDescriptor> getTypeParameters();
131
    }
A
Andrey Breslav 已提交
132

133 134 135 136
    static abstract class ResolverClassData extends ResolverScopeData {

        @NotNull
        public abstract ClassDescriptor getClassDescriptor();
137 138 139 140 141 142

        @NotNull
        @Override
        public List<TypeParameterDescriptor> getTypeParameters() {
            return getClassDescriptor().getTypeConstructor().getParameters();
        }
143 144
    }

145
    /** Class with instance members */
146 147 148 149 150
    static class ResolverBinaryClassData extends ResolverClassData {

        ResolverBinaryClassData() {
        }

151
        private MutableClassDescriptorLite classDescriptor;
152

153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170
        List<TypeParameterDescriptorInitialization> typeParameters;

        @Override
        @NotNull
        public ClassDescriptor getClassDescriptor() {
            return classDescriptor;
        }
    }

    static class ResolverSrcClassData extends ResolverClassData {
        @NotNull
        private final ClassDescriptor classDescriptor;

        ResolverSrcClassData(@NotNull ClassDescriptor classDescriptor) {
            this.classDescriptor = classDescriptor;
        }

        @Override
171 172 173 174 175 176
        @NotNull
        public ClassDescriptor getClassDescriptor() {
            return classDescriptor;
        }
    }

177
    /** Either package or class with static members */
178
    private static class ResolverNamespaceData extends ResolverScopeData {
179 180 181 182 183 184
        private JavaNamespaceDescriptor namespaceDescriptor;

        @NotNull
        public NamespaceDescriptor getNamespaceDescriptor() {
            return namespaceDescriptor;
        }
185 186 187 188 189 190

        @NotNull
        @Override
        public List<TypeParameterDescriptor> getTypeParameters() {
            return new ArrayList<TypeParameterDescriptor>(0);
        }
191 192
    }

S
Stepan Koltsov 已提交
193 194
    protected final Map<FqName, ResolverBinaryClassData> classDescriptorCache = Maps.newHashMap();
    protected final Map<FqName, ResolverNamespaceData> namespaceDescriptorCacheByFqn = Maps.newHashMap();
195 196
    protected final Map<PsiElement, ResolverNamespaceData> namespaceDescriptorCache = Maps.newHashMap();

197 198 199 200 201
    protected JavaPsiFacade javaFacade;
    protected Project project;
    protected GlobalSearchScope javaSearchScope ;
    protected JavaSemanticServices semanticServices;
    private AltClassFinder altClassFinder;
202

203 204 205 206
    @Inject
    public void setProject(Project project) {
        this.project = project;
        this.altClassFinder = new AltClassFinder(project);
207 208 209 210 211 212
        this.javaSearchScope = new DelegatingGlobalSearchScope(GlobalSearchScope.allScope(project)) {
            @Override
            public boolean contains(VirtualFile file) {
                return myBaseScope.contains(file) && file.getFileType() != JetFileType.INSTANCE;
            }
        };
213 214 215 216 217
        this.javaFacade = JavaPsiFacade.getInstance(project);
    }

    @Inject
    public void setSemanticServices(JavaSemanticServices semanticServices) {
218 219
        this.semanticServices = semanticServices;
    }
220 221 222



223
    @Nullable
224
    ResolverClassData resolveClassData(@NotNull PsiClass psiClass, @NotNull DescriptorSearchRule searchRule) {
S
Stepan Koltsov 已提交
225
        FqName qualifiedName = new FqName(psiClass.getQualifiedName());
226

S
Stepan Koltsov 已提交
227
        if (qualifiedName.getFqName().endsWith(JvmAbi.TRAIT_IMPL_SUFFIX)) {
228 229 230
            // TODO: only if -$$TImpl class is created by Kotlin
            return null;
        }
231

232 233 234 235 236
        ClassDescriptor builtinClassDescriptor = semanticServices.getKotlinBuiltinClassDescriptor(qualifiedName);
        if (builtinClassDescriptor != null) {
            return new ResolverSrcClassData(builtinClassDescriptor);
        }

237
        // First, let's check that this is a real Java class, not a Java's view on a Kotlin class:
238 239
        ClassDescriptor kotlinClassDescriptor = semanticServices.getKotlinClassDescriptor(qualifiedName);
        if (kotlinClassDescriptor != null) {
240 241 242 243 244 245 246 247 248 249
            if (searchRule == DescriptorSearchRule.ERROR_IF_FOUND_IN_KOTLIN) {
                throw new IllegalStateException("class must not be found in kotlin: " + qualifiedName);
            } else if (searchRule == DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN) {
                return null;
            } else if (searchRule == DescriptorSearchRule.INCLUDE_KOTLIN) {
                // TODO: probably this is evil
                return new ResolverSrcClassData(kotlinClassDescriptor);
            } else {
                throw new IllegalStateException("unknown searchRule: " + searchRule);
            }
250 251
        }

252 253 254
        PsiClass containingClass = psiClass.getContainingClass();
        if (containingClass != null) {
            // must resolve containing class first, because inner class must have a reference to it
255
            resolveClass(containingClass, DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN);
256 257
        }

258
        // Not let's take a descriptor of a Java class
259
        ResolverBinaryClassData classData = classDescriptorCache.get(qualifiedName);
260 261 262
        if (classData == null) {
            classData = createJavaClassDescriptor(psiClass);
            classDescriptorCache.put(qualifiedName, classData);
263
        }
264 265 266 267
        return classData;
    }

    @Nullable
268 269
    public ClassDescriptor resolveClass(@NotNull PsiClass psiClass, @NotNull DescriptorSearchRule searchRule) {
        ResolverClassData classData = resolveClassData(psiClass, searchRule);
270 271 272 273 274
        if (classData != null) {
            return classData.getClassDescriptor();
        } else {
            return null;
        }
275 276 277
    }

    @Nullable
278
    public ClassDescriptor resolveClass(@NotNull FqName qualifiedName, @NotNull DescriptorSearchRule searchRule) {
279

S
Stepan Koltsov 已提交
280
        if (qualifiedName.getFqName().endsWith(JvmAbi.TRAIT_IMPL_SUFFIX)) {
281 282 283
            // TODO: only if -$$TImpl class is created by Kotlin
            return null;
        }
284 285 286 287 288 289

        ClassDescriptor builtinClassDescriptor = semanticServices.getKotlinBuiltinClassDescriptor(qualifiedName);
        if (builtinClassDescriptor != null) {
            return builtinClassDescriptor;
        }

290
        // First, let's check that this is a real Java class, not a Java's view on a Kotlin class:
291 292
        ClassDescriptor kotlinClassDescriptor = semanticServices.getKotlinClassDescriptor(qualifiedName);
        if (kotlinClassDescriptor != null) {
293 294 295 296 297 298 299 300 301
            if (searchRule == DescriptorSearchRule.ERROR_IF_FOUND_IN_KOTLIN) {
                throw new IllegalStateException("class must not be found in kotlin: " + qualifiedName);
            } else if (searchRule == DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN) {
                return null;
            } else if (searchRule == DescriptorSearchRule.INCLUDE_KOTLIN) {
                return kotlinClassDescriptor;
            } else {
                throw new IllegalStateException("unknown searchRule: " + searchRule);
            }
302 303
        }

304
        // Not let's take a descriptor of a Java class
305
        ResolverBinaryClassData classData = classDescriptorCache.get(qualifiedName);
306
        if (classData == null) {
307
            PsiClass psiClass = findClass(qualifiedName);
308 309 310
            if (psiClass == null) {
                return null;
            }
311
            classData = createJavaClassDescriptor(psiClass);
312
        }
313
        return classData.getClassDescriptor();
314 315
    }

316
    private ResolverBinaryClassData createJavaClassDescriptor(@NotNull final PsiClass psiClass) {
S
Stepan Koltsov 已提交
317
        if (classDescriptorCache.containsKey(new FqName(psiClass.getQualifiedName()))) {
318 319
            throw new IllegalStateException(psiClass.getQualifiedName());
        }
A
Andrey Breslav 已提交
320

321 322
        checkPsiClassIsNotJet(psiClass);

323
        String name = psiClass.getName();
324
        ResolverBinaryClassData classData = new ResolverBinaryClassData();
S
Stepan Koltsov 已提交
325
        classDescriptorCache.put(new FqName(psiClass.getQualifiedName()), classData);
326
        ClassKind kind = psiClass.isInterface() ? (psiClass.isAnnotationType() ? ClassKind.ANNOTATION_CLASS : ClassKind.TRAIT) : ClassKind.CLASS;
S
Stepan Koltsov 已提交
327
        ClassOrNamespaceDescriptor containingDeclaration = resolveParentDescriptor(psiClass);
328
        classData.classDescriptor = new MutableClassDescriptorLite(containingDeclaration, kind);
329
        classData.classDescriptor.setName(name);
330 331
        classData.classDescriptor.setAnnotations(resolveAnnotations(psiClass));

A
Andrey Breslav 已提交
332
        List<JetType> supertypes = new ArrayList<JetType>();
333

S
Stepan Koltsov 已提交
334 335 336
        TypeVariableResolver outerTypeVariableByNameResolver = TypeVariableResolvers.classTypeVariableResolver(
                (ClassOrNamespaceDescriptor) classData.classDescriptor.getContainingDeclaration(),
                "class " + psiClass.getQualifiedName());
337 338

        classData.typeParameters = createUninitializedClassTypeParameters(psiClass, classData, outerTypeVariableByNameResolver);
339 340 341 342 343 344
        
        List<TypeParameterDescriptor> typeParameters = new ArrayList<TypeParameterDescriptor>();
        for (TypeParameterDescriptorInitialization typeParameter : classData.typeParameters) {
            typeParameters.add(typeParameter.descriptor);
        }
        
345 346 347
        classData.classDescriptor.setTypeParameterDescriptors(typeParameters);
        classData.classDescriptor.setSupertypes(supertypes);
        classData.classDescriptor.setVisibility(resolveVisibilityFromPsiModifiers(psiClass));
348 349 350 351 352 353 354 355 356 357
        Modality modality;
        if (classData.classDescriptor.getKind() == ClassKind.ANNOTATION_CLASS) {
            modality = Modality.FINAL;
        }
        else {
            modality = Modality.convertFromFlags(
                    psiClass.hasModifierProperty(PsiModifier.ABSTRACT) || psiClass.isInterface(),
                    !psiClass.hasModifierProperty(PsiModifier.FINAL));
        }
        classData.classDescriptor.setModality(modality);
358 359
        classData.classDescriptor.createTypeConstructor();
        classData.classDescriptor.setScopeForMemberLookup(new JavaClassMembersScope(classData.classDescriptor, psiClass, semanticServices, false));
360

S
Stepan Koltsov 已提交
361
        initializeTypeParameters(classData.typeParameters, classData.classDescriptor, "class " + psiClass.getQualifiedName());
362

S
Stepan Koltsov 已提交
363 364 365
        TypeVariableResolver resolverForTypeParameters = TypeVariableResolvers.classTypeVariableResolver(
                classData.classDescriptor,
                "class " + psiClass.getQualifiedName());
366

367
        // TODO: ugly hack: tests crash if initializeTypeParameters called with class containing proper supertypes
368
        supertypes.addAll(getSupertypes(new PsiClassWrapper(psiClass), classData.classDescriptor, classData.getTypeParameters()));
369

A
Andrey Breslav 已提交
370
        PsiMethod[] psiConstructors = psiClass.getConstructors();
371

372
        boolean isStatic = psiClass.hasModifierProperty(PsiModifier.STATIC);
373
        if (psiConstructors.length == 0) {
A
Andrey Breslav 已提交
374 375 376 377
            // We need to create default constructors for classes and abstract classes.
            // Example:
            // class Kotlin() : Java() {}
            // abstract public class Java {}
378
            if (!psiClass.isInterface()) {
379
                ConstructorDescriptorImpl constructorDescriptor = new ConstructorDescriptorImpl(
380
                        classData.classDescriptor,
A
Andrey Breslav 已提交
381
                        Collections.<AnnotationDescriptor>emptyList(),
382
                        false);
383
                constructorDescriptor.initialize(typeParameters, Collections.<ValueParameterDescriptor>emptyList(), classData.classDescriptor.getVisibility(), isStatic);
384
                constructorDescriptor.setReturnType(classData.classDescriptor.getDefaultType());
385
                classData.classDescriptor.addConstructor(constructorDescriptor, null);
386
                semanticServices.getTrace().record(BindingContext.CONSTRUCTOR, psiClass, constructorDescriptor);
387
            }
388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408
            if (psiClass.isAnnotationType()) {
                // A constructor for an annotation type takes all the "methods" in the @interface as parameters
                ConstructorDescriptorImpl constructorDescriptor = new ConstructorDescriptorImpl(
                        classData.classDescriptor,
                        Collections.<AnnotationDescriptor>emptyList(),
                        false);

                List<ValueParameterDescriptor> valueParameters = Lists.newArrayList();
                PsiMethod[] methods = psiClass.getMethods();
                for (int i = 0; i < methods.length; i++) {
                    PsiMethod method = methods[i];
                    if (method instanceof PsiAnnotationMethod) {
                        PsiAnnotationMethod annotationMethod = (PsiAnnotationMethod) method;
                        assert annotationMethod.getParameterList().getParameters().length == 0;

                        PsiType returnType = annotationMethod.getReturnType();

                        // We take the following heuristical convention:
                        // if the last method of the @interface is an array, we convert it into a vararg
                        JetType varargElementType = null;
                        if (i == methods.length - 1 && (returnType instanceof PsiArrayType)) {
409
                            varargElementType = semanticServices.getTypeTransformer().transformToType(((PsiArrayType) returnType).getComponentType(), resolverForTypeParameters);
410 411 412 413 414 415 416 417
                        }

                        valueParameters.add(new ValueParameterDescriptorImpl(
                                constructorDescriptor,
                                i,
                                Collections.<AnnotationDescriptor>emptyList(),
                                method.getName(),
                                false,
418
                                semanticServices.getTypeTransformer().transformToType(returnType, resolverForTypeParameters),
419 420 421 422 423
                                annotationMethod.getDefaultValue() != null,
                                varargElementType));
                    }
                }

424
                constructorDescriptor.initialize(typeParameters, valueParameters, classData.classDescriptor.getVisibility(), isStatic);
425 426 427 428
                constructorDescriptor.setReturnType(classData.classDescriptor.getDefaultType());
                classData.classDescriptor.addConstructor(constructorDescriptor, null);
                semanticServices.getTrace().record(BindingContext.CONSTRUCTOR, psiClass, constructorDescriptor);
            }
429 430
        }
        else {
431 432 433 434 435
            for (PsiMethod psiConstructor : psiConstructors) {
                PsiMethodWrapper constructor = new PsiMethodWrapper(psiConstructor);

                if (constructor.getJetConstructor().hidden()) {
                    continue;
436 437
                }

438
                ConstructorDescriptorImpl constructorDescriptor = new ConstructorDescriptorImpl(
439
                        classData.classDescriptor,
A
Andrey Breslav 已提交
440
                        Collections.<AnnotationDescriptor>emptyList(), // TODO
441
                        false);
S
Stepan Koltsov 已提交
442
                String context = "constructor of class " + psiClass.getQualifiedName();
443
                ValueParameterDescriptors valueParameterDescriptors = resolveParameterDescriptors(constructorDescriptor,
444
                        constructor.getParameters(),
S
Stepan Koltsov 已提交
445
                        TypeVariableResolvers.classTypeVariableResolver(classData.classDescriptor, context));
446 447 448
                if (valueParameterDescriptors.receiverType != null) {
                    throw new IllegalStateException();
                }
449
                constructorDescriptor.initialize(typeParameters, valueParameterDescriptors.descriptors,
450
                        resolveVisibilityFromPsiModifiers(psiConstructor), isStatic);
451
                constructorDescriptor.setReturnType(classData.classDescriptor.getDefaultType());
452
                classData.classDescriptor.addConstructor(constructorDescriptor, null);
453
                semanticServices.getTrace().record(BindingContext.CONSTRUCTOR, psiConstructor, constructorDescriptor);
454
            }
A
Andrey Breslav 已提交
455
        }
456

457 458 459 460
        MutableClassDescriptorLite classObject = createClassObjectDescriptor(classData.classDescriptor, psiClass);
        if (classObject != null) {
            classData.classDescriptor.setClassObjectDescriptor(classObject);
        }
461

462
        semanticServices.getTrace().record(BindingContext.CLASS, psiClass, classData.classDescriptor);
463

464
        return classData;
465 466
    }

467
    static void checkPsiClassIsNotJet(PsiClass psiClass) {
468
        if (psiClass instanceof JetJavaMirrorMarker) {
469
            throw new IllegalStateException("trying to resolve fake jet PsiClass as regular PsiClass: " + psiClass.getQualifiedName());
470 471 472
        }
    }

473 474 475 476 477 478 479 480 481 482
    @Nullable
    private PsiClass getInnerClassClassObject(@NotNull PsiClass outer) {
        for (PsiClass inner : outer.getInnerClasses()) {
            if (inner.getName().equals(JvmAbi.CLASS_OBJECT_CLASS_NAME)) {
                return inner;
            }
        }
        return null;
    }

483 484 485 486 487 488
    /**
     * TODO
     * @see #createJavaNamespaceDescriptor(com.intellij.psi.PsiClass)
     */
    @Nullable
    private MutableClassDescriptorLite createClassObjectDescriptor(@NotNull ClassDescriptor containing, @NotNull PsiClass psiClass) {
489 490 491 492 493
        PsiClass classObjectPsiClass = getInnerClassClassObject(psiClass);
        if (classObjectPsiClass == null) {
            return null;
        }

494 495
        checkPsiClassIsNotJet(psiClass);

496 497 498 499
        ResolverBinaryClassData classData = new ResolverBinaryClassData();
        classData.kotlin = true;
        classData.classDescriptor = new MutableClassDescriptorLite(containing, ClassKind.OBJECT);

S
Stepan Koltsov 已提交
500
        classDescriptorCache.put(new FqName(classObjectPsiClass.getQualifiedName()), classData);
501 502 503 504 505 506 507 508 509 510 511 512 513 514 515

        classData.classDescriptor.setSupertypes(getSupertypes(new PsiClassWrapper(classObjectPsiClass), classData.classDescriptor, new ArrayList<TypeParameterDescriptor>(0)));
        classData.classDescriptor.setName(JetPsiUtil.NO_NAME_PROVIDED); // TODO
        classData.classDescriptor.setModality(Modality.FINAL);
        classData.classDescriptor.setTypeParameterDescriptors(new ArrayList<TypeParameterDescriptor>(0));
        classData.classDescriptor.createTypeConstructor();
        classData.classDescriptor.setScopeForMemberLookup(new JavaClassMembersScope(classData.classDescriptor, classObjectPsiClass, semanticServices, false));

        // TODO: wrong: class objects do not need visible constructors
        ConstructorDescriptorImpl constructor = new ConstructorDescriptorImpl(classData.classDescriptor, new ArrayList<AnnotationDescriptor>(0), true);
        constructor.setReturnType(classData.classDescriptor.getDefaultType());
        constructor.initialize(new ArrayList<TypeParameterDescriptor>(0), new ArrayList<ValueParameterDescriptor>(0), Visibility.PUBLIC);

        classData.classDescriptor.addConstructor(constructor, null);
        return classData.classDescriptor;
516 517
    }

518
    private List<TypeParameterDescriptorInitialization> createUninitializedClassTypeParameters(PsiClass psiClass, ResolverBinaryClassData classData, TypeVariableResolver typeVariableResolver) {
519 520 521 522 523
        JetClassAnnotation jetClassAnnotation = JetClassAnnotation.get(psiClass);
        classData.kotlin = jetClassAnnotation.isDefined();
        
        if (jetClassAnnotation.signature().length() > 0) {
            return resolveClassTypeParametersFromJetSignature(
S
Stepan Koltsov 已提交
524
                    jetClassAnnotation.signature(), psiClass, classData.classDescriptor);
525
        }
526

527
        return makeUninitializedTypeParameters(classData.classDescriptor, psiClass.getTypeParameters());
528 529
    }

530
    @NotNull
531
    private PsiTypeParameter getPsiTypeParameterByName(PsiTypeParameterListOwner clazz, String name) {
532 533 534 535 536
        for (PsiTypeParameter typeParameter : clazz.getTypeParameters()) {
            if (typeParameter.getName().equals(name)) {
                return typeParameter; 
            }
        }
537 538 539
        throw new IllegalStateException("PsiTypeParameter '" + name + "' is not found");
    }

S
Stepan Koltsov 已提交
540

541
    private static final FqName JL_OBJECT = new FqName("java.lang.Object");
S
Stepan Koltsov 已提交
542 543

    private boolean isJavaLangObject(JetType type) {
544 545 546
        ClassifierDescriptor classifierDescriptor = type.getConstructor().getDeclarationDescriptor();
        return classifierDescriptor instanceof ClassDescriptor &&
               DescriptorUtils.getFQName(classifierDescriptor).equals(JL_OBJECT.toUnsafe());
S
Stepan Koltsov 已提交
547 548 549
    }


550
    private abstract class JetSignatureTypeParameterVisitor extends JetSignatureExceptionsAdapter {
551 552

        @NotNull
553
        private final PsiTypeParameterListOwner psiOwner;
554
        @NotNull
555
        private final String name;
556
        @NotNull
557
        private final TypeVariableResolver typeVariableResolver;
558 559
        @NotNull
        private final TypeParameterDescriptor typeParameterDescriptor;
560

561 562
        protected JetSignatureTypeParameterVisitor(PsiTypeParameterListOwner psiOwner,
                String name, TypeVariableResolver typeVariableResolver, TypeParameterDescriptor typeParameterDescriptor)
563
        {
564 565 566
            if (name.isEmpty()) {
                throw new IllegalStateException();
            }
567

568 569
            this.psiOwner = psiOwner;
            this.name = name;
570
            this.typeVariableResolver = typeVariableResolver;
571
            this.typeParameterDescriptor = typeParameterDescriptor;
572 573 574 575
        }

        List<JetType> upperBounds = new ArrayList<JetType>();
        List<JetType> lowerBounds = new ArrayList<JetType>();
S
Stepan Koltsov 已提交
576
        
577 578
        @Override
        public JetSignatureVisitor visitClassBound() {
579
            return new JetTypeJetSignatureReader(semanticServices, JetStandardLibrary.getInstance(), typeVariableResolver) {
580 581
                @Override
                protected void done(@NotNull JetType jetType) {
S
Stepan Koltsov 已提交
582 583 584
                    if (isJavaLangObject(jetType)) {
                        return;
                    }
585 586 587 588 589 590 591
                    upperBounds.add(jetType);
                }
            };
        }

        @Override
        public JetSignatureVisitor visitInterfaceBound() {
592
            return new JetTypeJetSignatureReader(semanticServices, JetStandardLibrary.getInstance(), typeVariableResolver) {
593 594 595 596 597 598 599 600 601
                @Override
                protected void done(@NotNull JetType jetType) {
                    upperBounds.add(jetType);
                }
            };
        }

        @Override
        public void visitFormalTypeParameterEnd() {
602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620
            PsiTypeParameter psiTypeParameter = getPsiTypeParameterByName(psiOwner, name);
            TypeParameterDescriptorInitialization typeParameterDescriptorInitialization = new TypeParameterDescriptorInitialization(typeParameterDescriptor, psiTypeParameter, upperBounds, lowerBounds);
            done(typeParameterDescriptorInitialization);
        }
        
        protected abstract void done(@NotNull TypeParameterDescriptorInitialization typeParameterDescriptor);
    }

    private class JetSignatureTypeParametersVisitor extends JetSignatureExceptionsAdapter {
        @NotNull
        private final DeclarationDescriptor containingDeclaration;
        @NotNull
        private final PsiTypeParameterListOwner psiOwner;

        private final List<TypeParameterDescriptor> previousTypeParameters = new ArrayList<TypeParameterDescriptor>();
        // note changes state in this method
        private final TypeVariableResolver typeVariableResolver;


S
Stepan Koltsov 已提交
621
        private JetSignatureTypeParametersVisitor(@NotNull DeclarationDescriptor containingDeclaration, @NotNull PsiTypeParameterListOwner psiOwner, @NotNull String context) {
622 623 624
            this.containingDeclaration = containingDeclaration;
            this.psiOwner = psiOwner;

S
Stepan Koltsov 已提交
625 626 627 628
            this.typeVariableResolver = TypeVariableResolvers.typeVariableResolverFromTypeParameters(
                    previousTypeParameters,
                    containingDeclaration,
                    context);
629 630 631 632 633 634 635 636 637
        }

        private int formalTypeParameterIndex = 0;


        List<TypeParameterDescriptorInitialization> r = new ArrayList<TypeParameterDescriptorInitialization>();

        @Override
        public JetSignatureVisitor visitFormalTypeParameter(final String name, final TypeInfoVariance variance, boolean reified) {
638 639 640
            TypeParameterDescriptor typeParameter = TypeParameterDescriptor.createForFurtherModification(
                    containingDeclaration,
                    Collections.<AnnotationDescriptor>emptyList(), // TODO: wrong
641
                    reified,
642 643
                    JetSignatureUtils.translateVariance(variance),
                    name,
644 645 646 647 648 649 650 651 652 653 654
                    formalTypeParameterIndex++);

            previousTypeParameters.add(typeParameter);

            return new JetSignatureTypeParameterVisitor(psiOwner, name, typeVariableResolver, typeParameter) {
                @Override
                protected void done(@NotNull TypeParameterDescriptorInitialization typeParameterDescriptor) {
                    r.add(typeParameterDescriptor);
                    previousTypeParameters.add(typeParameterDescriptor.descriptor);
                }
            };
655
        }
656 657
    }

658
    /**
S
Stepan Koltsov 已提交
659
     * @see #resolveMethodTypeParametersFromJetSignature(String, com.intellij.psi.PsiMethod, org.jetbrains.jet.lang.descriptors.DeclarationDescriptor)
660
     */
S
Stepan Koltsov 已提交
661 662 663 664
    private List<TypeParameterDescriptorInitialization> resolveClassTypeParametersFromJetSignature(String jetSignature,
            final PsiClass clazz, final ClassDescriptor classDescriptor) {
        String context = "class " + clazz.getQualifiedName();
        JetSignatureTypeParametersVisitor jetSignatureTypeParametersVisitor = new JetSignatureTypeParametersVisitor(classDescriptor, clazz, context) {
665 666 667 668 669 670 671 672 673 674 675
            @Override
            public JetSignatureVisitor visitSuperclass() {
                // TODO
                return new JetSignatureAdapter();
            }

            @Override
            public JetSignatureVisitor visitInterface() {
                // TODO
                return new JetSignatureAdapter();
            }
676 677 678
        };
        new JetSignatureReader(jetSignature).accept(jetSignatureTypeParametersVisitor);
        return jetSignatureTypeParametersVisitor.r;
679 680
    }

S
Stepan Koltsov 已提交
681
    private ClassOrNamespaceDescriptor resolveParentDescriptor(PsiClass psiClass) {
682 683
        PsiClass containingClass = psiClass.getContainingClass();
        if (containingClass != null) {
684
            return resolveClass(containingClass, DescriptorSearchRule.INCLUDE_KOTLIN);
685
        }
686

687
        return resolveNamespace(new FqName(psiClass.getQualifiedName()).parent(), DescriptorSearchRule.INCLUDE_KOTLIN);
688 689
    }

690 691
    private List<TypeParameterDescriptorInitialization> makeUninitializedTypeParameters(@NotNull DeclarationDescriptor containingDeclaration, @NotNull PsiTypeParameter[] typeParameters) {
        List<TypeParameterDescriptorInitialization> result = Lists.newArrayList();
692
        for (PsiTypeParameter typeParameter : typeParameters) {
693
            TypeParameterDescriptorInitialization typeParameterDescriptor = makeUninitializedTypeParameter(containingDeclaration, typeParameter);
A
Andrey Breslav 已提交
694
            result.add(typeParameterDescriptor);
695 696 697 698
        }
        return result;
    }

699
    @NotNull
700
    private TypeParameterDescriptorInitialization makeUninitializedTypeParameter(@NotNull DeclarationDescriptor containingDeclaration, @NotNull PsiTypeParameter psiTypeParameter) {
701
        TypeParameterDescriptor typeParameterDescriptor = TypeParameterDescriptor.createForFurtherModification(
702
                containingDeclaration,
A
Andrey Breslav 已提交
703
                Collections.<AnnotationDescriptor>emptyList(), // TODO
A
Andrey Breslav 已提交
704
                false,
705
                Variance.INVARIANT,
706 707
                psiTypeParameter.getName(),
                psiTypeParameter.getIndex()
708
        );
709
        return new TypeParameterDescriptorInitialization(typeParameterDescriptor, psiTypeParameter);
710 711
    }

712
    private void initializeTypeParameter(TypeParameterDescriptorInitialization typeParameter, TypeVariableResolver typeVariableByPsiResolver) {
713 714 715
        TypeParameterDescriptor typeParameterDescriptor = typeParameter.descriptor;
        if (typeParameter.origin == TypeParameterDescriptorOrigin.KOTLIN) {
            List<?> upperBounds = typeParameter.upperBoundsForKotlin;
716 717 718
            if (upperBounds.size() == 0){
                typeParameterDescriptor.addUpperBound(JetStandardClasses.getNullableAnyType());
            } else {
719
                for (JetType upperBound : typeParameter.upperBoundsForKotlin) {
720 721 722 723 724
                    typeParameterDescriptor.addUpperBound(upperBound);
                }
            }

            // TODO: lower bounds
725
        } else {
726
            PsiClassType[] referencedTypes = typeParameter.psiTypeParameter.getExtendsList().getReferencedTypes();
727 728 729 730
            if (referencedTypes.length == 0){
                typeParameterDescriptor.addUpperBound(JetStandardClasses.getNullableAnyType());
            }
            else if (referencedTypes.length == 1) {
731
                typeParameterDescriptor.addUpperBound(semanticServices.getTypeTransformer().transformToType(referencedTypes[0], typeVariableByPsiResolver));
732 733 734
            }
            else {
                for (PsiClassType referencedType : referencedTypes) {
735
                    typeParameterDescriptor.addUpperBound(semanticServices.getTypeTransformer().transformToType(referencedType, typeVariableByPsiResolver));
736
                }
A
Andrey Breslav 已提交
737 738
            }
        }
739
        typeParameterDescriptor.setInitialized();
740 741
    }

S
Stepan Koltsov 已提交
742
    private void initializeTypeParameters(List<TypeParameterDescriptorInitialization> typeParametersInitialization, @NotNull DeclarationDescriptor typeParametersOwner, @NotNull String context) {
743
        List<TypeParameterDescriptor> prevTypeParameters = new ArrayList<TypeParameterDescriptor>();
744
        for (TypeParameterDescriptorInitialization psiTypeParameter : typeParametersInitialization) {
745
            prevTypeParameters.add(psiTypeParameter.descriptor);
S
Stepan Koltsov 已提交
746
            initializeTypeParameter(psiTypeParameter, TypeVariableResolvers.typeVariableResolverFromTypeParameters(prevTypeParameters, typeParametersOwner, context));
S
Stepan Koltsov 已提交
747
        }
A
Andrey Breslav 已提交
748 749
    }

750
    private Collection<JetType> getSupertypes(PsiClassWrapper psiClass, ClassDescriptor classDescriptor, List<TypeParameterDescriptor> typeParameters) {
751 752
        final List<JetType> result = new ArrayList<JetType>();

S
Stepan Koltsov 已提交
753 754
        String context = "class " + psiClass.getQualifiedName();

755
        if (psiClass.getJetClass().signature().length() > 0) {
S
Stepan Koltsov 已提交
756
            final TypeVariableResolver typeVariableResolver = TypeVariableResolvers.typeVariableResolverFromTypeParameters(typeParameters, classDescriptor, context);
757 758 759 760 761 762 763 764 765 766
            
            new JetSignatureReader(psiClass.getJetClass().signature()).accept(new JetSignatureExceptionsAdapter() {
                @Override
                public JetSignatureVisitor visitFormalTypeParameter(String name, TypeInfoVariance variance, boolean reified) {
                    // TODO: collect
                    return new JetSignatureAdapter();
                }

                @Override
                public JetSignatureVisitor visitSuperclass() {
767
                    return new JetTypeJetSignatureReader(semanticServices, JetStandardLibrary.getInstance(), typeVariableResolver) {
768 769 770 771 772 773 774 775 776 777 778
                        @Override
                        protected void done(@NotNull JetType jetType) {
                            if (!jetType.equals(JetStandardClasses.getAnyType())) {
                                result.add(jetType);
                            }
                        }
                    };
                }

                @Override
                public JetSignatureVisitor visitInterface() {
S
Stepan Koltsov 已提交
779
                    return visitSuperclass();
780 781 782
                }
            });
        } else {
S
Stepan Koltsov 已提交
783 784 785
            TypeVariableResolver typeVariableResolverForSupertypes = TypeVariableResolvers.typeVariableResolverFromTypeParameters(typeParameters, classDescriptor, context);
            transformSupertypeList(result, psiClass.getPsiClass().getExtendsListTypes(), typeVariableResolverForSupertypes, classDescriptor.getKind() == ClassKind.ANNOTATION_CLASS);
            transformSupertypeList(result, psiClass.getPsiClass().getImplementsListTypes(), typeVariableResolverForSupertypes, classDescriptor.getKind() == ClassKind.ANNOTATION_CLASS);
786
        }
787 788 789 790 791 792 793
        
        for (JetType supertype : result) {
            if (ErrorUtils.isErrorType(supertype)) {
                semanticServices.getTrace().record(BindingContext.INCOMPLETE_HIERARCHY, classDescriptor);
            }
        }
        
794 795 796
        if (result.isEmpty()) {
            result.add(JetStandardClasses.getAnyType());
        }
797 798 799
        return result;
    }

800
    private void transformSupertypeList(List<JetType> result, PsiClassType[] extendsListTypes, TypeVariableResolver typeVariableResolver, boolean annotation) {
801
        for (PsiClassType type : extendsListTypes) {
802 803 804 805
            PsiClass resolved = type.resolve();
            if (resolved != null && resolved.getQualifiedName().equals(JvmStdlibNames.JET_OBJECT.getFqName())) {
                continue;
            }
806 807 808
            if (annotation && resolved.getQualifiedName().equals("java.lang.annotation.Annotation")) {
                continue;
            }
809
            
810
            JetType transform = semanticServices.getTypeTransformer().transformToType(type, typeVariableResolver);
811 812 813 814 815

            result.add(TypeUtils.makeNotNullable(transform));
        }
    }

816
    @Nullable
817
    public NamespaceDescriptor resolveNamespace(@NotNull FqName qualifiedName, @NotNull DescriptorSearchRule searchRule) {
818 819 820
        // First, let's check that there is no Kotlin package:
        NamespaceDescriptor kotlinNamespaceDescriptor = semanticServices.getKotlinNamespaceDescriptor(qualifiedName);
        if (kotlinNamespaceDescriptor != null) {
821 822 823 824 825 826 827 828 829 830
            if (searchRule == DescriptorSearchRule.ERROR_IF_FOUND_IN_KOTLIN) {
                throw new IllegalStateException("class must not be found in kotlin: " + qualifiedName);
            } else if (searchRule == DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN) {
                return null;
            } else if (searchRule == DescriptorSearchRule.INCLUDE_KOTLIN) {
                // TODO: probably this is evil
                return kotlinNamespaceDescriptor;
            } else {
                throw new IllegalStateException("unknown searchRule: " + searchRule);
            }
831 832
        }

833
        PsiPackage psiPackage = findPackage(qualifiedName);
834
        if (psiPackage == null) {
835
            PsiClass psiClass = findClass(qualifiedName);
A
Andrey Breslav 已提交
836 837
            if (psiClass == null) return null;
            return resolveNamespace(psiClass);
838 839 840 841
        }
        return resolveNamespace(psiPackage);
    }

842
    @Nullable
S
Stepan Koltsov 已提交
843 844
    public PsiClass findClass(@NotNull FqName qualifiedName) {
        PsiClass original = javaFacade.findClass(qualifiedName.getFqName(), javaSearchScope);
M
Maxim Shafirov 已提交
845
        PsiClass altClass = altClassFinder.findClass(qualifiedName);
846
        PsiClass result = original;
847 848 849 850 851
        if (altClass != null) {
            if (altClass instanceof ClsClassImpl) {
                altClass.putUserData(ClsClassImpl.DELEGATE_KEY, original);
            }

852 853 854 855
            result = altClass;
        }

        if (result != null) {
S
Stepan Koltsov 已提交
856
            FqName actualQualifiedName = new FqName(result.getQualifiedName());
857
            if (!actualQualifiedName.equals(qualifiedName)) {
858
//                throw new IllegalStateException("requested " + qualifiedName + ", got " + actualQualifiedName);
859
            }
860
        }
861 862

        return result;
863 864
    }

S
Stepan Koltsov 已提交
865 866
    /*package*/ PsiPackage findPackage(@NotNull FqName qualifiedName) {
        return javaFacade.findPackage(qualifiedName.getFqName());
867 868
    }

869
    private NamespaceDescriptor resolveNamespace(@NotNull PsiPackage psiPackage) {
870 871 872 873
        ResolverNamespaceData namespaceData = namespaceDescriptorCache.get(psiPackage);
        if (namespaceData == null) {
            namespaceData = createJavaNamespaceDescriptor(psiPackage);
            namespaceDescriptorCache.put(psiPackage, namespaceData);
S
Stepan Koltsov 已提交
874
            namespaceDescriptorCacheByFqn.put(new FqName(psiPackage.getQualifiedName()), namespaceData);
875
        }
876
        return namespaceData.namespaceDescriptor;
877 878
    }

A
Andrey Breslav 已提交
879
    private NamespaceDescriptor resolveNamespace(@NotNull PsiClass psiClass) {
880 881 882 883
        ResolverNamespaceData namespaceData = namespaceDescriptorCache.get(psiClass);
        if (namespaceData == null) {
            namespaceData = createJavaNamespaceDescriptor(psiClass);
            namespaceDescriptorCache.put(psiClass, namespaceData);
S
Stepan Koltsov 已提交
884
            namespaceDescriptorCacheByFqn.put(new FqName(psiClass.getQualifiedName()), namespaceData);
A
Andrey Breslav 已提交
885
        }
886
        return namespaceData.namespaceDescriptor;
A
Andrey Breslav 已提交
887 888
    }

889 890
    private ResolverNamespaceData createJavaNamespaceDescriptor(@NotNull PsiPackage psiPackage) {
        ResolverNamespaceData namespaceData = new ResolverNamespaceData();
891
        String name = psiPackage.getName();
892
        namespaceData.namespaceDescriptor = new JavaNamespaceDescriptor(
S
Stepan Koltsov 已提交
893
                (NamespaceDescriptorParent) resolveParentDescriptor(psiPackage),
A
Andrey Breslav 已提交
894
                Collections.<AnnotationDescriptor>emptyList(), // TODO
895
                name == null ? JAVA_ROOT : name,
S
Stepan Koltsov 已提交
896
                name == null ? FqName.ROOT : new FqName(psiPackage.getQualifiedName()),
897
                true
898
        );
899

S
Stepan Koltsov 已提交
900
        namespaceData.namespaceDescriptor.setMemberScope(createJavaPackageScope(new FqName(psiPackage.getQualifiedName()), namespaceData.namespaceDescriptor));
901 902 903 904
        semanticServices.getTrace().record(BindingContext.NAMESPACE, psiPackage, namespaceData.namespaceDescriptor);
        // TODO: hack
        namespaceData.kotlin = true;
        return namespaceData;
905 906
    }

S
Stepan Koltsov 已提交
907 908 909 910
    public JavaPackageScope createJavaPackageScope(@NotNull FqName fqName, @NotNull NamespaceDescriptor ns) {
        return new JavaPackageScope(fqName, ns, semanticServices);
    }

S
Stepan Koltsov 已提交
911
    @NotNull
912 913 914
    private DeclarationDescriptor resolveParentDescriptor(@NotNull PsiPackage psiPackage) {
        PsiPackage parentPackage = psiPackage.getParentPackage();
        if (parentPackage == null) {
S
Stepan Koltsov 已提交
915
            return FAKE_ROOT_MODULE;
916 917 918 919
        }
        return resolveNamespace(parentPackage);
    }

920 921 922 923
    /**
     * TODO
     * @see #createClassObjectDescriptor(org.jetbrains.jet.lang.descriptors.ClassDescriptor, com.intellij.psi.PsiClass)
     */
924
    private ResolverNamespaceData createJavaNamespaceDescriptor(@NotNull final PsiClass psiClass) {
925 926 927

        checkPsiClassIsNotJet(psiClass);

928 929
        ResolverNamespaceData namespaceData = new ResolverNamespaceData();
        namespaceData.namespaceDescriptor = new JavaNamespaceDescriptor(
S
Stepan Koltsov 已提交
930
                (NamespaceDescriptorParent) resolveParentDescriptor(psiClass),
A
Andrey Breslav 已提交
931
                Collections.<AnnotationDescriptor>emptyList(), // TODO
932
                psiClass.getName(),
S
Stepan Koltsov 已提交
933
                new FqName(psiClass.getQualifiedName()),
934
                false
935
        );
936 937 938
        namespaceData.namespaceDescriptor.setMemberScope(new JavaClassMembersScope(namespaceData.namespaceDescriptor, psiClass, semanticServices, true));
        semanticServices.getTrace().record(BindingContext.NAMESPACE, psiClass, namespaceData.namespaceDescriptor);
        return namespaceData;
939
    }
940 941 942 943 944 945 946 947 948 949
    
    private static class ValueParameterDescriptors {
        private final JetType receiverType;
        private final List<ValueParameterDescriptor> descriptors;

        private ValueParameterDescriptors(@Nullable JetType receiverType, List<ValueParameterDescriptor> descriptors) {
            this.receiverType = receiverType;
            this.descriptors = descriptors;
        }
    }
950

951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968 969 970 971 972 973 974 975 976 977 978 979 980 981 982 983
    private enum JvmMethodParameterKind {
        REGULAR,
        RECEIVER,
        TYPE_INFO,
    }
    
    private static class JvmMethodParameterMeaning {
        private final JvmMethodParameterKind kind;
        private final JetType receiverType;
        private final ValueParameterDescriptor valueParameterDescriptor;
        private final Object typeInfo;

        private JvmMethodParameterMeaning(JvmMethodParameterKind kind, JetType receiverType, ValueParameterDescriptor valueParameterDescriptor, Object typeInfo) {
            this.kind = kind;
            this.receiverType = receiverType;
            this.valueParameterDescriptor = valueParameterDescriptor;
            this.typeInfo = typeInfo;
        }
        
        public static JvmMethodParameterMeaning receiver(@NotNull JetType receiverType) {
            return new JvmMethodParameterMeaning(JvmMethodParameterKind.RECEIVER, receiverType, null, null);
        }
        
        public static JvmMethodParameterMeaning regular(@NotNull ValueParameterDescriptor valueParameterDescriptor) {
            return new JvmMethodParameterMeaning(JvmMethodParameterKind.REGULAR, null, valueParameterDescriptor, null);
        }
        
        public static JvmMethodParameterMeaning typeInfo(@NotNull Object typeInfo) {
            return new JvmMethodParameterMeaning(JvmMethodParameterKind.TYPE_INFO, null, null, typeInfo);
        }
    }

    @NotNull
984
    private JvmMethodParameterMeaning resolveParameterDescriptor(DeclarationDescriptor containingDeclaration, int i,
985 986 987 988 989 990 991
            PsiParameterWrapper parameter, TypeVariableResolver typeVariableResolver) {

        if (parameter.getJetTypeParameter().isDefined()) {
            return JvmMethodParameterMeaning.typeInfo(new Object());
        }

        PsiType psiType = parameter.getPsiParameter().getType();
992

993 994
        // TODO: must be very slow, make it lazy?
        String name = parameter.getPsiParameter().getName() != null ? parameter.getPsiParameter().getName() : "p" + i;
995

996 997
        if (parameter.getJetValueParameter().name().length() > 0) {
            name = parameter.getJetValueParameter().name();
998 999
        }
        
1000 1001 1002 1003
        String typeFromAnnotation = parameter.getJetValueParameter().type();
        boolean receiver = parameter.getJetValueParameter().receiver();
        boolean hasDefaultValue = parameter.getJetValueParameter().hasDefaultValue();

S
Stepan Koltsov 已提交
1004
        JetType outType;
1005
        if (typeFromAnnotation.length() > 0) {
1006
            outType = semanticServices.getTypeTransformer().transformToType(typeFromAnnotation, typeVariableResolver);
S
Stepan Koltsov 已提交
1007
        } else {
1008
            outType = semanticServices.getTypeTransformer().transformToType(psiType, typeVariableResolver);
S
Stepan Koltsov 已提交
1009
        }
1010 1011 1012

        JetType varargElementType;
        if (psiType instanceof PsiEllipsisType) {
1013
            varargElementType = JetStandardLibrary.getInstance().getArrayElementType(outType);
1014 1015 1016 1017
        } else {
            varargElementType = null;
        }

1018 1019 1020
        if (receiver) {
            return JvmMethodParameterMeaning.receiver(outType);
        } else {
S
Stepan Koltsov 已提交
1021 1022 1023 1024 1025 1026 1027 1028 1029

            JetType transformedType;
            if (parameter.getJetValueParameter().nullable()) {
                transformedType = TypeUtils.makeNullableAsSpecified(outType, parameter.getJetValueParameter().nullable());
            } else if (parameter.getPsiParameter().getModifierList().findAnnotation(JvmAbi.JETBRAINS_NOT_NULL_ANNOTATION.getFqName()) != null) {
                transformedType = TypeUtils.makeNullableAsSpecified(outType, false);
            } else {
                transformedType = outType;
            }
1030 1031 1032 1033 1034
            return JvmMethodParameterMeaning.regular(new ValueParameterDescriptorImpl(
                    containingDeclaration,
                    i,
                    Collections.<AnnotationDescriptor>emptyList(), // TODO
                    name,
S
Stepan Koltsov 已提交
1035
                    false,
S
Stepan Koltsov 已提交
1036
                    transformedType,
1037
                    hasDefaultValue,
1038 1039 1040
                    varargElementType
            ));
        }
1041 1042
    }

S
Stepan Koltsov 已提交
1043
    public Set<VariableDescriptor> resolveFieldGroupByName(@NotNull ClassOrNamespaceDescriptor owner, @NotNull PsiClass psiClass, String fieldName, boolean staticMembers) {
1044
        ResolverScopeData scopeData = getResolverScopeData(owner, new PsiClassWrapper(psiClass));
1045

1046 1047 1048
        NamedMembers namedMembers = scopeData.namedMembersMap.get(fieldName);
        if (namedMembers == null) {
            return Collections.emptySet();
1049
        }
1050
        Set<VariableDescriptor> r = new HashSet<VariableDescriptor>();
1051

S
Stepan Koltsov 已提交
1052
        resolveNamedGroupProperties(owner, scopeData, staticMembers, namedMembers, fieldName, "class or namespace " + psiClass.getQualifiedName());
1053

1054 1055 1056 1057 1058 1059 1060
        r.addAll(namedMembers.propertyDescriptors);

        for (JetType supertype : getSupertypes(scopeData)) {
            r.addAll(supertype.getMemberScope().getProperties(fieldName));
        }

        return r;
1061 1062 1063
    }
    
    @NotNull
S
Stepan Koltsov 已提交
1064
    public Set<VariableDescriptor> resolveFieldGroup(@NotNull ClassOrNamespaceDescriptor owner, @NotNull PsiClass psiClass, boolean staticMembers) {
1065

1066 1067
        ResolverScopeData scopeData = getResolverScopeData(owner, new PsiClassWrapper(psiClass));
        
1068
        Set<VariableDescriptor> descriptors = Sets.newHashSet();
1069 1070 1071
        Map<String, NamedMembers> membersForProperties = scopeData.namedMembersMap;
        for (Map.Entry<String, NamedMembers> entry : membersForProperties.entrySet()) {
            NamedMembers namedMembers = entry.getValue();
1072
            if (namedMembers.propertyAccessors == null) {
1073 1074 1075 1076
                continue;
            }
            
            String propertyName = entry.getKey();
1077

S
Stepan Koltsov 已提交
1078
            resolveNamedGroupProperties(owner, scopeData, staticMembers, namedMembers, propertyName, "class or namespace " + psiClass.getQualifiedName());
1079
            descriptors.addAll(namedMembers.propertyDescriptors);
1080
        }
1081 1082 1083 1084 1085 1086 1087 1088 1089 1090

        for (JetType supertype : getSupertypes(scopeData)) {
            for (DeclarationDescriptor descriptor : supertype.getMemberScope().getAllDescriptors()) {
                // TODO: ugly
                if (descriptor instanceof VariableDescriptor) {
                    descriptors.add((VariableDescriptor) descriptor);
                }
            }
        }
        
1091
        return descriptors;
1092
    }
1093 1094 1095 1096 1097 1098 1099
    
    private Object key(TypeSource typeSource) {
        if (typeSource == null) {
            return "";
        } else if (typeSource.getTypeString().length() > 0) {
            return typeSource.getTypeString();
        } else {
1100
            return psiTypeToKey(typeSource.getPsiType());
1101 1102
        }
    }
1103 1104 1105 1106 1107 1108 1109 1110 1111 1112 1113 1114 1115

    private Object psiTypeToKey(PsiType psiType) {
        if (psiType instanceof PsiClassType) {
            return ((PsiClassType) psiType).getClassName();
        } else if (psiType instanceof PsiPrimitiveType) {
            return psiType.getPresentableText();
        } else if (psiType instanceof PsiArrayType) {
            return Pair.create("[", psiTypeToKey(((PsiArrayType) psiType).getComponentType()));
        } else {
            throw new IllegalStateException("" + psiType.getClass());
        }
    }

1116 1117 1118 1119 1120
    private Object propertyKeyForGrouping(PropertyAccessorData propertyAccessor) {
        Object type = key(propertyAccessor.getType());
        Object receiverType = key(propertyAccessor.getReceiverType());
        return Pair.create(type, receiverType);
    }
1121

1122 1123 1124
    private void resolveNamedGroupProperties(
            @NotNull ClassOrNamespaceDescriptor owner,
            @NotNull ResolverScopeData scopeData,
S
Stepan Koltsov 已提交
1125 1126 1127
            boolean staticMembers, @NotNull NamedMembers namedMembers, @NotNull String propertyName,
            @NotNull String context
            ) {
1128 1129 1130 1131
        if (namedMembers.propertyDescriptors != null) {
            return;
        }
        
1132
        if (namedMembers.propertyAccessors == null) {
1133 1134 1135
            namedMembers.propertyDescriptors = Collections.emptySet();
            return;
        }
1136

S
Stepan Koltsov 已提交
1137
        TypeVariableResolver typeVariableResolver = TypeVariableResolvers.classTypeVariableResolver(owner, context);
1138

1139 1140 1141 1142
        class GroupingValue {
            PropertyAccessorData getter;
            PropertyAccessorData setter;
            PropertyAccessorData field;
1143
            boolean ext;
1144
        }
1145 1146
        
        Map<Object, GroupingValue> map = new HashMap<Object, GroupingValue>();
1147

1148
        for (PropertyAccessorData propertyAccessor : namedMembers.propertyAccessors) {
1149

1150 1151 1152 1153 1154
            Object key = propertyKeyForGrouping(propertyAccessor);
            
            GroupingValue value = map.get(key);
            if (value == null) {
                value = new GroupingValue();
1155
                value.ext = propertyAccessor.getReceiverType() != null;
1156 1157
                map.put(key, value);
            }
1158

1159 1160 1161 1162
            if (value.ext != (propertyAccessor.getReceiverType() != null)) {
                throw new IllegalStateException("internal error, incorrect key");
            }

1163 1164 1165 1166 1167 1168 1169 1170 1171 1172 1173 1174 1175 1176 1177 1178 1179 1180
            if (propertyAccessor.isGetter()) {
                if (value.getter != null) {
                    throw new IllegalStateException("oops, duplicate key");
                }
                value.getter = propertyAccessor;
            } else if (propertyAccessor.isSetter()) {
                if (value.setter != null) {
                    throw new IllegalStateException("oops, duplicate key");
                }
                value.setter = propertyAccessor;
            } else if (propertyAccessor.isField()) {
                if (value.field != null) {
                    throw new IllegalStateException("oops, duplicate key");
                }
                value.field = propertyAccessor;
            } else {
                throw new IllegalStateException();
            }
1181
        }
1182

1183
        
1184 1185
        Set<VariableDescriptor> r = new HashSet<VariableDescriptor>(1);

1186 1187 1188 1189 1190 1191 1192 1193 1194 1195 1196 1197 1198 1199
        int regularProperitesCount = 0;
        for (GroupingValue members : map.values()) {
            if (!members.ext) {
                ++regularProperitesCount;
            }
        }

        for (GroupingValue members : map.values()) {

            // we cannot have more then one property with given name even if java code
            // has several fields, getters and setter of different types
            if (!members.ext && regularProperitesCount > 1) {
                continue;
            }
1200

1201
            boolean isFinal;
1202 1203 1204
            if (!scopeData.kotlin) {
                isFinal = true;
            } else if (members.setter == null && members.getter == null) {
1205 1206 1207 1208 1209 1210 1211 1212
                isFinal = false;
            } else if (members.getter != null) {
                isFinal = members.getter.getMember().isFinal();
            } else if (members.setter != null) {
                isFinal = members.setter.getMember().isFinal();
            } else {
                isFinal = false;
            }
1213

1214 1215 1216 1217 1218 1219 1220 1221 1222 1223
            PropertyAccessorData anyMember;
            if (members.getter != null) {
                anyMember = members.getter;
            } else if (members.field != null) {
                anyMember = members.field;
            } else if (members.setter != null) {
                anyMember = members.setter;
            } else {
                throw new IllegalStateException();
            }
1224

1225 1226 1227 1228 1229 1230
            boolean isVar;
            if (members.getter == null && members.setter == null) {
                isVar = !members.field.getMember().isFinal();
            } else {
                isVar = members.setter != null;
            }
1231 1232 1233 1234 1235 1236 1237 1238 1239 1240

            Modality modality;
            if (isFinal) {
                modality = Modality.FINAL;
            }
            else {
                modality = anyMember.getMember().isAbstract() ? Modality.ABSTRACT : Modality.OPEN;
            }


1241 1242
            PropertyDescriptor propertyDescriptor = new PropertyDescriptor(
                    owner,
A
Alex Tkachman 已提交
1243
                    resolveAnnotations(anyMember.getMember().psiMember),
1244
                    modality,
1245 1246 1247
                    resolveVisibilityFromPsiModifiers(anyMember.getMember().psiMember),
                    isVar,
                    false,
1248 1249
                    propertyName,
                    CallableMemberDescriptor.Kind.DECLARATION);
1250

1251 1252 1253
            PropertyGetterDescriptor getterDescriptor = null;
            PropertySetterDescriptor setterDescriptor = null;
            if (members.getter != null) {
A
Alex Tkachman 已提交
1254
                getterDescriptor = new PropertyGetterDescriptor(propertyDescriptor, resolveAnnotations(members.getter.getMember().psiMember), Modality.OPEN, Visibility.PUBLIC, true, false, CallableMemberDescriptor.Kind.DECLARATION);
1255 1256
            }
            if (members.setter != null) {
A
Alex Tkachman 已提交
1257
                setterDescriptor = new PropertySetterDescriptor(propertyDescriptor, resolveAnnotations(members.setter.getMember().psiMember), Modality.OPEN, Visibility.PUBLIC, true, false, CallableMemberDescriptor.Kind.DECLARATION);
1258
            }
1259

1260
            propertyDescriptor.initialize(getterDescriptor, setterDescriptor);
1261

S
Stepan Koltsov 已提交
1262
            List<TypeParameterDescriptor> typeParameters = new ArrayList<TypeParameterDescriptor>(0);
1263 1264 1265

            if (members.setter != null) {
                PsiMethodWrapper method = (PsiMethodWrapper) members.setter.getMember();
1266

1267
                if (anyMember == members.setter) {
S
Stepan Koltsov 已提交
1268
                    typeParameters = resolveMethodTypeParameters(method, propertyDescriptor, typeVariableResolver);
1269 1270 1271 1272 1273 1274
                }
            }
            if (members.getter != null) {
                PsiMethodWrapper method = (PsiMethodWrapper) members.getter.getMember();

                if (anyMember == members.getter) {
S
Stepan Koltsov 已提交
1275
                    typeParameters = resolveMethodTypeParameters(method, propertyDescriptor, typeVariableResolver);
1276 1277 1278
                }
            }

S
Stepan Koltsov 已提交
1279
            TypeVariableResolver typeVariableResolverForPropertyInternals = TypeVariableResolvers.typeVariableResolverFromTypeParameters(typeParameters, propertyDescriptor, "property " + propertyName + " in " + context);
1280

1281 1282 1283 1284
            JetType propertyType;
            if (anyMember.getType().getTypeString().length() > 0) {
                propertyType = semanticServices.getTypeTransformer().transformToType(anyMember.getType().getTypeString(), typeVariableResolverForPropertyInternals);
            } else {
1285
                propertyType = semanticServices.getTypeTransformer().transformToType(anyMember.getType().getPsiType(), typeVariableResolverForPropertyInternals);
S
Stepan Koltsov 已提交
1286 1287 1288
                if (anyMember.getType().getPsiNotNullOwner().getModifierList().findAnnotation(JvmAbi.JETBRAINS_NOT_NULL_ANNOTATION.getFqName()) != null) {
                    propertyType = TypeUtils.makeNullableAsSpecified(propertyType, false);
                }
1289 1290 1291 1292 1293 1294 1295 1296
            }
            
            JetType receiverType;
            if (anyMember.getReceiverType() == null) {
                receiverType = null;
            } else if (anyMember.getReceiverType().getTypeString().length() > 0) {
                receiverType = semanticServices.getTypeTransformer().transformToType(anyMember.getReceiverType().getTypeString(), typeVariableResolverForPropertyInternals);
            } else {
1297
                receiverType = semanticServices.getTypeTransformer().transformToType(anyMember.getReceiverType().getPsiType(), typeVariableResolverForPropertyInternals);
1298 1299 1300 1301 1302 1303 1304
            }

            propertyDescriptor.setType(
                    propertyType,
                    typeParameters,
                    DescriptorUtils.getExpectedThisObjectIfNeeded(owner),
                    receiverType
1305
            );
1306 1307 1308 1309
            if (getterDescriptor != null) {
                getterDescriptor.initialize(propertyType);
            }
            if (setterDescriptor != null) {
1310
                setterDescriptor.initialize(new ValueParameterDescriptorImpl(setterDescriptor, 0, Collections.<AnnotationDescriptor>emptyList(), "p0"/*TODO*/, false, propertyDescriptor.getType(), false, null));
1311 1312 1313 1314 1315
            }

            semanticServices.getTrace().record(BindingContext.VARIABLE, anyMember.getMember().psiMember, propertyDescriptor);
            
            r.add(propertyDescriptor);
1316
        }
1317

1318
        namedMembers.propertyDescriptors = r;
1319
    }
1320

1321
    private void resolveNamedGroupFunctions(ClassOrNamespaceDescriptor owner, PsiClass psiClass, TypeSubstitutor typeSubstitutorForGenericSuperclasses, NamedMembers namedMembers, String methodName, ResolverScopeData scopeData) {
1322 1323 1324
        if (namedMembers.functionDescriptors != null) {
            return;
        }
1325 1326
        
        final Set<FunctionDescriptor> functions = new HashSet<FunctionDescriptor>();
1327

1328
        Set<SimpleFunctionDescriptor> functionsFromCurrent = Sets.newHashSet();
1329
        for (PsiMethodWrapper method : namedMembers.methods) {
1330 1331
            FunctionDescriptorImpl function = resolveMethodToFunctionDescriptor(owner, psiClass,
                    method);
1332
            if (function != null) {
1333
                functionsFromCurrent.add((SimpleFunctionDescriptor) function);
1334 1335 1336 1337 1338 1339
            }
        }

        if (owner instanceof ClassDescriptor) {
            ClassDescriptor classDescriptor = (ClassDescriptor) owner;

1340
            Set<SimpleFunctionDescriptor> functionsFromSupertypes = getFunctionsFromSupertypes(scopeData, methodName);
1341

S
Stepan Koltsov 已提交
1342
            OverrideResolver.generateOverridesInFunctionGroup(methodName, functionsFromSupertypes, functionsFromCurrent, classDescriptor, new OverrideResolver.DescriptorSink() {
1343
                @Override
S
Stepan Koltsov 已提交
1344 1345
                public void addToScope(@NotNull CallableMemberDescriptor fakeOverride) {
                    functions.add((FunctionDescriptor) fakeOverride);
1346
                }
1347 1348

                @Override
S
Stepan Koltsov 已提交
1349
                public void conflict(@NotNull CallableMemberDescriptor fromSuper, @NotNull CallableMemberDescriptor fromCurrent) {
1350 1351
                    // nop
                }
1352 1353 1354 1355 1356 1357 1358 1359 1360
            });

        }

        functions.addAll(functionsFromCurrent);

        namedMembers.functionDescriptors = functions;
    }
    
1361 1362
    private Set<SimpleFunctionDescriptor> getFunctionsFromSupertypes(ResolverScopeData scopeData, String methodName) {
        Set<SimpleFunctionDescriptor> r = new HashSet<SimpleFunctionDescriptor>();
1363 1364
        for (JetType supertype : getSupertypes(scopeData)) {
            for (FunctionDescriptor function : supertype.getMemberScope().getFunctions(methodName)) {
1365
                r.add((SimpleFunctionDescriptor) function);
1366
            }
1367
        }
1368
        return r;
1369 1370
    }

1371
    private ResolverScopeData getResolverScopeData(@NotNull ClassOrNamespaceDescriptor owner, PsiClassWrapper psiClass) {
1372
        // TODO: store scopeData in Java*Scope
1373
        ResolverScopeData scopeData;
1374
        boolean staticMembers;
1375 1376
        if (owner instanceof JavaNamespaceDescriptor) {
            scopeData = namespaceDescriptorCacheByFqn.get(((JavaNamespaceDescriptor) owner).getQualifiedName());
1377
            staticMembers = true;
1378
        } else if (owner instanceof ClassDescriptor) {
S
Stepan Koltsov 已提交
1379
            scopeData = classDescriptorCache.get(new FqName(psiClass.getQualifiedName()));
1380
            staticMembers = false;
1381
        } else {
1382
            throw new IllegalStateException("unknown owner: " + owner.getClass().getName());
1383 1384 1385 1386 1387
        }
        if (scopeData == null) {
            throw new IllegalStateException();
        }
        
1388 1389
        if (scopeData.namedMembersMap == null) {
            scopeData.namedMembersMap = JavaDescriptorResolverHelper.getNamedMembers(psiClass, staticMembers, scopeData.kotlin);
1390 1391
        }
        
1392
        return scopeData;
1393
    }
A
Andrey Breslav 已提交
1394

A
Andrey Breslav 已提交
1395
    @NotNull
1396
    public Set<FunctionDescriptor> resolveFunctionGroup(@NotNull ClassOrNamespaceDescriptor descriptor, @NotNull PsiClass psiClass, @NotNull String methodName, boolean staticMembers) {
A
Andrey Breslav 已提交
1397

1398
        ResolverScopeData resolverScopeData = getResolverScopeData(descriptor, new PsiClassWrapper(psiClass));
A
Andrey Breslav 已提交
1399

1400 1401 1402
        Map<String, NamedMembers> namedMembersMap = resolverScopeData.namedMembersMap;

        NamedMembers namedMembers = namedMembersMap.get(methodName);
1403 1404
        if (namedMembers != null && namedMembers.methods != null) {
            TypeSubstitutor typeSubstitutor = typeSubstitutorForGenericSupertypes(resolverScopeData);
1405

1406 1407 1408
            resolveNamedGroupFunctions(descriptor, psiClass, typeSubstitutor, namedMembers, methodName, resolverScopeData);

            return namedMembers.functionDescriptors;
1409
        } else {
1410
            return Collections.emptySet();
1411
        }
1412 1413
    }

1414
    private TypeSubstitutor createSubstitutorForGenericSupertypes(@Nullable ClassDescriptor classDescriptor) {
A
Andrey Breslav 已提交
1415 1416 1417 1418 1419 1420 1421 1422 1423
        TypeSubstitutor typeSubstitutor;
        if (classDescriptor != null) {
            typeSubstitutor = TypeUtils.buildDeepSubstitutor(classDescriptor.getDefaultType());
        }
        else {
            typeSubstitutor = TypeSubstitutor.EMPTY;
        }
        return typeSubstitutor;
    }
1424

1425 1426 1427 1428 1429 1430 1431 1432 1433 1434 1435 1436 1437 1438 1439 1440 1441 1442 1443 1444 1445 1446 1447 1448
    private ValueParameterDescriptors resolveParameterDescriptors(DeclarationDescriptor containingDeclaration,
            List<PsiParameterWrapper> parameters, TypeVariableResolver typeVariableResolver) {
        List<ValueParameterDescriptor> result = new ArrayList<ValueParameterDescriptor>();
        JetType receiverType = null;
        int indexDelta = 0;
        for (int i = 0, parametersLength = parameters.size(); i < parametersLength; i++) {
            PsiParameterWrapper parameter = parameters.get(i);
            JvmMethodParameterMeaning meaning = resolveParameterDescriptor(containingDeclaration, i + indexDelta, parameter, typeVariableResolver);
            if (meaning.kind == JvmMethodParameterKind.TYPE_INFO) {
                // TODO
                --indexDelta;
            } else if (meaning.kind == JvmMethodParameterKind.REGULAR) {
                result.add(meaning.valueParameterDescriptor);
            } else if (meaning.kind == JvmMethodParameterKind.RECEIVER) {
                if (receiverType != null) {
                    throw new IllegalStateException("more then one receiver");
                }
                --indexDelta;
                receiverType = meaning.receiverType;
            }
        }
        return new ValueParameterDescriptors(receiverType, result);
    }

A
Andrey Breslav 已提交
1449
    @Nullable
S
Stepan Koltsov 已提交
1450
    private FunctionDescriptorImpl resolveMethodToFunctionDescriptor(ClassOrNamespaceDescriptor owner, final PsiClass psiClass, final PsiMethodWrapper method) {
1451

1452
        PsiType returnType = method.getReturnType();
A
Andrey Breslav 已提交
1453 1454 1455
        if (returnType == null) {
            return null;
        }
1456 1457
        ResolverScopeData scopeData = getResolverScopeData(owner, new PsiClassWrapper(psiClass));

1458 1459 1460 1461 1462 1463 1464 1465 1466
        boolean kotlin;
        if (owner instanceof JavaNamespaceDescriptor) {
            JavaNamespaceDescriptor javaNamespaceDescriptor = (JavaNamespaceDescriptor) owner;
            ResolverNamespaceData namespaceData = namespaceDescriptorCacheByFqn.get(javaNamespaceDescriptor.getQualifiedName());
            if (namespaceData == null) {
                throw new IllegalStateException("namespaceData not found by name " + javaNamespaceDescriptor.getQualifiedName());
            }
            kotlin = namespaceData.kotlin;
        } else {
S
Stepan Koltsov 已提交
1467
            ResolverBinaryClassData classData = classDescriptorCache.get(new FqName(psiClass.getQualifiedName()));
1468 1469 1470 1471 1472 1473
            if (classData == null) {
                throw new IllegalStateException("classData not found by name " + psiClass.getQualifiedName());
            }
            kotlin = classData.kotlin;
        }

1474
        // TODO: ugly
1475
        if (method.getJetMethod().kind() == JvmStdlibNames.JET_METHOD_KIND_PROPERTY) {
1476
            return null;
1477
        }
1478

S
Stepan Koltsov 已提交
1479 1480 1481 1482 1483 1484 1485 1486
        if (kotlin) {
            // TODO: unless maybe class explicitly extends Object
            String ownerClassName = method.getPsiMethod().getContainingClass().getQualifiedName();
            if (ownerClassName.equals("java.lang.Object")) {
                return null;
            }
        }

1487
        ClassOrNamespaceDescriptor classDescriptor;
1488
        if (scopeData instanceof ResolverBinaryClassData) {
1489
            ClassDescriptor classClassDescriptor = resolveClass(method.getPsiMethod().getContainingClass(), DescriptorSearchRule.INCLUDE_KOTLIN);
1490
            classDescriptor = classClassDescriptor;
1491 1492 1493
        }
        else {
            classDescriptor = resolveNamespace(method.getPsiMethod().getContainingClass());
1494
        }
1495 1496 1497
        if (classDescriptor == null) {
            return null;
        }
1498

1499
        SimpleFunctionDescriptorImpl functionDescriptorImpl = new SimpleFunctionDescriptorImpl(
A
Andrey Breslav 已提交
1500
                owner,
1501
                resolveAnnotations(method.getPsiMethod()),
1502 1503
                method.getName(),
                CallableMemberDescriptor.Kind.DECLARATION
A
Andrey Breslav 已提交
1504
        );
1505

S
Stepan Koltsov 已提交
1506 1507 1508
        String context = "method " + method.getName() + " in class " + psiClass.getQualifiedName();

        final TypeVariableResolver typeVariableResolverForParameters = TypeVariableResolvers.classTypeVariableResolver(classDescriptor, context);
1509

1510
        final List<TypeParameterDescriptor> methodTypeParameters = resolveMethodTypeParameters(method, functionDescriptorImpl, typeVariableResolverForParameters);
1511

S
Stepan Koltsov 已提交
1512
        TypeVariableResolver methodTypeVariableResolver = TypeVariableResolvers.typeVariableResolverFromTypeParameters(methodTypeParameters, functionDescriptorImpl, context);
1513 1514


1515
        ValueParameterDescriptors valueParameterDescriptors = resolveParameterDescriptors(functionDescriptorImpl, method.getParameters(), methodTypeVariableResolver);
A
Andrey Breslav 已提交
1516
        functionDescriptorImpl.initialize(
1517
                valueParameterDescriptors.receiverType,
A
Andrey Breslav 已提交
1518
                DescriptorUtils.getExpectedThisObjectIfNeeded(classDescriptor),
1519
                methodTypeParameters,
1520
                valueParameterDescriptors.descriptors,
1521
                makeReturnType(returnType, method, methodTypeVariableResolver),
1522 1523
                Modality.convertFromFlags(method.getPsiMethod().hasModifierProperty(PsiModifier.ABSTRACT), !method.isFinal()),
                resolveVisibilityFromPsiModifiers(method.getPsiMethod())
A
Andrey Breslav 已提交
1524
        );
1525
        semanticServices.getTrace().record(BindingContext.FUNCTION, method.getPsiMethod(), functionDescriptorImpl);
A
Andrey Breslav 已提交
1526
        FunctionDescriptor substitutedFunctionDescriptor = functionDescriptorImpl;
S
Stepan Koltsov 已提交
1527 1528
        if (method.getPsiMethod().getContainingClass() != psiClass && !method.isStatic()) {
            throw new IllegalStateException("non-static method in subclass");
A
Andrey Breslav 已提交
1529
        }
1530
        return (FunctionDescriptorImpl) substitutedFunctionDescriptor;
A
Andrey Breslav 已提交
1531
    }
1532

1533 1534 1535 1536 1537 1538 1539 1540 1541 1542 1543 1544 1545 1546 1547 1548 1549 1550 1551 1552 1553 1554
    private List<AnnotationDescriptor> resolveAnnotations(PsiModifierListOwner owner) {
        PsiAnnotation[] psiAnnotations = owner.getModifierList().getAnnotations();
        List<AnnotationDescriptor> r = Lists.newArrayListWithCapacity(psiAnnotations.length);
        for (PsiAnnotation psiAnnotation : psiAnnotations) {
            AnnotationDescriptor annotation = resolveAnnotation(psiAnnotation);
            if (annotation != null) {
                r.add(annotation);
            }
        }
        return r;
    }

    @Nullable
    private AnnotationDescriptor resolveAnnotation(PsiAnnotation psiAnnotation) {
        AnnotationDescriptor annotation = new AnnotationDescriptor();

        String qname = psiAnnotation.getQualifiedName();
        if (qname.startsWith("java.lang.annotation.") || qname.startsWith("jet.runtime.typeinfo.") || qname.equals(JvmAbi.JETBRAINS_NOT_NULL_ANNOTATION.getFqName())) {
            // TODO
            return null;
        }

1555
        ClassDescriptor clazz = resolveClass(new FqName(psiAnnotation.getQualifiedName()), DescriptorSearchRule.INCLUDE_KOTLIN);
1556 1557 1558 1559
        if (clazz == null) {
            return null;
        }
        annotation.setAnnotationType(clazz.getDefaultType());
1560
        ArrayList<CompileTimeConstant<?>> valueArguments = new ArrayList<CompileTimeConstant<?>>();
1561 1562 1563 1564 1565 1566 1567 1568 1569 1570 1571 1572 1573 1574 1575 1576 1577 1578 1579 1580 1581 1582 1583 1584 1585 1586 1587 1588

        PsiAnnotationParameterList parameterList = psiAnnotation.getParameterList();
        for (PsiNameValuePair psiNameValuePair : parameterList.getAttributes()) {
            PsiAnnotationMemberValue value = psiNameValuePair.getValue();
            // todo
            assert value instanceof PsiLiteralExpression;
            Object literalValue = ((PsiLiteralExpression) value).getValue();
            if(literalValue instanceof String)
                valueArguments.add(new StringValue((String) literalValue));
            else if(literalValue instanceof Byte)
                valueArguments.add(new ByteValue((Byte) literalValue));
            else if(literalValue instanceof Short)
                valueArguments.add(new ShortValue((Short) literalValue));
            else if(literalValue instanceof Character)
                valueArguments.add(new CharValue((Character) literalValue));
            else if(literalValue instanceof Integer)
                valueArguments.add(new IntValue((Integer) literalValue));
            else if(literalValue instanceof Long)
                valueArguments.add(new LongValue((Long) literalValue));
            else if(literalValue instanceof Float)
                valueArguments.add(new FloatValue((Float) literalValue));
            else if(literalValue instanceof Double)
                valueArguments.add(new DoubleValue((Double) literalValue));
            else if(literalValue == null)
                valueArguments.add(NullValue.NULL);
        }

        annotation.setValueArguments(valueArguments); // TODO
1589 1590 1591
        return annotation;
    }

1592
    public List<FunctionDescriptor> resolveMethods(@NotNull PsiClass psiClass, @NotNull ClassOrNamespaceDescriptor containingDeclaration) {
1593 1594
        ResolverScopeData scopeData = getResolverScopeData(containingDeclaration, new PsiClassWrapper(psiClass));

1595
        TypeSubstitutor substitutorForGenericSupertypes = typeSubstitutorForGenericSupertypes(scopeData);
1596

1597
        List<FunctionDescriptor> functions = new ArrayList<FunctionDescriptor>();
1598 1599 1600 1601 1602

        for (Map.Entry<String, NamedMembers> entry : scopeData.namedMembersMap.entrySet()) {
            String methodName = entry.getKey();
            NamedMembers namedMembers = entry.getValue();
            resolveNamedGroupFunctions(containingDeclaration, psiClass, substitutorForGenericSupertypes, namedMembers, methodName, scopeData);
1603
            functions.addAll(namedMembers.functionDescriptors);
1604
        }
1605

1606 1607
        return functions;
    }
1608

1609 1610 1611 1612 1613 1614 1615 1616 1617 1618 1619 1620 1621 1622 1623 1624 1625 1626
    private Collection<JetType> getSupertypes(ResolverScopeData scope) {
        if (scope instanceof ResolverBinaryClassData) {
            return ((ResolverBinaryClassData) scope).classDescriptor.getSupertypes();
        } else if (scope instanceof ResolverNamespaceData) {
            return Collections.emptyList();
        } else {
            throw new IllegalStateException();
        }
    }

    private TypeSubstitutor typeSubstitutorForGenericSupertypes(ResolverScopeData scopeData) {
        if (scopeData instanceof ResolverClassData) {
            return createSubstitutorForGenericSupertypes(((ResolverClassData) scopeData).getClassDescriptor());
        } else {
            return TypeSubstitutor.EMPTY;
        }
    }

1627
    private List<TypeParameterDescriptor> resolveMethodTypeParameters(
1628
            @NotNull PsiMethodWrapper method,
1629
            @NotNull DeclarationDescriptor functionDescriptor,
1630 1631
            @NotNull TypeVariableResolver classTypeVariableResolver) {

1632
        List<TypeParameterDescriptorInitialization> typeParametersIntialization;
1633
        if (method.getJetMethod().typeParameters().length() > 0) {
1634
            typeParametersIntialization = resolveMethodTypeParametersFromJetSignature(
S
Stepan Koltsov 已提交
1635
                    method.getJetMethod().typeParameters(), method.getPsiMethod(), functionDescriptor);
1636
        } else {
1637
            typeParametersIntialization = makeUninitializedTypeParameters(functionDescriptor, method.getPsiMethod().getTypeParameters());
1638
        }
1639

S
Stepan Koltsov 已提交
1640 1641
        String context = "method " + method.getName() + " in class " + method.getPsiMethod().getContainingClass().getQualifiedName();
        initializeTypeParameters(typeParametersIntialization, functionDescriptor, context);
1642 1643 1644 1645 1646 1647 1648
        
        List<TypeParameterDescriptor> typeParameters = Lists.newArrayListWithCapacity(typeParametersIntialization.size());
        
        for (TypeParameterDescriptorInitialization tpdi : typeParametersIntialization) {
            typeParameters.add(tpdi.descriptor);
        }
        
1649 1650
        return typeParameters;
    }
1651 1652

    /**
S
Stepan Koltsov 已提交
1653
     * @see #resolveClassTypeParametersFromJetSignature(String, com.intellij.psi.PsiClass, org.jetbrains.jet.lang.descriptors.ClassDescriptor)
1654
     */
S
Stepan Koltsov 已提交
1655 1656
    private List<TypeParameterDescriptorInitialization> resolveMethodTypeParametersFromJetSignature(String jetSignature,
            final PsiMethod method, final DeclarationDescriptor functionDescriptor)
1657
    {
S
Stepan Koltsov 已提交
1658 1659
        String context = "method " + method.getName() + " in class " + method.getContainingClass().getQualifiedName();
        JetSignatureTypeParametersVisitor jetSignatureTypeParametersVisitor = new JetSignatureTypeParametersVisitor(functionDescriptor, method, context);
1660 1661
        new JetSignatureReader(jetSignature).acceptFormalTypeParametersOnly(jetSignatureTypeParametersVisitor);
        return jetSignatureTypeParametersVisitor.r;
1662 1663
    }

1664 1665
    private JetType makeReturnType(PsiType returnType, PsiMethodWrapper method,
            @NotNull TypeVariableResolver typeVariableResolver) {
1666 1667 1668

        String returnTypeFromAnnotation = method.getJetMethod().returnType();

S
Stepan Koltsov 已提交
1669
        JetType transformedType;
1670
        if (returnTypeFromAnnotation.length() > 0) {
1671
            transformedType = semanticServices.getTypeTransformer().transformToType(returnTypeFromAnnotation, typeVariableResolver);
S
Stepan Koltsov 已提交
1672
        } else {
1673
            transformedType = semanticServices.getTypeTransformer().transformToType(returnType, typeVariableResolver);
S
Stepan Koltsov 已提交
1674
        }
1675 1676
        if (method.getJetMethod().returnTypeNullable()) {
            return TypeUtils.makeNullableAsSpecified(transformedType, true);
S
Stepan Koltsov 已提交
1677 1678
        } else if (method.getPsiMethod().getModifierList().findAnnotation(JvmAbi.JETBRAINS_NOT_NULL_ANNOTATION.getFqName()) != null) {
            return TypeUtils.makeNullableAsSpecified(transformedType, false);
1679 1680 1681 1682 1683
        } else {
            return transformedType;
        }
    }

1684
    private static Visibility resolveVisibilityFromPsiModifiers(PsiModifierListOwner modifierListOwner) {
1685 1686 1687 1688 1689 1690
        //TODO report error
        return modifierListOwner.hasModifierProperty(PsiModifier.PUBLIC) ? Visibility.PUBLIC :
                                        (modifierListOwner.hasModifierProperty(PsiModifier.PRIVATE) ? Visibility.PRIVATE :
                                        (modifierListOwner.hasModifierProperty(PsiModifier.PROTECTED) ? Visibility.PROTECTED : Visibility.INTERNAL));
    }

1691
    public List<ClassDescriptor> resolveInnerClasses(DeclarationDescriptor owner, PsiClass psiClass, boolean staticMembers) {
1692 1693 1694 1695
        if (staticMembers) {
            return new ArrayList<ClassDescriptor>(0);
        }

1696 1697 1698
        PsiClass[] innerPsiClasses = psiClass.getInnerClasses();
        List<ClassDescriptor> r = new ArrayList<ClassDescriptor>(innerPsiClasses.length);
        for (PsiClass innerPsiClass : innerPsiClasses) {
1699 1700 1701 1702
            if (innerPsiClass.hasModifierProperty(PsiModifier.PRIVATE)) {
                // TODO: hack against inner classes
                continue;
            }
1703 1704 1705
            if (innerPsiClass.getName().equals(JvmAbi.CLASS_OBJECT_CLASS_NAME)) {
                continue;
            }
1706
            r.add(resolveClass(innerPsiClass, DescriptorSearchRule.IGNORE_IF_FOUND_IN_KOTLIN));
1707 1708 1709
        }
        return r;
    }
1710
}