Program: 12030
Project: 12030
Buggy source:
private void extractClone(){
  this.cloneInfo=new CloneInformation();
  Set<ITypeBinding> requiredImportTypeBindings=new LinkedHashSet<ITypeBinding>();
  ITypeBinding commonSuperTypeOfSourceTypeDeclarations=null;
  if (sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclarations.get(1).resolveBinding()) && sourceTypeDeclarations.get(0).resolveBinding().getQualifiedName().equals(sourceTypeDeclarations.get(1).resolveBinding().getQualifiedName())) {
    cloneInfo.sourceCompilationUnit=sourceCompilationUnits.get(0);
    cloneInfo.sourceICompilationUnit=(ICompilationUnit)cloneInfo.sourceCompilationUnit.getJavaElement();
    cloneInfo.sourceTypeDeclaration=sourceTypeDeclarations.get(0);
    cloneInfo.sourceRewriter=ASTRewrite.create(cloneInfo.sourceTypeDeclaration.getAST());
    cloneInfo.ast=cloneInfo.sourceTypeDeclaration.getAST();
  }
 else {
    ITypeBinding typeBinding1=sourceTypeDeclarations.get(0).resolveBinding();
    ITypeBinding typeBinding2=sourceTypeDeclarations.get(1).resolveBinding();
    commonSuperTypeOfSourceTypeDeclarations=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
    if (commonSuperTypeOfSourceTypeDeclarations != null) {
      if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.PULL_UP_TO_EXISTING_SUPERCLASS)) {
        IJavaElement javaElement=commonSuperTypeOfSourceTypeDeclarations.getJavaElement();
        javaElementsToOpenInEditor.add(javaElement);
        ICompilationUnit iCompilationUnit=(ICompilationUnit)javaElement.getParent();
        ASTParser parser=ASTParser.newParser(ASTReader.JLS);
        parser.setKind(ASTParser.K_COMPILATION_UNIT);
        parser.setSource(iCompilationUnit);
        parser.setResolveBindings(true);
        CompilationUnit compilationUnit=(CompilationUnit)parser.createAST(null);
        List<AbstractTypeDeclaration> typeDeclarations=compilationUnit.types();
        for (        AbstractTypeDeclaration abstractTypeDeclaration : typeDeclarations) {
          if (abstractTypeDeclaration instanceof TypeDeclaration) {
            TypeDeclaration typeDeclaration=(TypeDeclaration)abstractTypeDeclaration;
            if (typeDeclaration.resolveBinding().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)) {
              cloneInfo.sourceCompilationUnit=compilationUnit;
              cloneInfo.sourceICompilationUnit=iCompilationUnit;
              cloneInfo.sourceTypeDeclaration=typeDeclaration;
              cloneInfo.sourceRewriter=ASTRewrite.create(cloneInfo.sourceTypeDeclaration.getAST());
              cloneInfo.ast=cloneInfo.sourceTypeDeclaration.getAST();
              cloneInfo.superclassNotDirectlyInheritedFromRefactoredSubclasses=!superclassDirectlyInheritedFromRefactoredSubclasses(commonSuperTypeOfSourceTypeDeclarations,typeBinding1,typeBinding2);
              break;
            }
          }
        }
        MultiTextEdit multiTextEdit=new MultiTextEdit();
        CompilationUnitChange compilationUnitChange=new CompilationUnitChange("String_Node_Str",iCompilationUnit);
        compilationUnitChange.setEdit(multiTextEdit);
        compilationUnitChanges.put(iCompilationUnit,compilationUnitChange);
      }
 else {
        if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.EXTRACT_STATIC_METHOD_TO_NEW_UTILITY_CLASS)) {
          cloneInfo.extractUtilityClass=true;
        }
        if (cloneInfo.extractUtilityClass) {
          cloneInfo.intermediateClassName="String_Node_Str";
        }
 else {
          cloneInfo.intermediateClassName="String_Node_Str" + commonSuperTypeOfSourceTypeDeclarations.getName();
        }
        ClassObject commonSuperType=ASTReader.getSystemObject().getClassObject(commonSuperTypeOfSourceTypeDeclarations.getQualifiedName());
        CompilationUnit compilationUnit=null;
        if (commonSuperType != null) {
          compilationUnit=findCompilationUnit(commonSuperType.getAbstractTypeDeclaration());
        }
 else {
          compilationUnit=sourceCompilationUnits.get(0);
        }
        if (compilationUnit.getPackage() != null) {
          cloneInfo.intermediateClassPackageBinding=compilationUnit.getPackage().resolveBinding();
        }
        ICompilationUnit iCompilationUnit=(ICompilationUnit)compilationUnit.getJavaElement();
        IContainer container=(IContainer)iCompilationUnit.getResource().getParent();
        if (container instanceof IProject) {
          IProject contextProject=(IProject)container;
          cloneInfo.file=contextProject.getFile(cloneInfo.intermediateClassName + "String_Node_Str");
        }
 else         if (container instanceof IFolder) {
          IFolder contextFolder=(IFolder)container;
          cloneInfo.file=contextFolder.getFile(cloneInfo.intermediateClassName + "String_Node_Str");
        }
        boolean intermediateAlreadyExists=false;
        ICompilationUnit intermediateICompilationUnit=JavaCore.createCompilationUnitFrom(cloneInfo.file);
        javaElementsToOpenInEditor.add(intermediateICompilationUnit);
        ASTParser intermediateParser=ASTParser.newParser(ASTReader.JLS);
        intermediateParser.setKind(ASTParser.K_COMPILATION_UNIT);
        if (cloneInfo.file.exists()) {
          intermediateAlreadyExists=true;
          intermediateParser.setSource(intermediateICompilationUnit);
          intermediateParser.setResolveBindings(true);
        }
 else {
          cloneInfo.document=new Document();
          intermediateParser.setSource(cloneInfo.document.get().toCharArray());
        }
        CompilationUnit intermediateCompilationUnit=(CompilationUnit)intermediateParser.createAST(null);
        AST intermediateAST=intermediateCompilationUnit.getAST();
        ASTRewrite intermediateRewriter=ASTRewrite.create(intermediateAST);
        ListRewrite intermediateTypesRewrite=intermediateRewriter.getListRewrite(intermediateCompilationUnit,CompilationUnit.TYPES_PROPERTY);
        TypeDeclaration intermediateTypeDeclaration=null;
        if (intermediateAlreadyExists) {
          List<AbstractTypeDeclaration> abstractTypeDeclarations=intermediateCompilationUnit.types();
          for (          AbstractTypeDeclaration abstractTypeDeclaration : abstractTypeDeclarations) {
            if (abstractTypeDeclaration instanceof TypeDeclaration) {
              TypeDeclaration typeDeclaration=(TypeDeclaration)abstractTypeDeclaration;
              if (typeDeclaration.getName().getIdentifier().equals(cloneInfo.intermediateClassName)) {
                intermediateTypeDeclaration=typeDeclaration;
                int intermediateModifiers=intermediateTypeDeclaration.getModifiers();
                if ((intermediateModifiers & Modifier.ABSTRACT) == 0 && !cloneInfo.extractUtilityClass) {
                  ListRewrite intermediateModifiersRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.MODIFIERS2_PROPERTY);
                  intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
                }
                break;
              }
            }
          }
          MultiTextEdit intermediateMultiTextEdit=new MultiTextEdit();
          CompilationUnitChange intermediateCompilationUnitChange=new CompilationUnitChange("String_Node_Str",intermediateICompilationUnit);
          intermediateCompilationUnitChange.setEdit(intermediateMultiTextEdit);
          compilationUnitChanges.put(intermediateICompilationUnit,intermediateCompilationUnitChange);
        }
 else {
          if (compilationUnit.getPackage() != null) {
            intermediateRewriter.set(intermediateCompilationUnit,CompilationUnit.PACKAGE_PROPERTY,compilationUnit.getPackage(),null);
          }
          intermediateTypeDeclaration=intermediateAST.newTypeDeclaration();
          SimpleName intermediateName=intermediateAST.newSimpleName(cloneInfo.intermediateClassName);
          intermediateRewriter.set(intermediateTypeDeclaration,TypeDeclaration.NAME_PROPERTY,intermediateName,null);
          ListRewrite intermediateModifiersRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.MODIFIERS2_PROPERTY);
          intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD),null);
          if (!cloneInfo.extractUtilityClass) {
            intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
            Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
            if (commonSuperTypeOfSourceTypeDeclarations.isClass()) {
              intermediateRewriter.set(intermediateTypeDeclaration,TypeDeclaration.SUPERCLASS_TYPE_PROPERTY,intermediateAST.newSimpleType(intermediateAST.newSimpleName(commonSuperTypeOfSourceTypeDeclarations.getName())),null);
              typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
            }
            ListRewrite interfaceRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.SUPER_INTERFACE_TYPES_PROPERTY);
            if (commonSuperTypeOfSourceTypeDeclarations.isInterface()) {
              ITypeBinding[] superInterfaces=commonSuperTypeOfSourceTypeDeclarations.getInterfaces();
              int taggingSuperInterfaceCount=0;
              for (              ITypeBinding superInterface : superInterfaces) {
                if (ASTNodeMatcher.isTaggingInterface(superInterface)) {
                  taggingSuperInterfaceCount++;
                }
              }
              boolean allSuperInterfacesAreTaggingInterfaces=superInterfaces.length > 0 && taggingSuperInterfaceCount == superInterfaces.length;
              boolean bothSubClassesImplementCommonSuperType=ASTNodeMatcher.implementsInterface(typeBinding1,commonSuperTypeOfSourceTypeDeclarations) && ASTNodeMatcher.implementsInterface(typeBinding2,commonSuperTypeOfSourceTypeDeclarations);
              if (!allSuperInterfacesAreTaggingInterfaces && !bothSubClassesImplementCommonSuperType) {
                Type interfaceType=RefactoringUtility.generateTypeFromTypeBinding(commonSuperTypeOfSourceTypeDeclarations,intermediateAST,intermediateRewriter);
                interfaceRewrite.insertLast(interfaceType,null);
                typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
              }
            }
            List<Type> superInterfaceTypes1=sourceTypeDeclarations.get(0).superInterfaceTypes();
            List<Type> superInterfaceTypes2=sourceTypeDeclarations.get(1).superInterfaceTypes();
            for (            Type interfaceType1 : superInterfaceTypes1) {
              ITypeBinding interfaceTypeBinding1=interfaceType1.resolveBinding();
              for (              Type interfaceType2 : superInterfaceTypes2) {
                ITypeBinding interfaceTypeBinding2=interfaceType2.resolveBinding();
                if (interfaceTypeBinding1.isEqualTo(interfaceTypeBinding2) && interfaceTypeBinding1.getQualifiedName().equals(interfaceTypeBinding2.getQualifiedName()) && checkIfThisReferenceIsPassedAsArgumentToMethodInvocation(interfaceTypeBinding1)) {
                  interfaceRewrite.insertLast(interfaceType1,null);
                  typeBindings.add(interfaceTypeBinding1);
                  break;
                }
              }
            }
            ListRewrite bodyDeclarationsRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.BODY_DECLARATIONS_PROPERTY);
            Set<String> processedSuperConstructorBindingKeys=new LinkedHashSet<String>();
            for (            MethodDeclaration methodDeclaration1 : sourceTypeDeclarations.get(0).getMethods()) {
              if (methodDeclaration1.isConstructor()) {
                boolean matchingSuperConstructorCallFound=false;
                SuperConstructorInvocation superConstructorInvocation1=firstStatementIsSuperConstructorInvocation(methodDeclaration1);
                String superConstructorBindingKey1=superConstructorInvocation1 != null ? superConstructorInvocation1.resolveConstructorBinding().getKey() : null;
                for (                MethodDeclaration methodDeclaration2 : sourceTypeDeclarations.get(1).getMethods()) {
                  if (methodDeclaration2.isConstructor()) {
                    SuperConstructorInvocation superConstructorInvocation2=firstStatementIsSuperConstructorInvocation(methodDeclaration2);
                    if (superConstructorInvocation1 != null && superConstructorInvocation2 != null) {
                      List<Expression> superConstructorArguments1=superConstructorInvocation1.arguments();
                      List<Expression> superConstructorArguments2=superConstructorInvocation2.arguments();
                      if (matchingArgumentTypes(superConstructorArguments1,superConstructorArguments2) || superConstructorInvocation1.resolveConstructorBinding().isEqualTo(superConstructorInvocation2.resolveConstructorBinding())) {
                        matchingSuperConstructorCallFound=true;
                        if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey1)) {
                          processedSuperConstructorBindingKeys.add(superConstructorBindingKey1);
                          if (compareStatements(sourceCompilationUnits.get(0).getTypeRoot(),sourceCompilationUnits.get(1).getTypeRoot(),superConstructorInvocation1,superConstructorInvocation2)) {
                            MethodDeclaration constructor=copyConstructor(methodDeclaration1,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                            bodyDeclarationsRewrite.insertLast(constructor,null);
                          }
 else {
                            MethodDeclaration constructor=intermediateAST.newMethodDeclaration();
                            intermediateRewriter.set(constructor,MethodDeclaration.NAME_PROPERTY,intermediateName,null);
                            intermediateRewriter.set(constructor,MethodDeclaration.CONSTRUCTOR_PROPERTY,true,null);
                            ListRewrite constructorModifierRewriter=intermediateRewriter.getListRewrite(constructor,MethodDeclaration.MODIFIERS2_PROPERTY);
                            List<IExtendedModifier> modifiers=methodDeclaration1.modifiers();
                            for (                            IExtendedModifier modifier : modifiers) {
                              if (modifier instanceof Modifier) {
                                constructorModifierRewriter.insertLast((Modifier)modifier,null);
                              }
                            }
                            ListRewrite parameterRewriter=intermediateRewriter.getListRewrite(constructor,MethodDeclaration.PARAMETERS_PROPERTY);
                            SuperConstructorInvocation superConstructorInvocation=intermediateAST.newSuperConstructorInvocation();
                            ListRewrite argumentRewriter=intermediateRewriter.getListRewrite(superConstructorInvocation,SuperConstructorInvocation.ARGUMENTS_PROPERTY);
                            Map<String,Integer> parameterTypeCounterMap=new LinkedHashMap<String,Integer>();
                            for (                            ITypeBinding argumentTypeBinding : superConstructorInvocation1.resolveConstructorBinding().getParameterTypes()) {
                              SingleVariableDeclaration parameter=intermediateAST.newSingleVariableDeclaration();
                              typeBindings.add(argumentTypeBinding);
                              Type parameterType=RefactoringUtility.generateTypeFromTypeBinding(argumentTypeBinding,intermediateAST,intermediateRewriter);
                              intermediateRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,parameterType,null);
                              String typeName=argumentTypeBinding.getName();
                              String parameterName=typeName.replaceFirst(Character.toString(typeName.charAt(0)),Character.toString(Character.toLowerCase(typeName.charAt(0))));
                              if (parameterTypeCounterMap.containsKey(argumentTypeBinding.getKey())) {
                                int previousCounter=parameterTypeCounterMap.get(argumentTypeBinding.getKey());
                                parameterName+=previousCounter;
                                int currentCounter=previousCounter + 1;
                                parameterTypeCounterMap.put(argumentTypeBinding.getKey(),currentCounter);
                              }
 else {
                                parameterTypeCounterMap.put(argumentTypeBinding.getKey(),1);
                              }
                              SimpleName parameterSimpleName=intermediateAST.newSimpleName(parameterName);
                              intermediateRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,parameterSimpleName,null);
                              parameterRewriter.insertLast(parameter,null);
                              argumentRewriter.insertLast(parameterSimpleName,null);
                            }
                            Block constructorBody=intermediateAST.newBlock();
                            ListRewrite constructorBodyRewriter=intermediateRewriter.getListRewrite(constructorBody,Block.STATEMENTS_PROPERTY);
                            constructorBodyRewriter.insertLast(superConstructorInvocation,null);
                            intermediateRewriter.set(constructor,MethodDeclaration.BODY_PROPERTY,constructorBody,null);
                            bodyDeclarationsRewrite.insertLast(constructor,null);
                          }
                        }
                      }
                    }
                  }
                }
                if (!matchingSuperConstructorCallFound && superConstructorInvocation1 != null) {
                  if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey1)) {
                    processedSuperConstructorBindingKeys.add(superConstructorBindingKey1);
                    MethodDeclaration constructor=copyConstructor(methodDeclaration1,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                    bodyDeclarationsRewrite.insertLast(constructor,null);
                    constructorsToBeCopiedInSubclasses.get(1).add(methodDeclaration1);
                  }
                }
              }
            }
            for (            MethodDeclaration methodDeclaration2 : sourceTypeDeclarations.get(1).getMethods()) {
              if (methodDeclaration2.isConstructor()) {
                boolean matchingSuperConstructorCallFound=false;
                SuperConstructorInvocation superConstructorInvocation2=firstStatementIsSuperConstructorInvocation(methodDeclaration2);
                String superConstructorBindingKey2=superConstructorInvocation2 != null ? superConstructorInvocation2.resolveConstructorBinding().getKey() : null;
                for (                MethodDeclaration methodDeclaration1 : sourceTypeDeclarations.get(0).getMethods()) {
                  if (methodDeclaration1.isConstructor()) {
                    SuperConstructorInvocation superConstructorInvocation1=firstStatementIsSuperConstructorInvocation(methodDeclaration1);
                    if (superConstructorInvocation1 != null && superConstructorInvocation2 != null) {
                      List<Expression> superConstructorArguments1=superConstructorInvocation1.arguments();
                      List<Expression> superConstructorArguments2=superConstructorInvocation2.arguments();
                      if (matchingArgumentTypes(superConstructorArguments1,superConstructorArguments2) || superConstructorInvocation1.resolveConstructorBinding().isEqualTo(superConstructorInvocation2.resolveConstructorBinding())) {
                        matchingSuperConstructorCallFound=true;
                      }
                    }
                  }
                }
                if (!matchingSuperConstructorCallFound && superConstructorInvocation2 != null) {
                  if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey2)) {
                    processedSuperConstructorBindingKeys.add(superConstructorBindingKey2);
                    MethodDeclaration constructor=copyConstructor(methodDeclaration2,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                    bodyDeclarationsRewrite.insertLast(constructor,null);
                    constructorsToBeCopiedInSubclasses.get(0).add(methodDeclaration2);
                  }
                }
              }
            }
            if ((noneOfTheConstructorsContainsSuperConstructorCall(sourceTypeDeclarations.get(0)) && !containsConstructorCallingSuperConstructorWithoutArguments(sourceTypeDeclarations.get(1))) || (noneOfTheConstructorsContainsSuperConstructorCall(sourceTypeDeclarations.get(1)) && !containsConstructorCallingSuperConstructorWithoutArguments(sourceTypeDeclarations.get(0)))) {
              boolean commonSuperTypeDeclaresConstructorWithoutParameters=false;
              for (              IMethodBinding methodBinding : commonSuperTypeOfSourceTypeDeclarations.getDeclaredMethods()) {
                if (methodBinding.isConstructor() && methodBinding.getParameterTypes().length == 0) {
                  commonSuperTypeDeclaresConstructorWithoutParameters=true;
                  break;
                }
              }
              if (commonSuperTypeDeclaresConstructorWithoutParameters) {
                MethodDeclaration constructor=createDefaultConstructor(intermediateAST,intermediateRewriter,intermediateName);
                bodyDeclarationsRewrite.insertLast(constructor,null);
              }
            }
            RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
          }
          intermediateTypesRewrite.insertLast(intermediateTypeDeclaration,null);
        }
        cloneInfo.sourceCompilationUnit=intermediateCompilationUnit;
        cloneInfo.sourceICompilationUnit=intermediateICompilationUnit;
        cloneInfo.sourceTypeDeclaration=intermediateTypeDeclaration;
        cloneInfo.sourceRewriter=intermediateRewriter;
        cloneInfo.ast=intermediateAST;
      }
    }
  }
  ASTRewrite sourceRewriter=cloneInfo.sourceRewriter;
  AST ast=cloneInfo.ast;
  TypeDeclaration sourceTypeDeclaration=cloneInfo.sourceTypeDeclaration;
  MethodDeclaration sourceMethodDeclaration=sourceMethodDeclarations.get(0);
  ListRewrite bodyDeclarationsRewrite=sourceRewriter.getListRewrite(sourceTypeDeclaration,TypeDeclaration.BODY_DECLARATIONS_PROPERTY);
  if (commonSuperTypeOfSourceTypeDeclarations != null) {
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
  }
  Set<VariableDeclaration> accessedLocalFieldsG1=getLocallyAccessedFields(mapper.getDirectlyAccessedLocalFieldsG1(),sourceTypeDeclarations.get(0));
  Set<VariableDeclaration> accessedLocalFieldsG2=getLocallyAccessedFields(mapper.getDirectlyAccessedLocalFieldsG2(),sourceTypeDeclarations.get(1));
  Set<VariableDeclaration> modifiedLocalFieldsG1=getLocallyAccessedFields(mapper.getDirectlyModifiedLocalFieldsG1(),sourceTypeDeclarations.get(0));
  Set<VariableDeclaration> modifiedLocalFieldsG2=getLocallyAccessedFields(mapper.getDirectlyModifiedLocalFieldsG2(),sourceTypeDeclarations.get(1));
  if (!sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclarations.get(1).resolveBinding()) || !sourceTypeDeclarations.get(0).resolveBinding().getQualifiedName().equals(sourceTypeDeclarations.get(1).resolveBinding().getQualifiedName())) {
    pullUpLocallyAccessedFields(accessedLocalFieldsG1,accessedLocalFieldsG2,modifiedLocalFieldsG1,modifiedLocalFieldsG2,bodyDeclarationsRewrite,requiredImportTypeBindings);
    Set<VariableDeclaration> indirectlyAccessedLocalFieldsG1=getLocallyAccessedFields(mapper.getIndirectlyAccessedLocalFieldsG1(),sourceTypeDeclarations.get(0));
    Set<VariableDeclaration> indirectlyAccessedLocalFieldsG2=getLocallyAccessedFields(mapper.getIndirectlyAccessedLocalFieldsG2(),sourceTypeDeclarations.get(1));
    Set<VariableDeclaration> indirectlyModifiedLocalFieldsG1=getLocallyAccessedFields(mapper.getIndirectlyModifiedLocalFieldsG1(),sourceTypeDeclarations.get(0));
    Set<VariableDeclaration> indirectlyModifiedLocalFieldsG2=getLocallyAccessedFields(mapper.getIndirectlyModifiedLocalFieldsG2(),sourceTypeDeclarations.get(1));
    Set<MethodObject> accessedLocalMethodsG1=mapper.getAccessedLocalMethodsG1();
    Set<MethodObject> accessedLocalMethodsG2=mapper.getAccessedLocalMethodsG2();
    for (    MethodObject localMethodG1 : accessedLocalMethodsG1) {
      MethodDeclaration methodDeclaration1=localMethodG1.getMethodDeclaration();
      for (      MethodObject localMethodG2 : accessedLocalMethodsG2) {
        MethodDeclaration methodDeclaration2=localMethodG2.getMethodDeclaration();
        ITypeBinding returnTypesCommonSuperType=ASTNodeMatcher.commonSuperType(localMethodG1.getMethodDeclaration().getReturnType2().resolveBinding(),localMethodG2.getMethodDeclaration().getReturnType2().resolveBinding());
        if (localMethodG1.getName().equals(localMethodG2.getName()) && (localMethodG1.getReturnType().equals(localMethodG2.getReturnType()) || ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) && (localMethodG1.getParameterTypeList().equals(localMethodG2.getParameterTypeList()) || (MethodCallAnalyzer.equalSignatureIgnoringSubclassTypeDifferences(methodDeclaration1.resolveBinding(),methodDeclaration2.resolveBinding()) && mapper.getDirectlyAccessedLocalMethodsG1().contains(localMethodG1) && mapper.getDirectlyAccessedLocalMethodsG2().contains(localMethodG2)))) {
          Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
          boolean clones=type2Clones(methodDeclaration1,methodDeclaration2);
          Type returnType=methodDeclaration1.getReturnType2();
          TypeDeclaration typeDeclaration1=findTypeDeclaration(methodDeclaration1);
          TypeDeclaration typeDeclaration2=findTypeDeclaration(methodDeclaration2);
          Set<VariableDeclaration> fieldsAccessedInMethod1=getFieldsAccessedInMethod(indirectlyAccessedLocalFieldsG1,methodDeclaration1);
          Set<VariableDeclaration> fieldsAccessedInMethod2=getFieldsAccessedInMethod(indirectlyAccessedLocalFieldsG2,methodDeclaration2);
          Set<VariableDeclaration> fieldsModifiedInMethod1=getFieldsAccessedInMethod(indirectlyModifiedLocalFieldsG1,methodDeclaration1);
          Set<VariableDeclaration> fieldsModifiedInMethod2=getFieldsAccessedInMethod(indirectlyModifiedLocalFieldsG2,methodDeclaration2);
          if (!typeDeclaration1.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && !typeDeclaration2.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && !methodDeclaration1.resolveBinding().getDeclaringClass().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)&& !methodDeclaration2.resolveBinding().getDeclaringClass().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)&& !commonSuperTypeDeclaresMethodWithIdenticalSignature(methodDeclaration1)&& !commonSuperTypeDeclaresMethodWithIdenticalSignature(methodDeclaration2)&& !commonSuperTypeInheritsMethodWithIdenticalSignature(methodDeclaration1.resolveBinding(),cloneInfo.sourceTypeDeclaration.resolveBinding())&& !commonSuperTypeInheritsMethodWithIdenticalSignature(methodDeclaration2.resolveBinding(),cloneInfo.sourceTypeDeclaration.resolveBinding())) {
            boolean avoidPullUpDueToSerialization1=avoidPullUpMethodDueToSerialization(sourceTypeDeclarations.get(0),fieldsAccessedInMethod1);
            boolean avoidPullUpDueToSerialization2=avoidPullUpMethodDueToSerialization(sourceTypeDeclarations.get(1),fieldsAccessedInMethod2);
            if (clones && !avoidPullUpDueToSerialization1 && !avoidPullUpDueToSerialization2) {
              MethodDeclaration copiedMethodDeclaration=(MethodDeclaration)ASTNode.copySubtree(ast,methodDeclaration1);
              ListRewrite modifiersRewrite=sourceRewriter.getListRewrite(copiedMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
              List<IExtendedModifier> originalModifiers=copiedMethodDeclaration.modifiers();
              for (              IExtendedModifier extendedModifier : originalModifiers) {
                if (extendedModifier.isModifier()) {
                  Modifier modifier=(Modifier)extendedModifier;
                  if (modifier.isPrivate()) {
                    modifiersRewrite.replace(modifier,ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                  }
                }
              }
              if (!localMethodG1.getReturnType().equals(localMethodG2.getReturnType()) && ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) {
                Type newReturnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypesCommonSuperType,ast,sourceRewriter);
                sourceRewriter.set(copiedMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,newReturnType,null);
                typeBindings.add(returnTypesCommonSuperType);
              }
              if (!localMethodG1.isStatic() && localMethodG2.isStatic()) {
                modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.STATIC_KEYWORD),null);
              }
              bodyDeclarationsRewrite.insertLast(copiedMethodDeclaration,null);
              TypeVisitor typeVisitor=new TypeVisitor();
              methodDeclaration1.accept(typeVisitor);
              typeBindings.addAll(typeVisitor.getTypeBindings());
              fieldsAccessedInMethod1.removeAll(accessedLocalFieldsG1);
              fieldsAccessedInMethod2.removeAll(accessedLocalFieldsG2);
              pullUpLocallyAccessedFields(fieldsAccessedInMethod1,fieldsAccessedInMethod2,fieldsModifiedInMethod1,fieldsModifiedInMethod2,bodyDeclarationsRewrite,requiredImportTypeBindings);
              if (!typeDeclaration1.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
                methodDeclarationsToBePulledUp.get(0).add(methodDeclaration1);
              }
              if (!typeDeclaration2.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
                methodDeclarationsToBePulledUp.get(1).add(methodDeclaration2);
              }
            }
 else {
              if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.EXTRACT_STATIC_METHOD_TO_NEW_UTILITY_CLASS)) {
                createDifferencesForStaticMethodCalls(methodDeclaration1.resolveBinding(),methodDeclaration2.resolveBinding());
              }
 else               if (!containsSuperMethodCall(typeDeclaration1,methodDeclaration1.resolveBinding()) && !containsSuperMethodCall(typeDeclaration2,methodDeclaration2.resolveBinding())) {
                MethodDeclaration newMethodDeclaration=ast.newMethodDeclaration();
                sourceRewriter.set(newMethodDeclaration,MethodDeclaration.NAME_PROPERTY,ast.newSimpleName(methodDeclaration1.getName().getIdentifier()),null);
                if (localMethodG1.getReturnType().equals(localMethodG2.getReturnType())) {
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,returnType,null);
                  typeBindings.add(returnType.resolveBinding());
                }
 else                 if (ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) {
                  Type newReturnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypesCommonSuperType,ast,sourceRewriter);
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,newReturnType,null);
                  typeBindings.add(returnTypesCommonSuperType);
                }
                ListRewrite modifiersRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
                List<IExtendedModifier> originalModifiers=methodDeclaration1.modifiers();
                for (                IExtendedModifier extendedModifier : originalModifiers) {
                  if (extendedModifier.isModifier()) {
                    Modifier modifier=(Modifier)extendedModifier;
                    if (modifier.isProtected()) {
                      modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      }
                    }
 else                     if (modifier.isPublic()) {
                      if ((methodDeclaration2.getModifiers() & Modifier.PUBLIC) != 0) {
                        modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD),null);
                      }
 else                       if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) != 0) {
                        modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      }
                      if ((methodDeclaration2.getModifiers() & Modifier.PUBLIC) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PUBLIC_KEYWORD);
                      }
                    }
 else                     if (modifier.isPrivate()) {
                      modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      updateAccessModifier(methodDeclaration1,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      }
                    }
                  }
                }
                if (cloneInfo.superclassNotDirectlyInheritedFromRefactoredSubclasses) {
                  Block methodBody=ast.newBlock();
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.BODY_PROPERTY,methodBody,null);
                  Expression returnedExpression=generateDefaultValue(sourceRewriter,ast,returnType.resolveBinding());
                  if (returnedExpression != null) {
                    ReturnStatement returnStatement=ast.newReturnStatement();
                    sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,returnedExpression,null);
                    ListRewrite statementsRewrite=sourceRewriter.getListRewrite(methodBody,Block.STATEMENTS_PROPERTY);
                    statementsRewrite.insertLast(returnStatement,null);
                  }
                }
 else {
                  modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
                }
                ListRewrite parametersRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.PARAMETERS_PROPERTY);
                List<SingleVariableDeclaration> parameters1=methodDeclaration1.parameters();
                List<SingleVariableDeclaration> parameters2=methodDeclaration2.parameters();
                int parameterIndex=0;
                for (                SingleVariableDeclaration parameter1 : parameters1) {
                  SingleVariableDeclaration parameter2=parameters2.get(parameterIndex);
                  ITypeBinding parameterTypeBinding1=parameter1.getType().resolveBinding();
                  ITypeBinding parameterTypeBinding2=parameter2.getType().resolveBinding();
                  if (parameterTypeBinding1.isEqualTo(parameterTypeBinding2) && parameterTypeBinding1.getQualifiedName().equals(parameterTypeBinding2.getQualifiedName())) {
                    parametersRewrite.insertLast(parameter1,null);
                    typeBindings.add(parameterTypeBinding1);
                  }
 else {
                    ITypeBinding parameterCommonSuperTypeBinding=ASTNodeMatcher.commonSuperType(parameterTypeBinding1,parameterTypeBinding2);
                    Type parameterType=RefactoringUtility.generateTypeFromTypeBinding(parameterCommonSuperTypeBinding,ast,sourceRewriter);
                    SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
                    sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,parameterType,null);
                    sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName(parameter1.getName().getIdentifier()),null);
                    parametersRewrite.insertLast(parameter,null);
                    typeBindings.add(parameterCommonSuperTypeBinding);
                  }
                  parameterIndex++;
                }
                ListRewrite thrownExceptionsRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.THROWN_EXCEPTIONS_PROPERTY);
                List<Name> thrownExceptions=methodDeclaration1.thrownExceptions();
                for (                Name thrownException : thrownExceptions) {
                  thrownExceptionsRewrite.insertLast(thrownException,null);
                  typeBindings.add(thrownException.resolveTypeBinding());
                }
                bodyDeclarationsRewrite.insertLast(newMethodDeclaration,null);
              }
            }
          }
          RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
          break;
        }
      }
    }
  }
  MethodDeclaration newMethodDeclaration=ast.newMethodDeclaration();
  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.NAME_PROPERTY,ast.newSimpleName(extractedMethodName),null);
  List<VariableDeclaration> returnedVariables1=this.returnedVariables.get(0);
  List<VariableDeclaration> returnedVariables2=this.returnedVariables.get(1);
  ITypeBinding returnTypeBinding=mapper.getReturnTypeBinding();
  if (returnTypeBinding != null) {
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(returnTypeBinding);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
    Type returnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypeBinding,ast,sourceRewriter);
    sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,returnType,null);
  }
 else {
    sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,ast.newPrimitiveType(PrimitiveType.VOID),null);
  }
  ListRewrite modifierRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
  if (sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && sourceTypeDeclarations.get(1).resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
 else   if (cloneInfo.extractUtilityClass) {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
 else {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
  if (((sourceMethodDeclarations.get(0).getModifiers() & Modifier.STATIC) != 0 && (sourceMethodDeclarations.get(1).getModifiers() & Modifier.STATIC) != 0) || cloneInfo.extractUtilityClass) {
    Modifier staticModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.STATIC_KEYWORD);
    modifierRewrite.insertLast(staticModifier,null);
  }
  ListRewrite parameterRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.PARAMETERS_PROPERTY);
  Map<VariableBindingKeyPair,ArrayList<VariableDeclaration>> commonPassedParameters=mapper.getCommonPassedParameters();
  for (  VariableBindingKeyPair parameterName : commonPassedParameters.keySet()) {
    ArrayList<VariableDeclaration> variableDeclarations=commonPassedParameters.get(parameterName);
    VariableDeclaration variableDeclaration1=variableDeclarations.get(0);
    VariableDeclaration variableDeclaration2=variableDeclarations.get(1);
    if (parameterIsUsedByNodesWithoutDifferences(variableDeclaration1,variableDeclaration2)) {
      if (!variableDeclaration1.resolveBinding().isField() && !variableDeclaration2.resolveBinding().isField()) {
        ITypeBinding typeBinding1=extractTypeBinding(variableDeclaration1);
        ITypeBinding typeBinding2=extractTypeBinding(variableDeclaration2);
        ITypeBinding typeBinding=null;
        if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
          ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
          if (commonSuperTypeBinding != null) {
            typeBinding=commonSuperTypeBinding;
          }
        }
 else {
          typeBinding=typeBinding1;
        }
        boolean makeQualifiedType=RefactoringUtility.hasQualifiedType(variableDeclaration1) && RefactoringUtility.hasQualifiedType(variableDeclaration2);
        Type variableType=makeQualifiedType ? RefactoringUtility.generateQualifiedTypeFromTypeBinding(typeBinding,ast,sourceRewriter) : RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
        Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
        typeBindings.add(typeBinding);
        RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
        SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
        sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,variableDeclaration1.getName(),null);
        sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,variableType,null);
        parameterRewrite.insertLast(parameter,null);
        originalPassedParameters.put(parameterName,variableDeclarations);
      }
    }
  }
  Block newMethodBody=newMethodDeclaration.getAST().newBlock();
  ListRewrite methodBodyRewrite=sourceRewriter.getListRewrite(newMethodBody,Block.STATEMENTS_PROPERTY);
  Set<ITypeBinding> thrownExceptionTypeBindings=new LinkedHashSet<ITypeBinding>();
  for (  PDGNodeMapping pdgNodeMapping : sortedNodeMappings) {
    PDGNode pdgNode1=pdgNodeMapping.getNodeG1();
    AbstractStatement statement1=pdgNode1.getStatement();
    PDGBlockNode blockNode1=mapper.getPDG1().isNestedWithinBlockNode(pdgNode1);
    if (blockNode1 != null && blockNode1 instanceof PDGTryNode && mapper.getRemovableNodesG1().contains(blockNode1)) {
    }
 else {
      ThrownExceptionVisitor thrownExceptionVisitor=new ThrownExceptionVisitor();
      statement1.getStatement().accept(thrownExceptionVisitor);
      for (      ITypeBinding thrownException : thrownExceptionVisitor.getTypeBindings()) {
        if (pdgNode1.getThrownExceptionTypes().contains(thrownException.getQualifiedName())) {
          addTypeBinding(thrownException,thrownExceptionTypeBindings);
        }
      }
    }
    RefactoringUtility.getSimpleTypeBindings(extractTypeBindings(statement1),requiredImportTypeBindings);
    PDGNode pdgNode2=pdgNodeMapping.getNodeG2();
    AbstractStatement statement2=pdgNode2.getStatement();
    PDGBlockNode blockNode2=mapper.getPDG2().isNestedWithinBlockNode(pdgNode2);
    if (blockNode2 != null && blockNode2 instanceof PDGTryNode && mapper.getRemovableNodesG2().contains(blockNode2)) {
    }
 else {
      ThrownExceptionVisitor thrownExceptionVisitor=new ThrownExceptionVisitor();
      statement2.getStatement().accept(thrownExceptionVisitor);
      for (      ITypeBinding thrownException : thrownExceptionVisitor.getTypeBindings()) {
        if (pdgNode2.getThrownExceptionTypes().contains(thrownException.getQualifiedName())) {
          addTypeBinding(thrownException,thrownExceptionTypeBindings);
        }
      }
    }
    RefactoringUtility.getSimpleTypeBindings(extractTypeBindings(statement2),requiredImportTypeBindings);
  }
  ListRewrite thrownExceptionRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.THROWN_EXCEPTIONS_PROPERTY);
  List<Name> thrownExceptions1=sourceMethodDeclarations.get(0).thrownExceptions();
  List<Name> thrownExceptions2=sourceMethodDeclarations.get(1).thrownExceptions();
  for (  Name thrownException1 : thrownExceptions1) {
    for (    Name thrownException2 : thrownExceptions2) {
      if (thrownException1.resolveTypeBinding().isEqualTo(thrownException2.resolveTypeBinding()) && thrownExceptionTypeBindings.contains(thrownException1.resolveTypeBinding())) {
        thrownExceptionRewrite.insertLast(thrownException1,null);
        Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
        typeBindings.add(thrownException1.resolveTypeBinding());
        RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
        thrownExceptionTypeBindings.remove(thrownException1.resolveTypeBinding());
        break;
      }
    }
  }
  for (  ITypeBinding thrownExceptionTypeBinding : thrownExceptionTypeBindings) {
    thrownExceptionRewrite.insertLast(ast.newSimpleName(thrownExceptionTypeBinding.getName()),null);
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(thrownExceptionTypeBinding);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
  }
  CloneStructureNode root=mapper.getCloneStructureRoot();
  for (  CloneStructureNode child : root.getChildren()) {
    if (processableNode(child)) {
      Statement statement=processCloneStructureNode(child,ast,sourceRewriter);
      if (processableMappedNode(child) && ((PDGNodeMapping)child.getMapping()).declaresInconsistentlyRenamedVariable(mapper.getRenamedVariableBindings()) && mapper.movableBeforeFirstMappedNode((PDGNodeMapping)child.getMapping())) {
        methodBodyRewrite.insertFirst(statement,null);
      }
 else {
        methodBodyRewrite.insertLast(statement,null);
      }
    }
  }
  if (returnedVariables1.size() == 1 && returnedVariables2.size() == 1 && !mappedNodesContainStatementReturningVariable(returnedVariables1.get(0),returnedVariables2.get(0))) {
    ReturnStatement returnStatement=ast.newReturnStatement();
    BindingSignaturePair variableBelongingToParameterizedDifferences=variableBelongsToParameterizedDifferences(returnedVariables1.get(0),returnedVariables2.get(0));
    if (variableBelongingToParameterizedDifferences != null) {
      int existingArgValue=findExistingParametersWithArgName();
      int i=0;
      if (existingArgValue > 0) {
        i=existingArgValue + 1;
      }
      for (      BindingSignaturePair pair : parameterizedDifferenceMap.keySet()) {
        if (pair.equals(variableBelongingToParameterizedDifferences)) {
          break;
        }
        i++;
      }
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,ast.newSimpleName("String_Node_Str" + i),null);
    }
 else {
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,returnedVariables1.get(0).getName(),null);
    }
    methodBodyRewrite.insertLast(returnStatement,null);
    if (!mappedNodesContainStatementDeclaringVariable(returnedVariables1.get(0),returnedVariables2.get(0)) && !mappedNodesContainDifferentStatementsDeclaringVariables(returnedVariables1.get(0),returnedVariables2.get(0)) && variableBelongingToParameterizedDifferences == null && !variableIsPassedAsCommonParameter(returnedVariables1.get(0),returnedVariables2.get(0))) {
      ITypeBinding returnedTypeBinding=extractTypeBinding(returnedVariables1.get(0));
      Expression initializer=generateDefaultValue(sourceRewriter,ast,returnedTypeBinding);
      VariableDeclarationFragment fragment=ast.newVariableDeclarationFragment();
      sourceRewriter.set(fragment,VariableDeclarationFragment.NAME_PROPERTY,returnedVariables1.get(0).getName(),null);
      sourceRewriter.set(fragment,VariableDeclarationFragment.INITIALIZER_PROPERTY,initializer,null);
      VariableDeclarationStatement declarationStatement=ast.newVariableDeclarationStatement(fragment);
      Type returnedType=RefactoringUtility.generateTypeFromTypeBinding(returnedTypeBinding,ast,sourceRewriter);
      sourceRewriter.set(declarationStatement,VariableDeclarationStatement.TYPE_PROPERTY,returnedType,null);
      methodBodyRewrite.insertFirst(declarationStatement,null);
    }
  }
 else {
    if (returnTypeBinding != null && !root.containsMappedReturnStatementInDirectChildren() && !root.lastIfElseIfChainContainsReturnOrThrowStatements()) {
      ReturnStatement returnStatement=ast.newReturnStatement();
      Expression expression=generateDefaultValue(sourceRewriter,ast,returnTypeBinding);
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,expression,null);
      methodBodyRewrite.insertLast(returnStatement,null);
    }
  }
  int existingArgValue=findExistingParametersWithArgName();
  int i=0;
  if (existingArgValue > 0) {
    i=existingArgValue + 1;
  }
  for (  ASTNodeDifference difference : parameterizedDifferenceMap.values()) {
    AbstractExpression expression1=difference.getExpression1();
    AbstractExpression expression2=difference.getExpression2();
    boolean isReturnedVariable=false;
    if (expression1 != null) {
      isReturnedVariable=isReturnedVariable(expression1.getExpression(),this.returnedVariables.get(0));
    }
 else     if (expression2 != null) {
      isReturnedVariable=isReturnedVariable(expression2.getExpression(),this.returnedVariables.get(1));
    }
    ITypeBinding typeBinding1=expression1 != null ? ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression1.getExpression()).resolveTypeBinding() : ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression2.getExpression()).resolveTypeBinding();
    ITypeBinding typeBinding2=expression2 != null ? ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression2.getExpression()).resolveTypeBinding() : ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression1.getExpression()).resolveTypeBinding();
    if (!isReturnedVariable || (returnedVariables1.size() == 1 && returnedVariables2.size() == 1 && variableBelongsToParameterizedDifferences(returnedVariables1.get(0),returnedVariables2.get(0)) != null)) {
      ITypeBinding typeBinding=null;
      if (difference.containsDifferenceType(DifferenceType.SUBCLASS_TYPE_MISMATCH) || difference.containsDifferenceType(DifferenceType.METHOD_INVOCATION_NAME_MISMATCH) || differenceContainsSubDifferenceWithSubclassTypeMismatch(difference)) {
        if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
          ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
          if (commonSuperTypeBinding != null) {
            typeBinding=commonSuperTypeBinding;
          }
        }
 else {
          typeBinding=typeBinding1;
        }
      }
 else {
        if (expression1 != null && !typeBinding1.getQualifiedName().equals("String_Node_Str")) {
          if (typeBinding1.getErasure().getQualifiedName().equals("String_Node_Str") && typeBinding2.getErasure().getQualifiedName().equals("String_Node_Str") && (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName()))) {
            typeBinding=typeBinding1.getErasure();
          }
 else {
            typeBinding=typeBinding1;
          }
        }
 else {
          typeBinding=typeBinding2;
        }
      }
      Type type=null;
      if (typeBinding.isPrimitive() && (typeBinding1.getQualifiedName().equals("String_Node_Str") || typeBinding2.getQualifiedName().equals("String_Node_Str"))) {
        type=RefactoringUtility.generateWrapperTypeForPrimitiveTypeBinding(typeBinding,ast);
      }
 else {
        type=RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
      }
      Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
      typeBindings.add(typeBinding);
      RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
      SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
      sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName("String_Node_Str" + i),null);
      i++;
      sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,type,null);
      parameterRewrite.insertLast(parameter,null);
    }
  }
  int j=0;
  List<VariableDeclaration> fieldDeclarationsToBeParameterizedG2=new ArrayList<VariableDeclaration>(fieldDeclarationsToBeParameterized.get(1));
  for (  VariableDeclaration variableDeclaration1 : fieldDeclarationsToBeParameterized.get(0)) {
    if (accessedLocalFieldsG1.contains(variableDeclaration1)) {
      VariableDeclaration variableDeclaration2=fieldDeclarationsToBeParameterizedG2.get(j);
      ITypeBinding typeBinding1=variableDeclaration1.resolveBinding().getType();
      ITypeBinding typeBinding2=variableDeclaration2.resolveBinding().getType();
      ITypeBinding typeBinding=null;
      if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
        ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
        if (commonSuperTypeBinding != null) {
          typeBinding=commonSuperTypeBinding;
        }
      }
 else {
        typeBinding=typeBinding1;
      }
      SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
      Type type=RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
      sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,type,null);
      String identifier=(variableDeclaration1.resolveBinding().getModifiers() & Modifier.STATIC) != 0 ? variableDeclaration1.getName().getIdentifier() : createNameForParameterizedFieldAccess(variableDeclaration1.getName().getIdentifier());
      sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName(identifier),null);
      parameterRewrite.insertLast(parameter,null);
    }
    j++;
  }
  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.BODY_PROPERTY,newMethodBody,null);
  bodyDeclarationsRewrite.insertLast(newMethodDeclaration,null);
  cloneInfo.requiredImportTypeBindings=requiredImportTypeBindings;
  cloneInfo.methodBodyRewrite=methodBodyRewrite;
  cloneInfo.parameterRewrite=parameterRewrite;
}

Fixed version (ground truth):
private void extractClone(){
  this.cloneInfo=new CloneInformation();
  Set<ITypeBinding> requiredImportTypeBindings=new LinkedHashSet<ITypeBinding>();
  ITypeBinding commonSuperTypeOfSourceTypeDeclarations=null;
  if (sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclarations.get(1).resolveBinding()) && sourceTypeDeclarations.get(0).resolveBinding().getQualifiedName().equals(sourceTypeDeclarations.get(1).resolveBinding().getQualifiedName())) {
    cloneInfo.sourceCompilationUnit=sourceCompilationUnits.get(0);
    cloneInfo.sourceICompilationUnit=(ICompilationUnit)cloneInfo.sourceCompilationUnit.getJavaElement();
    cloneInfo.sourceTypeDeclaration=sourceTypeDeclarations.get(0);
    cloneInfo.sourceRewriter=ASTRewrite.create(cloneInfo.sourceTypeDeclaration.getAST());
    cloneInfo.ast=cloneInfo.sourceTypeDeclaration.getAST();
  }
 else {
    ITypeBinding typeBinding1=sourceTypeDeclarations.get(0).resolveBinding();
    ITypeBinding typeBinding2=sourceTypeDeclarations.get(1).resolveBinding();
    commonSuperTypeOfSourceTypeDeclarations=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
    if (commonSuperTypeOfSourceTypeDeclarations != null) {
      if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.PULL_UP_TO_EXISTING_SUPERCLASS)) {
        IJavaElement javaElement=commonSuperTypeOfSourceTypeDeclarations.getJavaElement();
        javaElementsToOpenInEditor.add(javaElement);
        ICompilationUnit iCompilationUnit=(ICompilationUnit)javaElement.getParent();
        ASTParser parser=ASTParser.newParser(ASTReader.JLS);
        parser.setKind(ASTParser.K_COMPILATION_UNIT);
        parser.setSource(iCompilationUnit);
        parser.setResolveBindings(true);
        CompilationUnit compilationUnit=(CompilationUnit)parser.createAST(null);
        List<AbstractTypeDeclaration> typeDeclarations=compilationUnit.types();
        for (        AbstractTypeDeclaration abstractTypeDeclaration : typeDeclarations) {
          if (abstractTypeDeclaration instanceof TypeDeclaration) {
            TypeDeclaration typeDeclaration=(TypeDeclaration)abstractTypeDeclaration;
            if (typeDeclaration.resolveBinding().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)) {
              cloneInfo.sourceCompilationUnit=compilationUnit;
              cloneInfo.sourceICompilationUnit=iCompilationUnit;
              cloneInfo.sourceTypeDeclaration=typeDeclaration;
              cloneInfo.sourceRewriter=ASTRewrite.create(cloneInfo.sourceTypeDeclaration.getAST());
              cloneInfo.ast=cloneInfo.sourceTypeDeclaration.getAST();
              cloneInfo.superclassNotDirectlyInheritedFromRefactoredSubclasses=!superclassDirectlyInheritedFromRefactoredSubclasses(commonSuperTypeOfSourceTypeDeclarations,typeBinding1,typeBinding2);
              break;
            }
          }
        }
        MultiTextEdit multiTextEdit=new MultiTextEdit();
        CompilationUnitChange compilationUnitChange=new CompilationUnitChange("String_Node_Str",iCompilationUnit);
        compilationUnitChange.setEdit(multiTextEdit);
        compilationUnitChanges.put(iCompilationUnit,compilationUnitChange);
      }
 else {
        if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.EXTRACT_STATIC_METHOD_TO_NEW_UTILITY_CLASS)) {
          cloneInfo.extractUtilityClass=true;
        }
        if (cloneInfo.extractUtilityClass) {
          cloneInfo.intermediateClassName="String_Node_Str";
        }
 else {
          cloneInfo.intermediateClassName="String_Node_Str" + commonSuperTypeOfSourceTypeDeclarations.getName();
        }
        ClassObject commonSuperType=ASTReader.getSystemObject().getClassObject(commonSuperTypeOfSourceTypeDeclarations.getQualifiedName());
        CompilationUnit compilationUnit=null;
        if (commonSuperType != null) {
          compilationUnit=findCompilationUnit(commonSuperType.getAbstractTypeDeclaration());
        }
 else {
          compilationUnit=sourceCompilationUnits.get(0);
        }
        if (compilationUnit.getPackage() != null) {
          cloneInfo.intermediateClassPackageBinding=compilationUnit.getPackage().resolveBinding();
        }
        ICompilationUnit iCompilationUnit=(ICompilationUnit)compilationUnit.getJavaElement();
        IContainer container=(IContainer)iCompilationUnit.getResource().getParent();
        if (container instanceof IProject) {
          IProject contextProject=(IProject)container;
          cloneInfo.file=contextProject.getFile(cloneInfo.intermediateClassName + "String_Node_Str");
        }
 else         if (container instanceof IFolder) {
          IFolder contextFolder=(IFolder)container;
          cloneInfo.file=contextFolder.getFile(cloneInfo.intermediateClassName + "String_Node_Str");
        }
        boolean intermediateAlreadyExists=false;
        ICompilationUnit intermediateICompilationUnit=JavaCore.createCompilationUnitFrom(cloneInfo.file);
        javaElementsToOpenInEditor.add(intermediateICompilationUnit);
        ASTParser intermediateParser=ASTParser.newParser(ASTReader.JLS);
        intermediateParser.setKind(ASTParser.K_COMPILATION_UNIT);
        if (cloneInfo.file.exists()) {
          intermediateAlreadyExists=true;
          intermediateParser.setSource(intermediateICompilationUnit);
          intermediateParser.setResolveBindings(true);
        }
 else {
          cloneInfo.document=new Document();
          intermediateParser.setSource(cloneInfo.document.get().toCharArray());
        }
        CompilationUnit intermediateCompilationUnit=(CompilationUnit)intermediateParser.createAST(null);
        AST intermediateAST=intermediateCompilationUnit.getAST();
        ASTRewrite intermediateRewriter=ASTRewrite.create(intermediateAST);
        ListRewrite intermediateTypesRewrite=intermediateRewriter.getListRewrite(intermediateCompilationUnit,CompilationUnit.TYPES_PROPERTY);
        TypeDeclaration intermediateTypeDeclaration=null;
        if (intermediateAlreadyExists) {
          List<AbstractTypeDeclaration> abstractTypeDeclarations=intermediateCompilationUnit.types();
          for (          AbstractTypeDeclaration abstractTypeDeclaration : abstractTypeDeclarations) {
            if (abstractTypeDeclaration instanceof TypeDeclaration) {
              TypeDeclaration typeDeclaration=(TypeDeclaration)abstractTypeDeclaration;
              if (typeDeclaration.getName().getIdentifier().equals(cloneInfo.intermediateClassName)) {
                intermediateTypeDeclaration=typeDeclaration;
                int intermediateModifiers=intermediateTypeDeclaration.getModifiers();
                if ((intermediateModifiers & Modifier.ABSTRACT) == 0 && !cloneInfo.extractUtilityClass) {
                  ListRewrite intermediateModifiersRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.MODIFIERS2_PROPERTY);
                  intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
                }
                break;
              }
            }
          }
          MultiTextEdit intermediateMultiTextEdit=new MultiTextEdit();
          CompilationUnitChange intermediateCompilationUnitChange=new CompilationUnitChange("String_Node_Str",intermediateICompilationUnit);
          intermediateCompilationUnitChange.setEdit(intermediateMultiTextEdit);
          compilationUnitChanges.put(intermediateICompilationUnit,intermediateCompilationUnitChange);
        }
 else {
          if (compilationUnit.getPackage() != null) {
            intermediateRewriter.set(intermediateCompilationUnit,CompilationUnit.PACKAGE_PROPERTY,compilationUnit.getPackage(),null);
          }
          intermediateTypeDeclaration=intermediateAST.newTypeDeclaration();
          SimpleName intermediateName=intermediateAST.newSimpleName(cloneInfo.intermediateClassName);
          intermediateRewriter.set(intermediateTypeDeclaration,TypeDeclaration.NAME_PROPERTY,intermediateName,null);
          ListRewrite intermediateModifiersRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.MODIFIERS2_PROPERTY);
          intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD),null);
          if (!cloneInfo.extractUtilityClass) {
            intermediateModifiersRewrite.insertLast(intermediateAST.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
            Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
            if (commonSuperTypeOfSourceTypeDeclarations.isClass()) {
              intermediateRewriter.set(intermediateTypeDeclaration,TypeDeclaration.SUPERCLASS_TYPE_PROPERTY,intermediateAST.newSimpleType(intermediateAST.newSimpleName(commonSuperTypeOfSourceTypeDeclarations.getName())),null);
              typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
            }
            ListRewrite interfaceRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.SUPER_INTERFACE_TYPES_PROPERTY);
            if (commonSuperTypeOfSourceTypeDeclarations.isInterface()) {
              ITypeBinding[] superInterfaces=commonSuperTypeOfSourceTypeDeclarations.getInterfaces();
              int taggingSuperInterfaceCount=0;
              for (              ITypeBinding superInterface : superInterfaces) {
                if (ASTNodeMatcher.isTaggingInterface(superInterface)) {
                  taggingSuperInterfaceCount++;
                }
              }
              boolean allSuperInterfacesAreTaggingInterfaces=superInterfaces.length > 0 && taggingSuperInterfaceCount == superInterfaces.length;
              boolean bothSubClassesImplementCommonSuperType=ASTNodeMatcher.implementsInterface(typeBinding1,commonSuperTypeOfSourceTypeDeclarations) && ASTNodeMatcher.implementsInterface(typeBinding2,commonSuperTypeOfSourceTypeDeclarations);
              if (!allSuperInterfacesAreTaggingInterfaces && !bothSubClassesImplementCommonSuperType) {
                Type interfaceType=RefactoringUtility.generateTypeFromTypeBinding(commonSuperTypeOfSourceTypeDeclarations,intermediateAST,intermediateRewriter);
                interfaceRewrite.insertLast(interfaceType,null);
                typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
              }
            }
            List<Type> superInterfaceTypes1=sourceTypeDeclarations.get(0).superInterfaceTypes();
            List<Type> superInterfaceTypes2=sourceTypeDeclarations.get(1).superInterfaceTypes();
            for (            Type interfaceType1 : superInterfaceTypes1) {
              ITypeBinding interfaceTypeBinding1=interfaceType1.resolveBinding();
              for (              Type interfaceType2 : superInterfaceTypes2) {
                ITypeBinding interfaceTypeBinding2=interfaceType2.resolveBinding();
                if (interfaceTypeBinding1.isEqualTo(interfaceTypeBinding2) && interfaceTypeBinding1.getQualifiedName().equals(interfaceTypeBinding2.getQualifiedName()) && checkIfThisReferenceIsPassedAsArgumentToMethodInvocation(interfaceTypeBinding1)) {
                  interfaceRewrite.insertLast(interfaceType1,null);
                  typeBindings.add(interfaceTypeBinding1);
                  break;
                }
              }
            }
            ListRewrite bodyDeclarationsRewrite=intermediateRewriter.getListRewrite(intermediateTypeDeclaration,TypeDeclaration.BODY_DECLARATIONS_PROPERTY);
            Set<String> processedSuperConstructorBindingKeys=new LinkedHashSet<String>();
            for (            MethodDeclaration methodDeclaration1 : sourceTypeDeclarations.get(0).getMethods()) {
              if (methodDeclaration1.isConstructor()) {
                boolean matchingSuperConstructorCallFound=false;
                SuperConstructorInvocation superConstructorInvocation1=firstStatementIsSuperConstructorInvocation(methodDeclaration1);
                String superConstructorBindingKey1=superConstructorInvocation1 != null ? superConstructorInvocation1.resolveConstructorBinding().getKey() : null;
                for (                MethodDeclaration methodDeclaration2 : sourceTypeDeclarations.get(1).getMethods()) {
                  if (methodDeclaration2.isConstructor()) {
                    SuperConstructorInvocation superConstructorInvocation2=firstStatementIsSuperConstructorInvocation(methodDeclaration2);
                    if (superConstructorInvocation1 != null && superConstructorInvocation2 != null) {
                      List<Expression> superConstructorArguments1=superConstructorInvocation1.arguments();
                      List<Expression> superConstructorArguments2=superConstructorInvocation2.arguments();
                      if (matchingArgumentTypes(superConstructorArguments1,superConstructorArguments2) || superConstructorInvocation1.resolveConstructorBinding().isEqualTo(superConstructorInvocation2.resolveConstructorBinding())) {
                        matchingSuperConstructorCallFound=true;
                        if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey1)) {
                          processedSuperConstructorBindingKeys.add(superConstructorBindingKey1);
                          if (compareStatements(sourceCompilationUnits.get(0).getTypeRoot(),sourceCompilationUnits.get(1).getTypeRoot(),superConstructorInvocation1,superConstructorInvocation2)) {
                            MethodDeclaration constructor=copyConstructor(methodDeclaration1,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                            bodyDeclarationsRewrite.insertLast(constructor,null);
                          }
 else {
                            MethodDeclaration constructor=intermediateAST.newMethodDeclaration();
                            intermediateRewriter.set(constructor,MethodDeclaration.NAME_PROPERTY,intermediateName,null);
                            intermediateRewriter.set(constructor,MethodDeclaration.CONSTRUCTOR_PROPERTY,true,null);
                            ListRewrite constructorModifierRewriter=intermediateRewriter.getListRewrite(constructor,MethodDeclaration.MODIFIERS2_PROPERTY);
                            List<IExtendedModifier> modifiers=methodDeclaration1.modifiers();
                            for (                            IExtendedModifier modifier : modifiers) {
                              if (modifier instanceof Modifier) {
                                constructorModifierRewriter.insertLast((Modifier)modifier,null);
                              }
                            }
                            ListRewrite parameterRewriter=intermediateRewriter.getListRewrite(constructor,MethodDeclaration.PARAMETERS_PROPERTY);
                            SuperConstructorInvocation superConstructorInvocation=intermediateAST.newSuperConstructorInvocation();
                            ListRewrite argumentRewriter=intermediateRewriter.getListRewrite(superConstructorInvocation,SuperConstructorInvocation.ARGUMENTS_PROPERTY);
                            Map<String,Integer> parameterTypeCounterMap=new LinkedHashMap<String,Integer>();
                            for (                            ITypeBinding argumentTypeBinding : superConstructorInvocation1.resolveConstructorBinding().getParameterTypes()) {
                              SingleVariableDeclaration parameter=intermediateAST.newSingleVariableDeclaration();
                              typeBindings.add(argumentTypeBinding);
                              Type parameterType=RefactoringUtility.generateTypeFromTypeBinding(argumentTypeBinding,intermediateAST,intermediateRewriter);
                              intermediateRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,parameterType,null);
                              String typeName=argumentTypeBinding.getName();
                              String parameterName=typeName.replaceFirst(Character.toString(typeName.charAt(0)),Character.toString(Character.toLowerCase(typeName.charAt(0))));
                              if (parameterTypeCounterMap.containsKey(argumentTypeBinding.getKey())) {
                                int previousCounter=parameterTypeCounterMap.get(argumentTypeBinding.getKey());
                                parameterName+=previousCounter;
                                int currentCounter=previousCounter + 1;
                                parameterTypeCounterMap.put(argumentTypeBinding.getKey(),currentCounter);
                              }
 else {
                                parameterTypeCounterMap.put(argumentTypeBinding.getKey(),1);
                              }
                              SimpleName parameterSimpleName=intermediateAST.newSimpleName(parameterName);
                              intermediateRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,parameterSimpleName,null);
                              parameterRewriter.insertLast(parameter,null);
                              argumentRewriter.insertLast(parameterSimpleName,null);
                            }
                            Block constructorBody=intermediateAST.newBlock();
                            ListRewrite constructorBodyRewriter=intermediateRewriter.getListRewrite(constructorBody,Block.STATEMENTS_PROPERTY);
                            constructorBodyRewriter.insertLast(superConstructorInvocation,null);
                            intermediateRewriter.set(constructor,MethodDeclaration.BODY_PROPERTY,constructorBody,null);
                            bodyDeclarationsRewrite.insertLast(constructor,null);
                          }
                        }
                      }
                    }
                  }
                }
                if (!matchingSuperConstructorCallFound && superConstructorInvocation1 != null) {
                  if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey1)) {
                    processedSuperConstructorBindingKeys.add(superConstructorBindingKey1);
                    MethodDeclaration constructor=copyConstructor(methodDeclaration1,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                    bodyDeclarationsRewrite.insertLast(constructor,null);
                    constructorsToBeCopiedInSubclasses.get(1).add(methodDeclaration1);
                  }
                }
              }
            }
            for (            MethodDeclaration methodDeclaration2 : sourceTypeDeclarations.get(1).getMethods()) {
              if (methodDeclaration2.isConstructor()) {
                boolean matchingSuperConstructorCallFound=false;
                SuperConstructorInvocation superConstructorInvocation2=firstStatementIsSuperConstructorInvocation(methodDeclaration2);
                String superConstructorBindingKey2=superConstructorInvocation2 != null ? superConstructorInvocation2.resolveConstructorBinding().getKey() : null;
                for (                MethodDeclaration methodDeclaration1 : sourceTypeDeclarations.get(0).getMethods()) {
                  if (methodDeclaration1.isConstructor()) {
                    SuperConstructorInvocation superConstructorInvocation1=firstStatementIsSuperConstructorInvocation(methodDeclaration1);
                    if (superConstructorInvocation1 != null && superConstructorInvocation2 != null) {
                      List<Expression> superConstructorArguments1=superConstructorInvocation1.arguments();
                      List<Expression> superConstructorArguments2=superConstructorInvocation2.arguments();
                      if (matchingArgumentTypes(superConstructorArguments1,superConstructorArguments2) || superConstructorInvocation1.resolveConstructorBinding().isEqualTo(superConstructorInvocation2.resolveConstructorBinding())) {
                        matchingSuperConstructorCallFound=true;
                      }
                    }
                  }
                }
                if (!matchingSuperConstructorCallFound && superConstructorInvocation2 != null) {
                  if (!processedSuperConstructorBindingKeys.contains(superConstructorBindingKey2)) {
                    processedSuperConstructorBindingKeys.add(superConstructorBindingKey2);
                    MethodDeclaration constructor=copyConstructor(methodDeclaration2,intermediateAST,intermediateRewriter,intermediateName,requiredImportTypeBindings);
                    bodyDeclarationsRewrite.insertLast(constructor,null);
                    constructorsToBeCopiedInSubclasses.get(0).add(methodDeclaration2);
                  }
                }
              }
            }
            if ((noneOfTheConstructorsContainsSuperConstructorCall(sourceTypeDeclarations.get(0)) && !containsConstructorCallingSuperConstructorWithoutArguments(sourceTypeDeclarations.get(1))) || (noneOfTheConstructorsContainsSuperConstructorCall(sourceTypeDeclarations.get(1)) && !containsConstructorCallingSuperConstructorWithoutArguments(sourceTypeDeclarations.get(0)))) {
              boolean commonSuperTypeDeclaresConstructorWithoutParameters=false;
              for (              IMethodBinding methodBinding : commonSuperTypeOfSourceTypeDeclarations.getDeclaredMethods()) {
                if (methodBinding.isConstructor() && methodBinding.getParameterTypes().length == 0) {
                  commonSuperTypeDeclaresConstructorWithoutParameters=true;
                  break;
                }
              }
              if (commonSuperTypeDeclaresConstructorWithoutParameters) {
                MethodDeclaration constructor=createDefaultConstructor(intermediateAST,intermediateRewriter,intermediateName);
                bodyDeclarationsRewrite.insertLast(constructor,null);
              }
            }
            RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
          }
          intermediateTypesRewrite.insertLast(intermediateTypeDeclaration,null);
        }
        cloneInfo.sourceCompilationUnit=intermediateCompilationUnit;
        cloneInfo.sourceICompilationUnit=intermediateICompilationUnit;
        cloneInfo.sourceTypeDeclaration=intermediateTypeDeclaration;
        cloneInfo.sourceRewriter=intermediateRewriter;
        cloneInfo.ast=intermediateAST;
      }
    }
  }
  ASTRewrite sourceRewriter=cloneInfo.sourceRewriter;
  AST ast=cloneInfo.ast;
  TypeDeclaration sourceTypeDeclaration=cloneInfo.sourceTypeDeclaration;
  MethodDeclaration sourceMethodDeclaration=sourceMethodDeclarations.get(0);
  ListRewrite bodyDeclarationsRewrite=sourceRewriter.getListRewrite(sourceTypeDeclaration,TypeDeclaration.BODY_DECLARATIONS_PROPERTY);
  if (commonSuperTypeOfSourceTypeDeclarations != null) {
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(commonSuperTypeOfSourceTypeDeclarations);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
  }
  Set<VariableDeclaration> accessedLocalFieldsG1=getLocallyAccessedFields(mapper.getDirectlyAccessedLocalFieldsG1(),sourceTypeDeclarations.get(0));
  Set<VariableDeclaration> accessedLocalFieldsG2=getLocallyAccessedFields(mapper.getDirectlyAccessedLocalFieldsG2(),sourceTypeDeclarations.get(1));
  Set<VariableDeclaration> modifiedLocalFieldsG1=getLocallyAccessedFields(mapper.getDirectlyModifiedLocalFieldsG1(),sourceTypeDeclarations.get(0));
  Set<VariableDeclaration> modifiedLocalFieldsG2=getLocallyAccessedFields(mapper.getDirectlyModifiedLocalFieldsG2(),sourceTypeDeclarations.get(1));
  if (!sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclarations.get(1).resolveBinding()) || !sourceTypeDeclarations.get(0).resolveBinding().getQualifiedName().equals(sourceTypeDeclarations.get(1).resolveBinding().getQualifiedName())) {
    pullUpLocallyAccessedFields(accessedLocalFieldsG1,accessedLocalFieldsG2,modifiedLocalFieldsG1,modifiedLocalFieldsG2,bodyDeclarationsRewrite,requiredImportTypeBindings);
    Set<VariableDeclaration> indirectlyAccessedLocalFieldsG1=getLocallyAccessedFields(mapper.getIndirectlyAccessedLocalFieldsG1(),sourceTypeDeclarations.get(0));
    Set<VariableDeclaration> indirectlyAccessedLocalFieldsG2=getLocallyAccessedFields(mapper.getIndirectlyAccessedLocalFieldsG2(),sourceTypeDeclarations.get(1));
    Set<VariableDeclaration> indirectlyModifiedLocalFieldsG1=getLocallyAccessedFields(mapper.getIndirectlyModifiedLocalFieldsG1(),sourceTypeDeclarations.get(0));
    Set<VariableDeclaration> indirectlyModifiedLocalFieldsG2=getLocallyAccessedFields(mapper.getIndirectlyModifiedLocalFieldsG2(),sourceTypeDeclarations.get(1));
    Set<MethodObject> accessedLocalMethodsG1=mapper.getAccessedLocalMethodsG1();
    Set<MethodObject> accessedLocalMethodsG2=mapper.getAccessedLocalMethodsG2();
    for (    MethodObject localMethodG1 : accessedLocalMethodsG1) {
      MethodDeclaration methodDeclaration1=localMethodG1.getMethodDeclaration();
      for (      MethodObject localMethodG2 : accessedLocalMethodsG2) {
        MethodDeclaration methodDeclaration2=localMethodG2.getMethodDeclaration();
        ITypeBinding returnTypesCommonSuperType=ASTNodeMatcher.commonSuperType(localMethodG1.getMethodDeclaration().getReturnType2().resolveBinding(),localMethodG2.getMethodDeclaration().getReturnType2().resolveBinding());
        if (localMethodG1.getName().equals(localMethodG2.getName()) && (localMethodG1.getReturnType().equals(localMethodG2.getReturnType()) || ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) && (localMethodG1.getParameterTypeList().equals(localMethodG2.getParameterTypeList()) || (MethodCallAnalyzer.equalSignatureIgnoringSubclassTypeDifferences(methodDeclaration1.resolveBinding(),methodDeclaration2.resolveBinding()) && mapper.getDirectlyAccessedLocalMethodsG1().contains(localMethodG1) && mapper.getDirectlyAccessedLocalMethodsG2().contains(localMethodG2)))) {
          Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
          boolean clones=type2Clones(methodDeclaration1,methodDeclaration2);
          Type returnType=methodDeclaration1.getReturnType2();
          TypeDeclaration typeDeclaration1=findTypeDeclaration(methodDeclaration1);
          TypeDeclaration typeDeclaration2=findTypeDeclaration(methodDeclaration2);
          Set<VariableDeclaration> fieldsAccessedInMethod1=getFieldsAccessedInMethod(indirectlyAccessedLocalFieldsG1,methodDeclaration1);
          Set<VariableDeclaration> fieldsAccessedInMethod2=getFieldsAccessedInMethod(indirectlyAccessedLocalFieldsG2,methodDeclaration2);
          Set<VariableDeclaration> fieldsModifiedInMethod1=getFieldsAccessedInMethod(indirectlyModifiedLocalFieldsG1,methodDeclaration1);
          Set<VariableDeclaration> fieldsModifiedInMethod2=getFieldsAccessedInMethod(indirectlyModifiedLocalFieldsG2,methodDeclaration2);
          if (!typeDeclaration1.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && !typeDeclaration2.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && !methodDeclaration1.resolveBinding().getDeclaringClass().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)&& !methodDeclaration2.resolveBinding().getDeclaringClass().isEqualTo(commonSuperTypeOfSourceTypeDeclarations)&& !commonSuperTypeDeclaresOrInheritsMethodWithIdenticalSignature(methodDeclaration1.resolveBinding(),commonSuperTypeOfSourceTypeDeclarations)&& !commonSuperTypeDeclaresOrInheritsMethodWithIdenticalSignature(methodDeclaration2.resolveBinding(),commonSuperTypeOfSourceTypeDeclarations)) {
            boolean avoidPullUpDueToSerialization1=avoidPullUpMethodDueToSerialization(sourceTypeDeclarations.get(0),fieldsAccessedInMethod1);
            boolean avoidPullUpDueToSerialization2=avoidPullUpMethodDueToSerialization(sourceTypeDeclarations.get(1),fieldsAccessedInMethod2);
            if (clones && !avoidPullUpDueToSerialization1 && !avoidPullUpDueToSerialization2) {
              MethodDeclaration copiedMethodDeclaration=(MethodDeclaration)ASTNode.copySubtree(ast,methodDeclaration1);
              ListRewrite modifiersRewrite=sourceRewriter.getListRewrite(copiedMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
              List<IExtendedModifier> originalModifiers=copiedMethodDeclaration.modifiers();
              for (              IExtendedModifier extendedModifier : originalModifiers) {
                if (extendedModifier.isModifier()) {
                  Modifier modifier=(Modifier)extendedModifier;
                  if (modifier.isPrivate()) {
                    modifiersRewrite.replace(modifier,ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                  }
                }
              }
              if (!localMethodG1.getReturnType().equals(localMethodG2.getReturnType()) && ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) {
                Type newReturnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypesCommonSuperType,ast,sourceRewriter);
                sourceRewriter.set(copiedMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,newReturnType,null);
                typeBindings.add(returnTypesCommonSuperType);
              }
              if (!localMethodG1.isStatic() && localMethodG2.isStatic()) {
                modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.STATIC_KEYWORD),null);
              }
              bodyDeclarationsRewrite.insertLast(copiedMethodDeclaration,null);
              TypeVisitor typeVisitor=new TypeVisitor();
              methodDeclaration1.accept(typeVisitor);
              typeBindings.addAll(typeVisitor.getTypeBindings());
              fieldsAccessedInMethod1.removeAll(accessedLocalFieldsG1);
              fieldsAccessedInMethod2.removeAll(accessedLocalFieldsG2);
              pullUpLocallyAccessedFields(fieldsAccessedInMethod1,fieldsAccessedInMethod2,fieldsModifiedInMethod1,fieldsModifiedInMethod2,bodyDeclarationsRewrite,requiredImportTypeBindings);
              if (!typeDeclaration1.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
                methodDeclarationsToBePulledUp.get(0).add(methodDeclaration1);
              }
              if (!typeDeclaration2.resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
                methodDeclarationsToBePulledUp.get(1).add(methodDeclaration2);
              }
            }
 else {
              if (mapper.getCloneRefactoringType().equals(CloneRefactoringType.EXTRACT_STATIC_METHOD_TO_NEW_UTILITY_CLASS)) {
                createDifferencesForStaticMethodCalls(methodDeclaration1.resolveBinding(),methodDeclaration2.resolveBinding());
              }
 else               if (!containsSuperMethodCall(typeDeclaration1,methodDeclaration1.resolveBinding()) && !containsSuperMethodCall(typeDeclaration2,methodDeclaration2.resolveBinding())) {
                MethodDeclaration newMethodDeclaration=ast.newMethodDeclaration();
                sourceRewriter.set(newMethodDeclaration,MethodDeclaration.NAME_PROPERTY,ast.newSimpleName(methodDeclaration1.getName().getIdentifier()),null);
                if (localMethodG1.getReturnType().equals(localMethodG2.getReturnType())) {
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,returnType,null);
                  typeBindings.add(returnType.resolveBinding());
                }
 else                 if (ASTNodeMatcher.validCommonSuperType(returnTypesCommonSuperType)) {
                  Type newReturnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypesCommonSuperType,ast,sourceRewriter);
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,newReturnType,null);
                  typeBindings.add(returnTypesCommonSuperType);
                }
                ListRewrite modifiersRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
                List<IExtendedModifier> originalModifiers=methodDeclaration1.modifiers();
                for (                IExtendedModifier extendedModifier : originalModifiers) {
                  if (extendedModifier.isModifier()) {
                    Modifier modifier=(Modifier)extendedModifier;
                    if (modifier.isProtected()) {
                      modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      }
                    }
 else                     if (modifier.isPublic()) {
                      if ((methodDeclaration2.getModifiers() & Modifier.PUBLIC) != 0) {
                        modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD),null);
                      }
 else                       if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) != 0) {
                        modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      }
                      if ((methodDeclaration2.getModifiers() & Modifier.PUBLIC) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PUBLIC_KEYWORD);
                      }
                    }
 else                     if (modifier.isPrivate()) {
                      modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD),null);
                      updateAccessModifier(methodDeclaration1,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      if ((methodDeclaration2.getModifiers() & Modifier.PROTECTED) == 0) {
                        updateAccessModifier(methodDeclaration2,Modifier.ModifierKeyword.PROTECTED_KEYWORD);
                      }
                    }
                  }
                }
                if (cloneInfo.superclassNotDirectlyInheritedFromRefactoredSubclasses) {
                  Block methodBody=ast.newBlock();
                  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.BODY_PROPERTY,methodBody,null);
                  Expression returnedExpression=generateDefaultValue(sourceRewriter,ast,returnType.resolveBinding());
                  if (returnedExpression != null) {
                    ReturnStatement returnStatement=ast.newReturnStatement();
                    sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,returnedExpression,null);
                    ListRewrite statementsRewrite=sourceRewriter.getListRewrite(methodBody,Block.STATEMENTS_PROPERTY);
                    statementsRewrite.insertLast(returnStatement,null);
                  }
                }
 else {
                  modifiersRewrite.insertLast(ast.newModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD),null);
                }
                ListRewrite parametersRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.PARAMETERS_PROPERTY);
                List<SingleVariableDeclaration> parameters1=methodDeclaration1.parameters();
                List<SingleVariableDeclaration> parameters2=methodDeclaration2.parameters();
                int parameterIndex=0;
                for (                SingleVariableDeclaration parameter1 : parameters1) {
                  SingleVariableDeclaration parameter2=parameters2.get(parameterIndex);
                  ITypeBinding parameterTypeBinding1=parameter1.getType().resolveBinding();
                  ITypeBinding parameterTypeBinding2=parameter2.getType().resolveBinding();
                  if (parameterTypeBinding1.isEqualTo(parameterTypeBinding2) && parameterTypeBinding1.getQualifiedName().equals(parameterTypeBinding2.getQualifiedName())) {
                    parametersRewrite.insertLast(parameter1,null);
                    typeBindings.add(parameterTypeBinding1);
                  }
 else {
                    ITypeBinding parameterCommonSuperTypeBinding=ASTNodeMatcher.commonSuperType(parameterTypeBinding1,parameterTypeBinding2);
                    Type parameterType=RefactoringUtility.generateTypeFromTypeBinding(parameterCommonSuperTypeBinding,ast,sourceRewriter);
                    SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
                    sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,parameterType,null);
                    sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName(parameter1.getName().getIdentifier()),null);
                    parametersRewrite.insertLast(parameter,null);
                    typeBindings.add(parameterCommonSuperTypeBinding);
                  }
                  parameterIndex++;
                }
                ListRewrite thrownExceptionsRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.THROWN_EXCEPTIONS_PROPERTY);
                List<Name> thrownExceptions=methodDeclaration1.thrownExceptions();
                for (                Name thrownException : thrownExceptions) {
                  thrownExceptionsRewrite.insertLast(thrownException,null);
                  typeBindings.add(thrownException.resolveTypeBinding());
                }
                bodyDeclarationsRewrite.insertLast(newMethodDeclaration,null);
              }
            }
          }
          RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
          break;
        }
      }
    }
  }
  MethodDeclaration newMethodDeclaration=ast.newMethodDeclaration();
  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.NAME_PROPERTY,ast.newSimpleName(extractedMethodName),null);
  List<VariableDeclaration> returnedVariables1=this.returnedVariables.get(0);
  List<VariableDeclaration> returnedVariables2=this.returnedVariables.get(1);
  ITypeBinding returnTypeBinding=mapper.getReturnTypeBinding();
  if (returnTypeBinding != null) {
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(returnTypeBinding);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
    Type returnType=RefactoringUtility.generateTypeFromTypeBinding(returnTypeBinding,ast,sourceRewriter);
    sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,returnType,null);
  }
 else {
    sourceRewriter.set(newMethodDeclaration,MethodDeclaration.RETURN_TYPE2_PROPERTY,ast.newPrimitiveType(PrimitiveType.VOID),null);
  }
  ListRewrite modifierRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.MODIFIERS2_PROPERTY);
  if (sourceTypeDeclarations.get(0).resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding()) && sourceTypeDeclarations.get(1).resolveBinding().isEqualTo(sourceTypeDeclaration.resolveBinding())) {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
 else   if (cloneInfo.extractUtilityClass) {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
 else {
    Modifier accessModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD);
    modifierRewrite.insertLast(accessModifier,null);
  }
  if (((sourceMethodDeclarations.get(0).getModifiers() & Modifier.STATIC) != 0 && (sourceMethodDeclarations.get(1).getModifiers() & Modifier.STATIC) != 0) || cloneInfo.extractUtilityClass) {
    Modifier staticModifier=newMethodDeclaration.getAST().newModifier(Modifier.ModifierKeyword.STATIC_KEYWORD);
    modifierRewrite.insertLast(staticModifier,null);
  }
  ListRewrite parameterRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.PARAMETERS_PROPERTY);
  Map<VariableBindingKeyPair,ArrayList<VariableDeclaration>> commonPassedParameters=mapper.getCommonPassedParameters();
  for (  VariableBindingKeyPair parameterName : commonPassedParameters.keySet()) {
    ArrayList<VariableDeclaration> variableDeclarations=commonPassedParameters.get(parameterName);
    VariableDeclaration variableDeclaration1=variableDeclarations.get(0);
    VariableDeclaration variableDeclaration2=variableDeclarations.get(1);
    if (parameterIsUsedByNodesWithoutDifferences(variableDeclaration1,variableDeclaration2)) {
      if (!variableDeclaration1.resolveBinding().isField() && !variableDeclaration2.resolveBinding().isField()) {
        ITypeBinding typeBinding1=extractTypeBinding(variableDeclaration1);
        ITypeBinding typeBinding2=extractTypeBinding(variableDeclaration2);
        ITypeBinding typeBinding=null;
        if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
          ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
          if (commonSuperTypeBinding != null) {
            typeBinding=commonSuperTypeBinding;
          }
        }
 else {
          typeBinding=typeBinding1;
        }
        boolean makeQualifiedType=RefactoringUtility.hasQualifiedType(variableDeclaration1) && RefactoringUtility.hasQualifiedType(variableDeclaration2);
        Type variableType=makeQualifiedType ? RefactoringUtility.generateQualifiedTypeFromTypeBinding(typeBinding,ast,sourceRewriter) : RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
        Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
        typeBindings.add(typeBinding);
        RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
        SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
        sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,variableDeclaration1.getName(),null);
        sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,variableType,null);
        parameterRewrite.insertLast(parameter,null);
        originalPassedParameters.put(parameterName,variableDeclarations);
      }
    }
  }
  Block newMethodBody=newMethodDeclaration.getAST().newBlock();
  ListRewrite methodBodyRewrite=sourceRewriter.getListRewrite(newMethodBody,Block.STATEMENTS_PROPERTY);
  Set<ITypeBinding> thrownExceptionTypeBindings=new LinkedHashSet<ITypeBinding>();
  for (  PDGNodeMapping pdgNodeMapping : sortedNodeMappings) {
    PDGNode pdgNode1=pdgNodeMapping.getNodeG1();
    AbstractStatement statement1=pdgNode1.getStatement();
    PDGBlockNode blockNode1=mapper.getPDG1().isNestedWithinBlockNode(pdgNode1);
    if (blockNode1 != null && blockNode1 instanceof PDGTryNode && mapper.getRemovableNodesG1().contains(blockNode1)) {
    }
 else {
      ThrownExceptionVisitor thrownExceptionVisitor=new ThrownExceptionVisitor();
      statement1.getStatement().accept(thrownExceptionVisitor);
      for (      ITypeBinding thrownException : thrownExceptionVisitor.getTypeBindings()) {
        if (pdgNode1.getThrownExceptionTypes().contains(thrownException.getQualifiedName())) {
          addTypeBinding(thrownException,thrownExceptionTypeBindings);
        }
      }
    }
    RefactoringUtility.getSimpleTypeBindings(extractTypeBindings(statement1),requiredImportTypeBindings);
    PDGNode pdgNode2=pdgNodeMapping.getNodeG2();
    AbstractStatement statement2=pdgNode2.getStatement();
    PDGBlockNode blockNode2=mapper.getPDG2().isNestedWithinBlockNode(pdgNode2);
    if (blockNode2 != null && blockNode2 instanceof PDGTryNode && mapper.getRemovableNodesG2().contains(blockNode2)) {
    }
 else {
      ThrownExceptionVisitor thrownExceptionVisitor=new ThrownExceptionVisitor();
      statement2.getStatement().accept(thrownExceptionVisitor);
      for (      ITypeBinding thrownException : thrownExceptionVisitor.getTypeBindings()) {
        if (pdgNode2.getThrownExceptionTypes().contains(thrownException.getQualifiedName())) {
          addTypeBinding(thrownException,thrownExceptionTypeBindings);
        }
      }
    }
    RefactoringUtility.getSimpleTypeBindings(extractTypeBindings(statement2),requiredImportTypeBindings);
  }
  ListRewrite thrownExceptionRewrite=sourceRewriter.getListRewrite(newMethodDeclaration,MethodDeclaration.THROWN_EXCEPTIONS_PROPERTY);
  List<Name> thrownExceptions1=sourceMethodDeclarations.get(0).thrownExceptions();
  List<Name> thrownExceptions2=sourceMethodDeclarations.get(1).thrownExceptions();
  for (  Name thrownException1 : thrownExceptions1) {
    for (    Name thrownException2 : thrownExceptions2) {
      if (thrownException1.resolveTypeBinding().isEqualTo(thrownException2.resolveTypeBinding()) && thrownExceptionTypeBindings.contains(thrownException1.resolveTypeBinding())) {
        thrownExceptionRewrite.insertLast(thrownException1,null);
        Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
        typeBindings.add(thrownException1.resolveTypeBinding());
        RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
        thrownExceptionTypeBindings.remove(thrownException1.resolveTypeBinding());
        break;
      }
    }
  }
  for (  ITypeBinding thrownExceptionTypeBinding : thrownExceptionTypeBindings) {
    thrownExceptionRewrite.insertLast(ast.newSimpleName(thrownExceptionTypeBinding.getName()),null);
    Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
    typeBindings.add(thrownExceptionTypeBinding);
    RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
  }
  CloneStructureNode root=mapper.getCloneStructureRoot();
  for (  CloneStructureNode child : root.getChildren()) {
    if (processableNode(child)) {
      Statement statement=processCloneStructureNode(child,ast,sourceRewriter);
      if (processableMappedNode(child) && ((PDGNodeMapping)child.getMapping()).declaresInconsistentlyRenamedVariable(mapper.getRenamedVariableBindings()) && mapper.movableBeforeFirstMappedNode((PDGNodeMapping)child.getMapping())) {
        methodBodyRewrite.insertFirst(statement,null);
      }
 else {
        methodBodyRewrite.insertLast(statement,null);
      }
    }
  }
  if (returnedVariables1.size() == 1 && returnedVariables2.size() == 1 && !mappedNodesContainStatementReturningVariable(returnedVariables1.get(0),returnedVariables2.get(0))) {
    ReturnStatement returnStatement=ast.newReturnStatement();
    BindingSignaturePair variableBelongingToParameterizedDifferences=variableBelongsToParameterizedDifferences(returnedVariables1.get(0),returnedVariables2.get(0));
    if (variableBelongingToParameterizedDifferences != null) {
      int existingArgValue=findExistingParametersWithArgName();
      int i=0;
      if (existingArgValue > 0) {
        i=existingArgValue + 1;
      }
      for (      BindingSignaturePair pair : parameterizedDifferenceMap.keySet()) {
        if (pair.equals(variableBelongingToParameterizedDifferences)) {
          break;
        }
        i++;
      }
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,ast.newSimpleName("String_Node_Str" + i),null);
    }
 else {
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,returnedVariables1.get(0).getName(),null);
    }
    methodBodyRewrite.insertLast(returnStatement,null);
    if (!mappedNodesContainStatementDeclaringVariable(returnedVariables1.get(0),returnedVariables2.get(0)) && !mappedNodesContainDifferentStatementsDeclaringVariables(returnedVariables1.get(0),returnedVariables2.get(0)) && variableBelongingToParameterizedDifferences == null && !variableIsPassedAsCommonParameter(returnedVariables1.get(0),returnedVariables2.get(0))) {
      ITypeBinding returnedTypeBinding=extractTypeBinding(returnedVariables1.get(0));
      Expression initializer=generateDefaultValue(sourceRewriter,ast,returnedTypeBinding);
      VariableDeclarationFragment fragment=ast.newVariableDeclarationFragment();
      sourceRewriter.set(fragment,VariableDeclarationFragment.NAME_PROPERTY,returnedVariables1.get(0).getName(),null);
      sourceRewriter.set(fragment,VariableDeclarationFragment.INITIALIZER_PROPERTY,initializer,null);
      VariableDeclarationStatement declarationStatement=ast.newVariableDeclarationStatement(fragment);
      Type returnedType=RefactoringUtility.generateTypeFromTypeBinding(returnedTypeBinding,ast,sourceRewriter);
      sourceRewriter.set(declarationStatement,VariableDeclarationStatement.TYPE_PROPERTY,returnedType,null);
      methodBodyRewrite.insertFirst(declarationStatement,null);
    }
  }
 else {
    if (returnTypeBinding != null && !root.containsMappedReturnStatementInDirectChildren() && !root.lastIfElseIfChainContainsReturnOrThrowStatements()) {
      ReturnStatement returnStatement=ast.newReturnStatement();
      Expression expression=generateDefaultValue(sourceRewriter,ast,returnTypeBinding);
      sourceRewriter.set(returnStatement,ReturnStatement.EXPRESSION_PROPERTY,expression,null);
      methodBodyRewrite.insertLast(returnStatement,null);
    }
  }
  int existingArgValue=findExistingParametersWithArgName();
  int i=0;
  if (existingArgValue > 0) {
    i=existingArgValue + 1;
  }
  for (  ASTNodeDifference difference : parameterizedDifferenceMap.values()) {
    AbstractExpression expression1=difference.getExpression1();
    AbstractExpression expression2=difference.getExpression2();
    boolean isReturnedVariable=false;
    if (expression1 != null) {
      isReturnedVariable=isReturnedVariable(expression1.getExpression(),this.returnedVariables.get(0));
    }
 else     if (expression2 != null) {
      isReturnedVariable=isReturnedVariable(expression2.getExpression(),this.returnedVariables.get(1));
    }
    ITypeBinding typeBinding1=expression1 != null ? ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression1.getExpression()).resolveTypeBinding() : ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression2.getExpression()).resolveTypeBinding();
    ITypeBinding typeBinding2=expression2 != null ? ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression2.getExpression()).resolveTypeBinding() : ASTNodeDifference.getParentExpressionOfMethodNameOrTypeName(expression1.getExpression()).resolveTypeBinding();
    if (!isReturnedVariable || (returnedVariables1.size() == 1 && returnedVariables2.size() == 1 && variableBelongsToParameterizedDifferences(returnedVariables1.get(0),returnedVariables2.get(0)) != null)) {
      ITypeBinding typeBinding=null;
      if (difference.containsDifferenceType(DifferenceType.SUBCLASS_TYPE_MISMATCH) || difference.containsDifferenceType(DifferenceType.METHOD_INVOCATION_NAME_MISMATCH) || differenceContainsSubDifferenceWithSubclassTypeMismatch(difference)) {
        if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
          ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
          if (commonSuperTypeBinding != null) {
            typeBinding=commonSuperTypeBinding;
          }
        }
 else {
          typeBinding=typeBinding1;
        }
      }
 else {
        if (expression1 != null && !typeBinding1.getQualifiedName().equals("String_Node_Str")) {
          if (typeBinding1.getErasure().getQualifiedName().equals("String_Node_Str") && typeBinding2.getErasure().getQualifiedName().equals("String_Node_Str") && (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName()))) {
            typeBinding=typeBinding1.getErasure();
          }
 else {
            typeBinding=typeBinding1;
          }
        }
 else {
          typeBinding=typeBinding2;
        }
      }
      Type type=null;
      if (typeBinding.isPrimitive() && (typeBinding1.getQualifiedName().equals("String_Node_Str") || typeBinding2.getQualifiedName().equals("String_Node_Str"))) {
        type=RefactoringUtility.generateWrapperTypeForPrimitiveTypeBinding(typeBinding,ast);
      }
 else {
        type=RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
      }
      Set<ITypeBinding> typeBindings=new LinkedHashSet<ITypeBinding>();
      typeBindings.add(typeBinding);
      RefactoringUtility.getSimpleTypeBindings(typeBindings,requiredImportTypeBindings);
      SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
      sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName("String_Node_Str" + i),null);
      i++;
      sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,type,null);
      parameterRewrite.insertLast(parameter,null);
    }
  }
  int j=0;
  List<VariableDeclaration> fieldDeclarationsToBeParameterizedG2=new ArrayList<VariableDeclaration>(fieldDeclarationsToBeParameterized.get(1));
  for (  VariableDeclaration variableDeclaration1 : fieldDeclarationsToBeParameterized.get(0)) {
    if (accessedLocalFieldsG1.contains(variableDeclaration1)) {
      VariableDeclaration variableDeclaration2=fieldDeclarationsToBeParameterizedG2.get(j);
      ITypeBinding typeBinding1=variableDeclaration1.resolveBinding().getType();
      ITypeBinding typeBinding2=variableDeclaration2.resolveBinding().getType();
      ITypeBinding typeBinding=null;
      if (!typeBinding1.isEqualTo(typeBinding2) || !typeBinding1.getQualifiedName().equals(typeBinding2.getQualifiedName())) {
        ITypeBinding commonSuperTypeBinding=ASTNodeMatcher.commonSuperType(typeBinding1,typeBinding2);
        if (commonSuperTypeBinding != null) {
          typeBinding=commonSuperTypeBinding;
        }
      }
 else {
        typeBinding=typeBinding1;
      }
      SingleVariableDeclaration parameter=ast.newSingleVariableDeclaration();
      Type type=RefactoringUtility.generateTypeFromTypeBinding(typeBinding,ast,sourceRewriter);
      sourceRewriter.set(parameter,SingleVariableDeclaration.TYPE_PROPERTY,type,null);
      String identifier=(variableDeclaration1.resolveBinding().getModifiers() & Modifier.STATIC) != 0 ? variableDeclaration1.getName().getIdentifier() : createNameForParameterizedFieldAccess(variableDeclaration1.getName().getIdentifier());
      sourceRewriter.set(parameter,SingleVariableDeclaration.NAME_PROPERTY,ast.newSimpleName(identifier),null);
      parameterRewrite.insertLast(parameter,null);
    }
    j++;
  }
  sourceRewriter.set(newMethodDeclaration,MethodDeclaration.BODY_PROPERTY,newMethodBody,null);
  bodyDeclarationsRewrite.insertLast(newMethodDeclaration,null);
  cloneInfo.requiredImportTypeBindings=requiredImportTypeBindings;
  cloneInfo.methodBodyRewrite=methodBodyRewrite;
  cloneInfo.parameterRewrite=parameterRewrite;
}