MethodDefinition.java revision eb78b7fa6462e7c52e6f5779206a86559a64a06b
1fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org/*
2ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * [The "BSD licence"]
3ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * Copyright (c) 2009 Ben Gruver
4ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * All rights reserved.
5ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *
6ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * Redistribution and use in source and binary forms, with or without
7ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * modification, are permitted provided that the following conditions
8ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * are met:
9ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * 1. Redistributions of source code must retain the above copyright
10ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *    notice, this list of conditions and the following disclaimer.
11ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * 2. Redistributions in binary form must reproduce the above copyright
12ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *    notice, this list of conditions and the following disclaimer in the
13ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *    documentation and/or other materials provided with the distribution.
14ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * 3. The name of the author may not be used to endorse or promote products
15ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *    derived from this software without specific prior written permission.
16ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org *
17ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org */
28ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
29ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgpackage org.jf.baksmali.Adaptors;
30ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
31ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.baksmali.Adaptors.Format.*;
32ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.baksmali.baksmali;
3379e7902fa5f94747b5383dd40f3002dd8b62303arossberg@chromium.orgimport org.jf.dexlib.*;
34ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.dexlib.Debug.DebugInstructionIterator;
35ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.dexlib.Code.Format.*;
36ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.dexlib.Code.Instruction;
37ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.dexlib.Code.Opcode;
38ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.jf.dexlib.Code.InstructionIterator;
394efbdb18fa3063085682c44cc77cf5254cb3d75dsvenpanne@chromium.orgimport org.jf.dexlib.Util.AccessFlags;
40ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.antlr.stringtemplate.StringTemplateGroup;
41ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport org.antlr.stringtemplate.StringTemplate;
42ab30bb83bf3dae0053739c57b1db9ad13c1f9e3ayangguo@chromium.org
43ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgimport java.util.*;
44304cc33f8259ef467e8e3c79f448d0bae0e8cd85yangguo@chromium.org
45ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgpublic class MethodDefinition {
46ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    public static StringTemplate makeTemplate(StringTemplateGroup stg, ClassDataItem.EncodedMethod encodedMethod,
47ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                              AnnotationSetItem annotationSet,
48ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                              AnnotationSetRefList parameterAnnotations) {
49ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
50ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        CodeItem codeItem = encodedMethod.codeItem;
51ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
52ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        StringTemplate template = stg.getInstanceOf("method");
53ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
5457a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org        template.setAttribute("AccessFlags", getAccessFlags(encodedMethod));
55ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        template.setAttribute("MethodName", encodedMethod.method.getMethodName().getStringValue());
56ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        template.setAttribute("Prototype", encodedMethod.method.getPrototype().getPrototypeString());
57a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.org        template.setAttribute("HasCode", codeItem != null);
58e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org        template.setAttribute("RegistersDirective", baksmali.useLocalsDirective?".locals":".registers");
59ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        template.setAttribute("RegisterCount", codeItem==null?"0":Integer.toString(getRegisterCount(encodedMethod)));
6057a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org        template.setAttribute("Parameters", getParameters(stg, codeItem, parameterAnnotations));
61ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        template.setAttribute("Annotations", getAnnotations(stg, annotationSet));
62ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        template.setAttribute("MethodItems", getMethodItems(encodedMethod.method.getDexFile(), stg, codeItem));
63ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
64ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        return template;
65ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    }
66ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
67ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    private static int getRegisterCount(ClassDataItem.EncodedMethod encodedMethod)
68c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org    {
69ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        int totalRegisters = encodedMethod.codeItem.getRegisterCount();
70ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        if (baksmali.useLocalsDirective) {
71ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            int parameterRegisters = encodedMethod.method.getPrototype().getParameterRegisterCount();
72ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if ((encodedMethod.accessFlags & AccessFlags.STATIC.getValue()) == 0) {
73ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                parameterRegisters++;
74750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org            }
75750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org            return totalRegisters - parameterRegisters;
76ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
77c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com        return totalRegisters;
7857a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org    }
7957a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org
80c5d4971574b7a205fa0e788d8121dc79485e5e67hpayer@chromium.org    private static List<String> getAccessFlags(ClassDataItem.EncodedMethod encodedMethod) {
81ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        List<String> accessFlags = new ArrayList<String>();
82ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
83ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        for (AccessFlags accessFlag: AccessFlags.getAccessFlagsForMethod(encodedMethod.accessFlags)) {
84ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            accessFlags.add(accessFlag.toString());
85e3b8d0fe80e858c990832db1233c069f8b8cd5c9mstarzinger@chromium.org        }
86ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
87ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        return accessFlags;
88ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    }
8957a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org
90ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org    private static List<StringTemplate> getParameters(StringTemplateGroup stg, CodeItem codeItem,
91ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                                               AnnotationSetRefList parameterAnnotations) {
92ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        DebugInfoItem debugInfoItem = null;
93ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        if (codeItem != null) {
94ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            debugInfoItem = codeItem.getDebugInfo();
95ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
96ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
97ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        int parameterCount = 0;
98ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
99ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        List<AnnotationSetItem> annotations = new ArrayList<AnnotationSetItem>();
100ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        if (parameterAnnotations != null) {
101ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            AnnotationSetItem[] _annotations = parameterAnnotations.getAnnotationSets();
102ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (_annotations != null) {
103ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                annotations.addAll(Arrays.asList(_annotations));
10493a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org            }
105fa0c3c69b9d632e5730bdd9c745c375beef5e54dmachenbach@chromium.org
10693a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org            parameterCount = annotations.size();
107ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
108ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
109ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        List<String> parameterNames = new ArrayList<String>();
110ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        if (debugInfoItem != null) {
1117516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org            StringIdItem[] _parameterNames = debugInfoItem.getParameterNames();
112ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (_parameterNames != null) {
113ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                for (StringIdItem parameterName: _parameterNames) {
114ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    parameterNames.add(parameterName==null?null:parameterName.getStringValue());
115ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
116ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
117ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
118ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (parameterCount < parameterNames.size()) {
119ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                parameterCount = parameterNames.size();
120fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org            }
121fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org        }
122fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org
123fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org        List<StringTemplate> parameters = new ArrayList<StringTemplate>();
124fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org        for (int i=0; i<parameterCount; i++) {
125fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org            AnnotationSetItem annotationSet = null;
126fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org            if (i < annotations.size()) {
127ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                annotationSet = annotations.get(i);
128ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org            }
129ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org
130ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org            String parameterName = null;
131ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org            if (i < parameterNames.size()) {
132ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org                parameterName = parameterNames.get(i);
133ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org            }
134ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org
135ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org            parameters.add(ParameterAdaptor.makeTemplate(stg, parameterName, annotationSet));
136ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org        }
137255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
138255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        return parameters;
139255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org    }
140255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
141255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org    private static List<StringTemplate> getAnnotations(StringTemplateGroup stg, AnnotationSetItem annotationSet) {
142255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        if (annotationSet == null) {
143fab1498f2f42726c7de46c3ed560d56dd072a8b3rossberg@chromium.org            return null;
144ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
145f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com
146f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com        List<StringTemplate> annotationAdaptors = new ArrayList<StringTemplate>();
147f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com
148f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com        for (AnnotationItem annotationItem: annotationSet.getAnnotations()) {
149f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com            annotationAdaptors.add(AnnotationAdaptor.makeTemplate(stg, annotationItem));
150f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com        }
151255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        return annotationAdaptors;
152ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    }
153ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
154255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org    private static List<MethodItem> getMethodItems(DexFile dexFile, StringTemplateGroup stg, CodeItem codeItem) {
155255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        List<MethodItem> methodItems = new ArrayList<MethodItem>();
156255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
157255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        MethodItemList methodItemList = new MethodItemList(dexFile, stg, codeItem);
158255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        methodItemList.generateMethodItemList();
159255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
160255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        for (LabelMethodItem labelMethodItem: methodItemList.labels.getLabels()) {
161255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org            if (labelMethodItem.isCommentedOut()) {
162255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org                methodItems.add(new CommentedOutMethodItem(stg, labelMethodItem));
163255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org            } else {
164255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org                methodItems.add(labelMethodItem);
165255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org            }
166255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        }
167255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
168255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        methodItems.addAll(methodItemList.instructions);
169255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        methodItems.addAll(methodItemList.blanks);
170255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        methodItems.addAll(methodItemList.catches);
171255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        methodItems.addAll(methodItemList.debugItems);
172255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        Collections.sort(methodItems);
173255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
174255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        return methodItems;
175255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org    }
176255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
177255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
178255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org    private static class MethodItemList {
179255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        private final DexFile dexFile;
1808f8fe81d7a9cced7a0d30e56124c0428d1a6d229machenbach@chromium.org        private final StringTemplateGroup stg;
181255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        private final CodeItem codeItem;
182255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
183255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public LabelCache labels = new LabelCache();
184255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org
185255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public List<MethodItem> instructions = new ArrayList<MethodItem>();
186255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public List<BlankMethodItem> blanks = new ArrayList<BlankMethodItem>();
187255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public List<CatchMethodItem> catches = new ArrayList<CatchMethodItem>();
188255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public List<MethodItem> debugItems = new ArrayList<MethodItem>();
1898f8fe81d7a9cced7a0d30e56124c0428d1a6d229machenbach@chromium.org
190255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        private HashMap<Integer, Integer> packedSwitchMap = new HashMap<Integer, Integer>();
191255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        private HashMap<Integer, Integer> sparseSwitchMap = new HashMap<Integer, Integer>();
1928f8fe81d7a9cced7a0d30e56124c0428d1a6d229machenbach@chromium.org
193255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org        public MethodItemList(DexFile dexFile, StringTemplateGroup stg, CodeItem codeItem) {
194255043f8054e713a64509c707cfabadd42344683machenbach@chromium.org            this.dexFile = dexFile;
19583e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org            this.stg = stg;
19683e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org            this.codeItem = codeItem;
19783e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org        }
19883e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org
19983e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org        public void generateMethodItemList() {
20083e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org            if (codeItem == null) {
20183e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org                return;
202ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
203ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
204a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org            if (baksmali.deodexUtil != null && dexFile.isOdex()) {
205a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                List<Instruction> instructions = baksmali.deodexUtil.deodexerizeCode(codeItem);
206a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
207a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                int offset = 0;
208a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                for (Instruction instruction: instructions) {
209a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    if (instruction.opcode == Opcode.PACKED_SWITCH) {
210a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        Instruction31t ins = (Instruction31t)instruction;
211a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        packedSwitchMap.put(offset + ins.getOffset(), offset);
212a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    } else if (instruction.opcode == Opcode.SPARSE_SWITCH) {
213a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        Instruction31t ins = (Instruction31t)instruction;
214a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        sparseSwitchMap.put(offset + ins.getOffset(), offset);
215a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    }
216a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
217a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    offset += instruction.getSize()/2;
218a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                }
219a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
220a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                offset = 0;
221a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                for (Instruction instruction: instructions) {
222a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    addMethodItemsForInstruction(offset, instruction, false);
223a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    blanks.add(new BlankMethodItem(stg, offset));
224a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
225a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    offset += instruction.getSize()/2;
226a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                }
227a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
228a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                /*
229a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                 * Look for the last uncommented instruction. If it is an UnresolvedNullReference,
230a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                 * then set IsLastInstruction, so a goto will be added after it, to avoid validation
231a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                 * issues
232a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                 */
233a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                for (int i=this.instructions.size()-1; i>=0; i--) {
234a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    MethodItem ins = this.instructions.get(i);
235a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    if (ins instanceof UnresolvedNullReferenceMethodItem) {
236a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        ((UnresolvedNullReferenceMethodItem)ins).setIsLastInstruction(true);
237a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        break;
238a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    }
239a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
240a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    if (!(ins instanceof CommentedOutMethodItem)) {
241a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        break;
242a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    }
243a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                }
244a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org            } else {
245a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                final byte[] encodedInstructions = codeItem.getEncodedInstructions();
246a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org
247a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                InstructionIterator.IterateInstructions(encodedInstructions,
248a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                        new InstructionIterator.ProcessRawInstructionDelegate() {
249a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                            public void ProcessNormalInstruction(Opcode opcode, int index) {
250a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                                if (opcode == Opcode.PACKED_SWITCH) {
251f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                    Instruction31t ins = (Instruction31t)opcode.format.Factory.makeInstruction(
252f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                            dexFile, opcode, encodedInstructions, index);
253f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                    packedSwitchMap.put(index/2 + ins.getOffset(), index/2);
254f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                } else if (opcode == Opcode.SPARSE_SWITCH) {
255f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                    Instruction31t ins = (Instruction31t)opcode.format.Factory.makeInstruction(
256ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                            dexFile, opcode, encodedInstructions, index);
257ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    sparseSwitchMap.put(index/2 + ins.getOffset(),  index/2);
2585523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org                                }
2595523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org                            }
2605523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org
2615523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org                            public void ProcessReferenceInstruction(Opcode opcode, int index) {
262ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            }
263ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
264ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            public void ProcessPackedSwitchInstruction(int index, int targetCount, int instructionLength) {
265ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            }
266ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
267ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            public void ProcessSparseSwitchInstruction(int index, int targetCount, int instructionLength) {
268ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            }
269ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
270ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            public void ProcessFillArrayDataInstruction(int index, int elementWidth, int elementCount,
271ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                                                        int instructionLength) {
272ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            }
273ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        });
274ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
275ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                InstructionIterator.IterateInstructions(dexFile, encodedInstructions,
276ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        new InstructionIterator.ProcessInstructionDelegate() {
277ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            public void ProcessInstruction(int index, Instruction instruction) {
278ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                int offset = index/2;
279ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                addMethodItemsForInstruction(offset, instruction, false);
280ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                blanks.add(new BlankMethodItem(stg, offset));
281ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            }
282f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        });
283ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
284ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
285ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            blanks.remove(blanks.size()-1);
286ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
287ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            addTries();
288ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
289ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            addDebugInfo();
2901c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org
291ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (baksmali.useIndexedLabels) {
292ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                setLabelIndexes();
293ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
294a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org        }
2959e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org
296ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        private void addOffsetInstructionMethodItem(OffsetInstructionFormatMethodItem methodItem,
29793a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                                                    boolean commentedOut) {
298ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (commentedOut) {
29993a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                instructions.add(new CommentedOutMethodItem(stg, methodItem));
300ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            } else {
301ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                instructions.add(methodItem);
302ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                LabelMethodItem label = methodItem.getLabel();
303ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                label.setUncommented();
304ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
3059e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org        }
306ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
307ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
308ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        private void addInstructionMethodItem(InstructionFormatMethodItem methodItem, boolean commentedOut) {
309ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (commentedOut) {
310ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                instructions.add(new CommentedOutMethodItem(stg, methodItem));
311ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            } else {
312ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                instructions.add(methodItem);
313ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
314ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
315ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
316ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        private void addMethodItemsForInstruction(int offset, Instruction instruction, boolean commentedOut) {
317ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            switch (instruction.getFormat()) {
3182efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org                case Format10t:
319c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org                    addOffsetInstructionMethodItem(
320c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org                            new Instruction10tMethodItem(labels, codeItem, offset, stg,(Instruction10t)instruction),
321ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
322ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
323ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format10x:
324ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
325ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction10xMethodItem(codeItem, offset, stg, (Instruction10x)instruction),
326ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
327ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
328ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format11n:
329394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com                    addInstructionMethodItem(
330394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com                            new Instruction11nMethodItem(codeItem, offset, stg, (Instruction11n)instruction),
331394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com                            commentedOut);
332ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
3335523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org                case Format11x:
3345523ec3bee8180775e7a6fff2b57c04ef707ad3bvitalyr@chromium.org                    addInstructionMethodItem(
335ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction11xMethodItem(codeItem, offset, stg, (Instruction11x)instruction),
336ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
337ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
338ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format12x:
339ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
340ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction12xMethodItem(codeItem, offset, stg, (Instruction12x)instruction),
341ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
342ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
343ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format20t:
344ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addOffsetInstructionMethodItem(
345ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction20tMethodItem(labels, codeItem, offset, stg, (Instruction20t)instruction),
346ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
347ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
348ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format21c:
3496b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addInstructionMethodItem(
3506b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            new Instruction21cMethodItem(codeItem, offset, stg, (Instruction21c)instruction),
351fa0c3c69b9d632e5730bdd9c745c375beef5e54dmachenbach@chromium.org                            commentedOut);
3526b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    return;
3536b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                case Format21h:
3546b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addInstructionMethodItem(
3556b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            new Instruction21hMethodItem(codeItem, offset, stg, (Instruction21h)instruction),
3566b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            commentedOut);
3576b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    return;
3586b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                case Format21s:
3596b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addInstructionMethodItem(
3606b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            new Instruction21sMethodItem(codeItem, offset, stg, (Instruction21s)instruction),
3616b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            commentedOut);
3626b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    return;
3636b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                case Format21t:
3646b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addOffsetInstructionMethodItem(
365ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction21tMethodItem(labels, codeItem, offset, stg, (Instruction21t)instruction),
366ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
367ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
368ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format22b:
3696b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addInstructionMethodItem(
3706b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            new Instruction22bMethodItem(codeItem, offset, stg, (Instruction22b)instruction),
371ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
372ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
373ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format22c:
374ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
375ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction22cMethodItem(codeItem, offset, stg, (Instruction22c)instruction),
376ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
377ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
378ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format22cs:
379355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org                    addInstructionMethodItem(
380ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction22csMethodItem(codeItem, offset, stg, (Instruction22cs)instruction),
381ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
382ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
3834f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org                case Format22csf:
384ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
385ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction22csfMethodItem(codeItem, offset, stg, (Instruction22csf)instruction),
3867ff7607c2315ea91e4d13330ce14125e4bb4851amachenbach@chromium.org                            commentedOut);
387ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
388ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format22s:
389ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
390ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction22sMethodItem(codeItem, offset, stg, (Instruction22s)instruction),
3915a11aaf63fdb7843c9b116fdb84ee35b0a980ea6yangguo@chromium.org                            commentedOut);
3925a11aaf63fdb7843c9b116fdb84ee35b0a980ea6yangguo@chromium.org                    return;
393ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format22t:
394ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addOffsetInstructionMethodItem(
395ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction22tMethodItem(labels, codeItem, offset, stg, (Instruction22t)instruction),
396ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
397ca2f2040e0e1a10df95bec18e69499f85f4c1316machenbach@chromium.org                    return;
398fb144a0716afe7ab8bf245f2391a9e53b3db3c89fschneider@chromium.org                case Format22x:
399ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
40046839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org                            new Instruction22xMethodItem(codeItem, offset, stg, (Instruction22x)instruction),
401ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
402ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
403ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format23x:
404ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
405ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction23xMethodItem(codeItem, offset, stg, (Instruction23x)instruction),
406ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
407ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
408ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format30t:
409ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addOffsetInstructionMethodItem(
410ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction30tMethodItem(labels, codeItem, offset, stg, (Instruction30t)instruction),
411ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
412b1df11df5b7bdcc201852bfcdce0a8eace33b011svenpanne@chromium.org                    return;
413ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format31c:
414f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                    addInstructionMethodItem(
415f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            new Instruction31cMethodItem(codeItem, offset, stg, (Instruction31c)instruction),
416750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org                            commentedOut);
417750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org                    return;
418e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org                case Format31i:
4196b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    addInstructionMethodItem(
4206b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                            new Instruction31iMethodItem(codeItem, offset, stg, (Instruction31i)instruction),
4215697144afb43181fed170b81c194fe1cc0fce3b6machenbach@chromium.org                            commentedOut);
4226b6df382019a622ba20133e47bbe2e6f323b013bdslomov@chromium.org                    return;
423ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format31t:
424ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addOffsetInstructionMethodItem(
425f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            new Instruction31tMethodItem(labels, codeItem, offset, stg, (Instruction31t)instruction),
426f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            commentedOut);
427f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                    return;
428f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                case Format32x:
429f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                    addInstructionMethodItem(
430ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction32xMethodItem(codeItem, offset, stg, (Instruction32x)instruction),
431ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
432ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
433ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format35c:
434ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
435ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction35cMethodItem(codeItem, offset, stg, (Instruction35c)instruction),
436ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
437ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
438ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format35s:
439ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
440ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction35sMethodItem(codeItem, offset, stg, (Instruction35s)instruction),
441ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
442ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
443ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format35sf:
444ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
445ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction35sfMethodItem(codeItem, offset, stg, (Instruction35sf)instruction),
446ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
447ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
44893a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                case Format35ms:
449fa0c3c69b9d632e5730bdd9c745c375beef5e54dmachenbach@chromium.org                    addInstructionMethodItem(
45093a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                            new Instruction35msMethodItem(codeItem, offset, stg, (Instruction35ms)instruction),
451ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
452ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
453ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format35msf:
454ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
455f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            new Instruction35msfMethodItem(codeItem, offset, stg, (Instruction35msf)instruction),
456ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
457ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
458f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                case Format3rc:
459f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                    addInstructionMethodItem(
460f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            new Instruction3rcMethodItem(codeItem, offset, stg, (Instruction3rc)instruction),
461ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
46293a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                    return;
463fa0c3c69b9d632e5730bdd9c745c375beef5e54dmachenbach@chromium.org                case Format3rms:
46493a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                    addInstructionMethodItem(
465f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            new Instruction3rmsMethodItem(codeItem, offset, stg, (Instruction3rms)instruction),
466ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
467ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
468ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format3rmsf:
469a9aa5fa8ae2a2b43a94e6462ded2cd51445e9ee3ager@chromium.org                    addInstructionMethodItem(
470ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction3rmsfMethodItem(codeItem, offset, stg, (Instruction3rmsf)instruction),
471ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
472ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
473ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case Format51l:
474ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addInstructionMethodItem(
475ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            new Instruction51lMethodItem(codeItem, offset, stg, (Instruction51l)instruction),
476ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
477ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
47893a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                case ArrayData:
479fa0c3c69b9d632e5730bdd9c745c375beef5e54dmachenbach@chromium.org                    addInstructionMethodItem(
48093a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org                            new ArrayDataMethodItem(codeItem, offset, stg, (ArrayDataPseudoInstruction)instruction),
481ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            commentedOut);
482ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
483ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case PackedSwitchData:
484ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                {
485ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    final Integer baseAddress = packedSwitchMap.get(offset);
486ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
487ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    if (baseAddress != null) {
488ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        PackedSwitchDataPseudoInstruction packedSwitchInstruction =
489ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                (PackedSwitchDataPseudoInstruction)instruction;
490ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
491ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        PackedSwitchMethodItem packedSwitch = new PackedSwitchMethodItem(labels, codeItem, offset, stg,
492ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                packedSwitchInstruction, baseAddress);
493ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        addInstructionMethodItem(packedSwitch, commentedOut);
494ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
495ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        if (!commentedOut) {
49683e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org                            for (LabelMethodItem label: packedSwitch) {
49783e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org                                label.setUncommented();
498efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org                            }
49983e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org                        }
500ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    }
501ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
502ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
503ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case SparseSwitchData:
504ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                {
505ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    final Integer baseAddress = sparseSwitchMap.get(offset);
5068c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org
507ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    if (baseAddress != null) {
508ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        SparseSwitchDataPseudoInstruction sparseSwitchInstruction =
509ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                (SparseSwitchDataPseudoInstruction)instruction;
510ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
5117979bbb1df2eaff193e85d44c8da1ffa1525b7fcfschneider@chromium.org                        SparseSwitchMethodItem sparseSwitch = new SparseSwitchMethodItem(labels, codeItem, offset, stg,
5128c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                                sparseSwitchInstruction, baseAddress);
513ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        addInstructionMethodItem(sparseSwitch, commentedOut);
514ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
515ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        if (!commentedOut) {
516ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            for (LabelMethodItem label: sparseSwitch) {
517ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                label.setUncommented();
5188c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                            }
519ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        }
520ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    }
5217c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                    return;
5227c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                }
5237c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                case UnresolvedNullReference:
5247c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                {
5257c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                    addInstructionMethodItem(new UnresolvedNullReferenceMethodItem(codeItem, offset, stg,
5267c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                            (UnresolvedNullReference)instruction), commentedOut);
5277c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org                    addMethodItemsForInstruction(offset, ((UnresolvedNullReference)instruction).OriginalInstruction,
528ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            true);
529ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
530ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
531ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                case DeadInstruction:
532ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                {
533ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    //TODO: what about try/catch blocks inside the dead code? those will need to be commented out too. ugh.
534ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    addMethodItemsForInstruction(offset, ((DeadInstruction)instruction).OriginalInstruction, true);
535ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    return;
536ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
537ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
538ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
539ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
5407c3372bc426136cb79479c1b59d1770f5528882ahpayer@chromium.org        private void addTries() {
5417c3372bc426136cb79479c1b59d1770f5528882ahpayer@chromium.org            if (codeItem.getTries() == null) {
5428c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                return;
543ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
544528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org            for (CodeItem.TryItem tryItem: codeItem.getTries()) {
545ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                int startAddress = tryItem.startAddress;
5462efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org                int endAddress = tryItem.startAddress + tryItem.instructionCount;
547ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
548ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                /**
549ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                 * The end address points to the address immediately after the end of the last
550ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                 * instruction that the try block covers. We want the .catch directive and end_try
5511c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org                 * label to be associated with the last covered instruction, so we need to get
5521c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org                 * the offset for that instruction
5531c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org                 */
5541c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org                int index = Collections.binarySearch(instructions, new BlankMethodItem(stg, endAddress));
555e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org                if (index < 0) {
556e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org                    index = (index * -1) - 1;
557e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org                }
558e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org                //index should never be 0, so this should be safe
5593847bd5ff857259e945a01d75fdb383e2351d166erik.corry@gmail.com                if (index == instructions.size()) {
560ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    //if the end address is the same as the address of the last instruction, then
561ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    //this try item ends at the next to last instruction.
562ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    //otherwise, if the end address is past the address of the last instruction,
5633847bd5ff857259e945a01d75fdb383e2351d166erik.corry@gmail.com                    //thin this try item ends at the last instruction
564ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    if (instructions.get(instructions.size() - 1).getOffset() == endAddress) {
565ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        //get the address for the next to last instruction
566ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        index -= 2;
567ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    } else {
568ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        //get the address for the last instruction
569ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        index--;
570ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    }
571ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                } else {
5728c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                    index -= 2;
5738c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                }
5748c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org
575ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                int lastInstructionOffset = instructions.get(index).getOffset();
576ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
5778c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                //add the catch all handler if it exists
5788c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                int catchAllAddress = tryItem.encodedCatchHandler.catchAllHandlerAddress;
5798c0a43f09f145d9fc6f969d559873018176eeb6adanno@chromium.org                if (catchAllAddress != -1) {
5801456e708d277e725ca42a03463af16fe471c9210jkummerow@chromium.org                    CatchMethodItem catchMethodItem = new CatchMethodItem(labels, lastInstructionOffset, stg, null,
5811456e708d277e725ca42a03463af16fe471c9210jkummerow@chromium.org                            startAddress, endAddress, catchAllAddress);
582ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    catches.add(catchMethodItem);
583ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
584ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
585ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                //add the rest of the handlers
586ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                for (CodeItem.EncodedTypeAddrPair handler: tryItem.encodedCatchHandler.handlers) {
587ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    //use the offset from the last covered instruction
588ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    CatchMethodItem catchMethodItem = new CatchMethodItem(labels, lastInstructionOffset, stg,
589ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            handler.exceptionType, startAddress, endAddress, handler.handlerAddress);
590dc94e19484d1700cb0ec22365444223e49a3ac1ejkummerow@chromium.org                    catches.add(catchMethodItem);
591ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
5927c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org            }
593dc94e19484d1700cb0ec22365444223e49a3ac1ejkummerow@chromium.org        }
5947c2628c3f0353f0558760c3ca442f934263ea766kmillikin@chromium.org
595ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        private void addDebugInfo() {
596ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            DebugInfoItem debugInfoItem = codeItem.getDebugInfo();
597ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (debugInfoItem == null) {
598ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                return;
599ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
600e297f5973a8a9ff0d9945da3f1e2d8a6230c294djkummerow@chromium.org
601ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            DebugInstructionIterator.DecodeInstructions(debugInfoItem, codeItem.getRegisterCount(),
602ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                    new DebugInstructionIterator.ProcessDecodedDebugInstructionDelegate() {
603ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        @Override
604ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        public void ProcessStartLocal(int codeAddress, int length, int registerNum, StringIdItem name,
605f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                                                      TypeIdItem type) {
606ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new LocalDebugMethodItem(codeItem, codeAddress, stg, "StartLocal", -1,
607ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    registerNum, name, type, null));
608f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        }
609ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
610ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        @Override
6119e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                        public void ProcessStartLocalExtended(int codeAddress, int length, int registerNum,
612ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                                              StringIdItem name, TypeIdItem type,
6139e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                                                              StringIdItem signature) {
614ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new LocalDebugMethodItem(codeItem, codeAddress, stg, "StartLocal", -1,
615ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    registerNum, name, type, signature));
616f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        }
6179e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org
6189e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                        @Override
619ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        public void ProcessEndLocal(int codeAddress, int length, int registerNum, StringIdItem name,
620ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                                    TypeIdItem type, StringIdItem signature) {
621f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                            debugItems.add(new LocalDebugMethodItem(codeItem, codeAddress, stg, "EndLocal", -1,
622ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    registerNum, name, type, signature));
6239e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                        }
624ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
625ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        @Override
626f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        public void ProcessRestartLocal(int codeAddress, int length, int registerNum, StringIdItem name,
6279e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                                                        TypeIdItem type, StringIdItem signature) {
628ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new LocalDebugMethodItem(codeItem, codeAddress, stg, "RestartLocal", -1,
629ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    registerNum, name, type, signature));
630f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        }
631ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
6329e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                        @Override
633ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        public void ProcessSetPrologueEnd(int codeAddress) {
634ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new DebugMethodItem(codeAddress, stg, "EndPrologue", -4));
635f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        }
636f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org
637f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        @Override
638ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        public void ProcessSetEpilogueBegin(int codeAddress) {
639ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new DebugMethodItem(codeAddress, stg, "StartEpilogue", -4));
640ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        }
64193a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org
642ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        @Override
643ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        public void ProcessSetFile(int codeAddress, int length, final StringIdItem name) {
644ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            debugItems.add(new DebugMethodItem(codeAddress, stg, "SetFile", -3) {
645ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                @Override
646ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                protected void setAttributes(StringTemplate template) {
647ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                    template.setAttribute("FileName", name.getStringValue());
648ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                }
649ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                            });
650ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                        }
651ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
652f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        @Override
653f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org                        public void ProcessLineEmit(int codeAddress, final int line) {
654ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                             debugItems.add(new DebugMethodItem(codeAddress, stg, "Line", -2) {
6559e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                                 @Override
656ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                 protected void setAttributes(StringTemplate template) {
657ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                                     template.setAttribute("Line", line);
6587028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org                                 }
6597028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org                             });
6607028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org                        }
6617028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org                    });
6627028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org        }
6637028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org
6647028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org        private void setLabelIndexes() {
6657028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org            HashMap<String, Integer> nextLabelIndexByType = new HashMap<String, Integer>();
6667028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org            ArrayList<LabelMethodItem> sortedLabels = new ArrayList<LabelMethodItem>(labels.getLabels());
6677028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org
6687028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org            //sort the labels by their location in the method
6697028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org            Collections.sort(sortedLabels);
6707028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org
6717028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org            for (LabelMethodItem labelMethodItem: sortedLabels) {
6729e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                Integer labelIndex = nextLabelIndexByType.get(labelMethodItem.getLabelPrefix());
673ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                if (labelIndex == null) {
6749e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org                    labelIndex = 0;
675ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                }
676ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                labelMethodItem.setLabelIndex(labelIndex);
677ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                nextLabelIndexByType.put(labelMethodItem.getLabelPrefix(), labelIndex + 1);
6789e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org            }
6796d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org        }
680ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    }
681ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
6829e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org    public static class LabelCache {
683ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        protected HashMap<LabelMethodItem, LabelMethodItem> labels = new HashMap<LabelMethodItem, LabelMethodItem>();
684ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
685ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        public LabelCache() {
686ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
687ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
6889e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org        public LabelMethodItem internLabel(LabelMethodItem labelMethodItem) {
689a221880197f38ff22d942851060daffa5d036bdfmachenbach@chromium.org            LabelMethodItem internedLabelMethodItem = labels.get(labelMethodItem);
690ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            if (internedLabelMethodItem != null) {
691ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org                if (!labelMethodItem.isCommentedOut()) {
6925a11aaf63fdb7843c9b116fdb84ee35b0a980ea6yangguo@chromium.org                    internedLabelMethodItem.setUncommented();
6935a11aaf63fdb7843c9b116fdb84ee35b0a980ea6yangguo@chromium.org                }
6945a11aaf63fdb7843c9b116fdb84ee35b0a980ea6yangguo@chromium.org                return internedLabelMethodItem;
695ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            }
696ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            labels.put(labelMethodItem, labelMethodItem);
697ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            return labelMethodItem;
698ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
699ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
700ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org
701ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        public Collection<LabelMethodItem> getLabels() {
702ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org            return labels.values();
703ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org        }
704ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org    }
705ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org}
706594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org