class BodyExtractorWalker extends Walker {
  private static final Logger logger = LoggerFactory.getLogger(BodyExtractorWalker.class);
  Map<SootMethod, JimpleBody> methodToParsedBodyMap;

  /**
   * Constructs a walker, and attaches it to the given SootClass, sending bodies to the given methodToParsedBodyMap.
   */
  public BodyExtractorWalker(SootClass sc, SootResolver resolver, Map<SootMethod, JimpleBody> methodToParsedBodyMap) {
    super(sc, resolver);
    this.methodToParsedBodyMap = methodToParsedBodyMap;
  }

  /*
   * file = modifier* file_type class_name extends_clause? implements_clause? file_body;
   */
  public void caseAFile(AFile node) {<FILL_FUNCTION_BODY>}

  public void outAFile(AFile node) {
    if (node.getImplementsClause() != null) {
      mProductions.removeLast(); // implements_clause
    }

    if (node.getExtendsClause() != null) {
      mProductions.removeLast(); // extends_clause
    }

    mProductions.removeLast(); // file_type
    mProductions.addLast(mSootClass);
  }

  /*
   * member = {field} modifier* type name semicolon | {method} modifier* type name l_paren parameter_list? r_paren
   * throws_clause? method_body;
   */
  public void outAFieldMember(AFieldMember node) {
    mProductions.removeLast(); // name
    mProductions.removeLast(); // type
  }

  public void outAMethodMember(AMethodMember node) {
    Type type;
    String name;
    List<Type> parameterList = new ArrayList<Type>();
    List throwsClause = null;
    JimpleBody methodBody = null;

    if (node.getMethodBody() instanceof AFullMethodBody) {
      methodBody = (JimpleBody) mProductions.removeLast();
    }

    if (node.getThrowsClause() != null) {
      throwsClause = (List) mProductions.removeLast();
    }

    if (node.getParameterList() != null) {
      parameterList = (List) mProductions.removeLast();
    }

    name = (String) mProductions.removeLast(); // name
    type = (Type) mProductions.removeLast(); // type
    SootMethod sm = mSootClass.getMethodUnsafe(SootMethod.getSubSignature(name, parameterList, type));
    if (sm != null) {
      if (Options.v().verbose()) {
        logger.debug("[Jimple parser] " + SootMethod.getSubSignature(name, parameterList, type));
      }
    } else {
      logger.debug("[!!! Couldn't parse !!] " + SootMethod.getSubSignature(name, parameterList, type));

      logger.debug("[!] Methods in class are:");
      for (SootMethod next : mSootClass.getMethods()) {
        logger.debug("" + next.getSubSignature());
      }

    }

    if (sm.isConcrete() && methodBody != null) {
      if (Options.v().verbose()) {
        logger.debug("[Parsed] " + sm.getDeclaration());
      }

      methodBody.setMethod(sm);
      methodToParsedBodyMap.put(sm, methodBody);
    } else if (node.getMethodBody() instanceof AFullMethodBody) {
      if (sm.isPhantom() && Options.v().verbose()) {
        logger.debug("[jimple parser] phantom method!");
      }
      throw new RuntimeException("Impossible: !concrete => ! instanceof " + sm.getName());
    }
  }

}

    inAFile(node);
    {
      Object temp[] = node.getModifier().toArray();
      for (Object element : temp) {
        ((PModifier) element).apply(this);
      }
    }
    if (node.getFileType() != null) {
      node.getFileType().apply(this);
    }
    if (node.getClassName() != null) {
      node.getClassName().apply(this);
    }

    String className = (String) mProductions.removeLast();
    if (!className.equals(mSootClass.getName())) {
      throw new RuntimeException("expected:  " + className + ", but got: " + mSootClass.getName());
    }

    if (node.getExtendsClause() != null) {
      node.getExtendsClause().apply(this);
    }
    if (node.getImplementsClause() != null) {
      node.getImplementsClause().apply(this);
    }
    if (node.getFileBody() != null) {
      node.getFileBody().apply(this);
    }
    outAFile(node);
  
<methods>public void <init>(soot.SootResolver) ,public void <init>(soot.SootClass, soot.SootResolver) ,public void caseAFile(AFile) ,public void defaultCase(Node) ,public soot.SootClass getSootClass() ,public void inAFile(AFile) ,public void inAFullMethodBody(AFullMethodBody) ,public void outAAndBinop(AAndBinop) ,public void outAArrayNewExpr(AArrayNewExpr) ,public void outAArrayReference(AArrayReference) ,public void outAAssignStatement(AAssignStatement) ,public void outABaseNonvoidType(ABaseNonvoidType) ,public void outABinopBoolExpr(ABinopBoolExpr) ,public void outABinopExpr(ABinopExpr) ,public void outABooleanBaseType(ABooleanBaseType) ,public void outABooleanBaseTypeNoName(ABooleanBaseTypeNoName) ,public void outABreakpointStatement(ABreakpointStatement) ,public void outAByteBaseType(AByteBaseType) ,public void outAByteBaseTypeNoName(AByteBaseTypeNoName) ,public void outACaseStmt(ACaseStmt) ,public void outACastExpression(ACastExpression) ,public void outACatchClause(ACatchClause) ,public void outACharBaseType(ACharBaseType) ,public void outACharBaseTypeNoName(ACharBaseTypeNoName) ,public void outAClassFileType(AClassFileType) ,public void outAClassNameBaseType(AClassNameBaseType) ,public void outAClassNameMultiClassNameList(AClassNameMultiClassNameList) ,public void outAClassNameSingleClassNameList(AClassNameSingleClassNameList) ,public void outAClzzConstant(AClzzConstant) ,public void outACmpBinop(ACmpBinop) ,public void outACmpeqBinop(ACmpeqBinop) ,public void outACmpgBinop(ACmpgBinop) ,public void outACmpgeBinop(ACmpgeBinop) ,public void outACmpgtBinop(ACmpgtBinop) ,public void outACmplBinop(ACmplBinop) ,public void outACmpleBinop(ACmpleBinop) ,public void outACmpltBinop(ACmpltBinop) ,public void outACmpneBinop(ACmpneBinop) ,public void outAConstantCaseLabel(AConstantCaseLabel) ,public void outADeclaration(ADeclaration) ,public void outADivBinop(ADivBinop) ,public void outADoubleBaseType(ADoubleBaseType) ,public void outADoubleBaseTypeNoName(ADoubleBaseTypeNoName) ,public void outADynamicInvokeExpr(ADynamicInvokeExpr) ,public void outAEntermonitorStatement(AEntermonitorStatement) ,public void outAExitmonitorStatement(AExitmonitorStatement) ,public void outAFieldMember(AFieldMember) ,public void outAFieldSignature(AFieldSignature) ,public void outAFile(AFile) ,public void outAFloatBaseType(AFloatBaseType) ,public void outAFloatBaseTypeNoName(AFloatBaseTypeNoName) ,public void outAFloatConstant(AFloatConstant) ,public void outAFullIdentNonvoidType(AFullIdentNonvoidType) ,public void outAFullMethodBody(AFullMethodBody) ,public void outAGotoStatement(AGotoStatement) ,public void outAIdentNonvoidType(AIdentNonvoidType) ,public void outAIdentityNoTypeStatement(AIdentityNoTypeStatement) ,public void outAIdentityStatement(AIdentityStatement) ,public void outAIfStatement(AIfStatement) ,public void outAInstanceofExpression(AInstanceofExpression) ,public void outAIntBaseType(AIntBaseType) ,public void outAIntBaseTypeNoName(AIntBaseTypeNoName) ,public void outAIntegerConstant(AIntegerConstant) ,public void outAInterfaceFileType(AInterfaceFileType) ,public void outAInvokeStatement(AInvokeStatement) ,public void outALabelStatement(ALabelStatement) ,public void outALengthofUnop(ALengthofUnop) ,public void outALocalFieldRef(ALocalFieldRef) ,public void outALocalImmediate(ALocalImmediate) ,public void outALocalVariable(ALocalVariable) ,public void outALongBaseType(ALongBaseType) ,public void outALongBaseTypeNoName(ALongBaseTypeNoName) ,public void outALookupswitchStatement(ALookupswitchStatement) ,public void outAMethodMember(AMethodMember) ,public void outAMethodSignature(AMethodSignature) ,public void outAMinusBinop(AMinusBinop) ,public void outAModBinop(AModBinop) ,public void outAMultBinop(AMultBinop) ,public void outAMultiArgList(AMultiArgList) ,public void outAMultiLocalNameList(AMultiLocalNameList) ,public void outAMultiNewExpr(AMultiNewExpr) ,public void outAMultiParameterList(AMultiParameterList) ,public void outANegUnop(ANegUnop) ,public void outANonstaticInvokeExpr(ANonstaticInvokeExpr) ,public void outANopStatement(ANopStatement) ,public void outANovoidType(ANovoidType) ,public void outANullBaseType(ANullBaseType) ,public void outANullBaseTypeNoName(ANullBaseTypeNoName) ,public void outANullConstant(ANullConstant) ,public void outAOrBinop(AOrBinop) ,public void outAPlusBinop(APlusBinop) ,public void outAQuotedNonvoidType(AQuotedNonvoidType) ,public void outARetStatement(ARetStatement) ,public void outAReturnStatement(AReturnStatement) ,public void outAShlBinop(AShlBinop) ,public void outAShortBaseType(AShortBaseType) ,public void outAShortBaseTypeNoName(AShortBaseTypeNoName) ,public void outAShrBinop(AShrBinop) ,public void outASigFieldRef(ASigFieldRef) ,public void outASimpleNewExpr(ASimpleNewExpr) ,public void outASingleArgList(ASingleArgList) ,public void outASingleLocalNameList(ASingleLocalNameList) ,public void outASingleParameterList(ASingleParameterList) ,public void outAStaticInvokeExpr(AStaticInvokeExpr) ,public void outAStringConstant(AStringConstant) ,public void outATableswitchStatement(ATableswitchStatement) ,public void outAThrowStatement(AThrowStatement) ,public void outAThrowsClause(AThrowsClause) ,public void outAUnknownJimpleType(AUnknownJimpleType) ,public void outAUnnamedMethodSignature(AUnnamedMethodSignature) ,public void outAUnopExpr(AUnopExpr) ,public void outAUnopExpression(AUnopExpression) ,public void outAUshrBinop(AUshrBinop) ,public void outAVoidType(AVoidType) ,public void outAXorBinop(AXorBinop) ,public void outStart(Start) <variables>boolean debug,private static final org.slf4j.Logger logger,Map<java.lang.String,List#RAW> mLabelToPatchList,Map<java.lang.Object,soot.Unit> mLabelToStmtMap,Map<java.lang.String,soot.Local> mLocals,LinkedList#RAW mProductions,protected final non-sealed soot.SootResolver mResolver,soot.SootClass mSootClass,soot.Value mValue