classMemberSym.updateInfo(thisTpMap.apply(classMemberSym.info()));
    protected Symbol getClassSymbol(Symbol ifaceSym) {        if (ifaceSym.isPrimaryConstructor())            return getClassSymbol(ifaceSym.primaryConstructorClass())                .constructor();        if (!needInterface(ifaceSym))            return ifaceSym;        Symbol classSym = (Symbol)ifaceToClass.get(ifaceSym);        if (classSym == null) {            classSym = cloneSymbol(ifaceSym, ifaceSym.owner());            classSym.name = className(ifaceSym.name);            classSym.flags &= ~Modifiers.INTERFACE;            Symbol ifaceConstrSym = ifaceSym.constructor();            Symbol classConstrSym = classSym.constructor();            classConstrSym.name = className(ifaceConstrSym.name);            Scope ifaceOwnerMembers = ifaceSym.owner().members();            ifaceOwnerMembers.enter(classSym);            ifaceOwnerMembers.enter(classConstrSym);            // Clone type and value parameters of constructor.            Map classSubst = newClassSubst(classSym);            Symbol[] tparams = classConstrSym.typeParams();            for (int i = 0; i < tparams.length; ++i) {                Symbol newParam = cloneSymbol(tparams[i], classConstrSym);                classSubst.put(tparams[i], newParam);            }            SymbolSubstTypeMap paramsSubst =                new SymbolSubstTypeMap(classSubst, Collections.EMPTY_MAP);            // Play it safe and make sure that classSubst won't be            // modified anymore.            classSubst = Collections.unmodifiableMap(classSubst);            Symbol[] vparams = classConstrSym.valueParams();            for (int i = 0; i < vparams.length; ++i) {                vparams[i].setOwner(classConstrSym);                vparams[i].updateInfo(paramsSubst.apply(vparams[i].info()));            }            // Clone all members, entering them in the class scope.            Map classMembersMap = newClassMemberMap(classSym);            Scope classMembers = new Scope();            Scope.SymbolIterator ifaceMembersIt =                new Scope.UnloadIterator(ifaceSym.members().iterator());            while (ifaceMembersIt.hasNext()) {                Symbol ifaceMemberSym = ifaceMembersIt.next();                if (memberMovesToInterface(ifaceMemberSym)                    || ifaceMemberSym.isPrimaryConstructor())                    continue;                Symbol classMemberSym;                if (memberGoesInInterface(ifaceMemberSym)) {                    if (ifaceMemberSym.isPrivate()) {                        ifaceMemberSym.name = uniqueName(ifaceMemberSym);                        ifaceMemberSym.flags ^= Modifiers.PRIVATE;                    } else if (ifaceMemberSym.isProtected())                        ifaceMemberSym.flags ^= Modifiers.PROTECTED;                    classMemberSym =                        deepCloneSymbol(ifaceMemberSym, classSym, paramsSubst);                    ifaceMemberSym.flags |= Modifiers.DEFERRED;                    // TODO substitute symbols in ThisTypes appearing in                    // the type of the class member                    classMembersMap.put(ifaceMemberSym, classMemberSym);                } else {                    // Member doesn't go in interface, we just make it                    // owned by the class.                    classMemberSym = ifaceMemberSym;                    classMemberSym.setOwner(classSym);                }                Type nextMemberTp = classMemberSym.nextInfo();                classMemberSym.updateInfo(paramsSubst.apply(nextMemberTp));                classMembers.enterOrOverload(classMemberSym);                if (classMemberSym.isClass())                    classMembers.enterOrOverload(classMemberSym.constructor());            }            // Give correct type to the class symbol by using class            // symbols for its parents, and by adding the interface            // among them.            Type[] oldClassParents = classSym.parents();            int oldParentsCount = oldClassParents.length;            Type[] newClassParents = new Type[oldParentsCount + 1];            for (int i = 0; i < oldParentsCount; ++i) {                switch (oldClassParents[i]) {                case TypeRef(Type pre, Symbol sym, Type[] args):                    Type newTp = Type.typeRef(pre, getClassSymbol(sym), args);                    newClassParents[i] = paramsSubst.apply(newTp);                    break;                default:                    throw Debug.abort("unexpected type for parent", oldClassParents[i]);                }            }            newClassParents[oldParentsCount] = paramsSubst.apply(ifaceSym.type());            // TODO setInfo cannot be used here because the type then            // goes through transformInfo. Maybe setInfo should behave            // like updateInfo.            classSym.updateInfo(Type.compoundType(newClassParents,                                                  classMembers,                                                  classSym));            classConstrSym.updateInfo(substResType(substParams(classConstrSym.info(),                                                               paramsSubst),                                                   ifaceSym,                                                   classSym));            ifaceToClass.put(ifaceSym, classSym);            classToIFace.put(classSym, ifaceSym);        }        return classSym;    }