Initial Jack import part 2.

Change-Id: Ic439604a1f030700d9049800fbf62422e0004d35
diff --git a/dexcomparator/.settings/org.eclipse.jdt.ui.prefs b/dexcomparator/.settings/org.eclipse.jdt.ui.prefs
index d44207b..ae892c8 100644
--- a/dexcomparator/.settings/org.eclipse.jdt.ui.prefs
+++ b/dexcomparator/.settings/org.eclipse.jdt.ui.prefs
@@ -4,7 +4,7 @@
 formatter_profile=_Jack Format 100
 formatter_settings_version=13
 org.eclipse.jdt.ui.ignorelowercasenames=true
-org.eclipse.jdt.ui.importorder=com.google;android;antenna;antlr;ar;asposewobfuscated;asquare;atg;au;beaver;bibtex;bmsi;bsh;ccl;cern;ChartDirector;checkers;com;COM;common;contribs;corejava;cryptix;cybervillains;dalvik;danbikel;de;EDU;eg;eu;examples;fat;fit;fitlibrary;fmpp;freemarker;gnu;groovy;groovyjarjarantlr;groovyjarjarasm;hak;hep;ie;imageinfo;info;it;jal;Jama;japa;japacheckers;jas;jasmin;javancss;javanet;javassist;javazoom;java_cup;jcifs;jetty;JFlex;jj2000;jline;jp;JSci;jsr166y;junit;jxl;jxxload_help;kawa;kea;libcore;libsvm;lti;memetic;mt;mx4j;net;netscape;nl;nu;oauth;ognl;opennlp;oracle;org;penn2dg;pennconverter;pl;prefuse;proguard;repackage;scm;se;serp;simple;soot;sqlj;src;ssa;sun;sunlabs;tcl;testdata;testshell;testsuite;twitter4j;uk;ViolinStrings;weka;wet;winstone;woolfel;wowza;;java;javax;
+org.eclipse.jdt.ui.importorder=com.google;android;antenna;antlr;ar;asposewobfuscated;asquare;atg;au;beaver;bibtex;bmsi;bsh;ccl;cern;ChartDirector;checkers;com;COM;common;contribs;corejava;cryptix;cybervillains;dalvik;danbikel;de;EDU;eg;eu;examples;fat;fit;fitlibrary;fmpp;freemarker;gnu;groovy;groovyjarjarantlr;groovyjarjarasm;hak;hep;ie;imageinfo;info;it;jal;Jama;japa;japacheckers;jas;jasmin;javancss;javanet;javassist;javazoom;java_cup;jcifs;jetty;JFlex;jj2000;jline;jp;JSci;jsr166y;junit;jxl;jxxload_help;kawa;kea;libcore;libsvm;lti;memetic;mt;mx4j;net;netscape;nl;nu;oauth;ognl;opennlp;oracle;org;org.jf.dexlib.EncodedValue;penn2dg;pennconverter;pl;prefuse;proguard;repackage;scm;se;serp;simple;soot;sqlj;src;ssa;sun;sunlabs;tcl;testdata;testshell;testsuite;twitter4j;uk;ViolinStrings;weka;wet;winstone;woolfel;wowza;;java;javax;
 org.eclipse.jdt.ui.javadoc=true
 org.eclipse.jdt.ui.ondemandthreshold=999
 org.eclipse.jdt.ui.staticondemandthreshold=999
diff --git a/dexcomparator/jackstyle.xml b/dexcomparator/jackstyle.xml
index 59286c8..76fa6e9 100644
--- a/dexcomparator/jackstyle.xml
+++ b/dexcomparator/jackstyle.xml
@@ -67,7 +67,7 @@
     <module name="ImportOrder">
       <!-- Checks for out of order import statements. -->
       <property name="severity" value="warning"/>
-      <property name="groups" value="com.google,*,java,javax"/>
+      <property name="groups" value="com.google,*,org,org.jf.dexlib.EncodedValue,*,java,javax"/>
       <!-- This ensures that static imports go first. -->
       <property name="option" value="top"/>
       <property name="tokens" value="STATIC_IMPORT, IMPORT"/>
diff --git a/dexcomparator/src/com/android/jack/DexAnnotationsComparator.java b/dexcomparator/src/com/android/jack/DexAnnotationsComparator.java
index df7b2a7..529db1f 100644
--- a/dexcomparator/src/com/android/jack/DexAnnotationsComparator.java
+++ b/dexcomparator/src/com/android/jack/DexAnnotationsComparator.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack;
 
 import com.android.jack.dx.rop.code.AccessFlags;
@@ -20,6 +36,7 @@
 import org.jf.dexlib.StringIdItem;
 import org.jf.dexlib.TypeIdItem;
 import org.jf.dexlib.TypeListItem;
+
 import org.jf.dexlib.EncodedValue.AnnotationEncodedSubValue;
 import org.jf.dexlib.EncodedValue.ArrayEncodedSubValue;
 import org.jf.dexlib.EncodedValue.ArrayEncodedValue;
diff --git a/dx/.checkstyle b/dx/.checkstyle
new file mode 100644
index 0000000..16b1f09
--- /dev/null
+++ b/dx/.checkstyle
@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<fileset-config file-format-version="1.2.0" simple-config="false" sync-formatter="false">
+  <local-check-config name="Jack Checkstyle" location="jackstyle.xml" type="project" description="">
+    <additional-data name="protect-config-file" value="true"/>
+  </local-check-config>
+  <fileset name="all" enabled="true" check-config-name="Jack Checkstyle" local="true">
+    <file-match-pattern match-pattern="." include-pattern="true"/>
+  </fileset>
+</fileset-config>
diff --git a/dx/.project b/dx/.project
index b9adec6..08f639b 100644
--- a/dx/.project
+++ b/dx/.project
@@ -10,8 +10,14 @@
 			<arguments>
 			</arguments>
 		</buildCommand>
+		<buildCommand>
+			<name>net.sf.eclipsecs.core.CheckstyleBuilder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
 	</buildSpec>
 	<natures>
 		<nature>org.eclipse.jdt.core.javanature</nature>
+		<nature>net.sf.eclipsecs.core.CheckstyleNature</nature>
 	</natures>
 </projectDescription>
diff --git a/dx/.settings/org.eclipse.jdt.core.prefs b/dx/.settings/org.eclipse.jdt.core.prefs
index 8000cd6..942db7e 100644
--- a/dx/.settings/org.eclipse.jdt.core.prefs
+++ b/dx/.settings/org.eclipse.jdt.core.prefs
@@ -9,3 +9,329 @@
 org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
 org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
 org.eclipse.jdt.core.compiler.source=1.6
+org.eclipse.jdt.core.formatter.align_type_members_on_columns=false
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_field=1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_field.count_dependent=1585|-1|1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_local_variable=1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_local_variable.count_dependent=1585|-1|1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_method=1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_method.count_dependent=1585|-1|1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_package=1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_package.count_dependent=1585|-1|1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_parameter=1040
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_parameter.count_dependent=1040|-1|1040
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_type=1585
+org.eclipse.jdt.core.formatter.alignment_for_annotations_on_type.count_dependent=1585|-1|1585
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression=16
+org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression.count_dependent=16|4|80
+org.eclipse.jdt.core.formatter.alignment_for_assignment=16
+org.eclipse.jdt.core.formatter.alignment_for_binary_expression=16
+org.eclipse.jdt.core.formatter.alignment_for_binary_expression.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_cascading_method_invocation_with_arguments=16
+org.eclipse.jdt.core.formatter.alignment_for_cascading_method_invocation_with_arguments.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_compact_if=16
+org.eclipse.jdt.core.formatter.alignment_for_conditional_expression=80
+org.eclipse.jdt.core.formatter.alignment_for_enum_constants=0
+org.eclipse.jdt.core.formatter.alignment_for_enum_constants.count_dependent=16|5|48
+org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16
+org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_field_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_for_statement=16
+org.eclipse.jdt.core.formatter.alignment_for_generic_type_arguments=16
+org.eclipse.jdt.core.formatter.alignment_for_generic_type_arguments.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_local_variable_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_method_declaration=0
+org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16
+org.eclipse.jdt.core.formatter.alignment_for_multiple_fields.count_dependent=16|-1|16
+org.eclipse.jdt.core.formatter.alignment_for_new_anonymous_class=20
+org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration.count_dependent=16|5|80
+org.eclipse.jdt.core.formatter.alignment_for_resources_in_try=80
+org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation=16
+org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation.count_dependent=16|4|48
+org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration.count_dependent=16|4|49
+org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration.count_dependent=16|4|48
+org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration.count_dependent=16|4|48
+org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration=16
+org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration.count_dependent=16|4|48
+org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch=16
+org.eclipse.jdt.core.formatter.blank_lines_after_imports=1
+org.eclipse.jdt.core.formatter.blank_lines_after_package=1
+org.eclipse.jdt.core.formatter.blank_lines_before_field=0
+org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration=0
+org.eclipse.jdt.core.formatter.blank_lines_before_imports=0
+org.eclipse.jdt.core.formatter.blank_lines_before_member_type=0
+org.eclipse.jdt.core.formatter.blank_lines_before_method=1
+org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk=1
+org.eclipse.jdt.core.formatter.blank_lines_before_package=0
+org.eclipse.jdt.core.formatter.blank_lines_between_import_groups=1
+org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations=2
+org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_array_initializer=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_block=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_block_in_case=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_enum_constant=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_method_declaration=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_switch=end_of_line
+org.eclipse.jdt.core.formatter.brace_position_for_type_declaration=end_of_line
+org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false
+org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false
+org.eclipse.jdt.core.formatter.comment.format_block_comments=true
+org.eclipse.jdt.core.formatter.comment.format_header=false
+org.eclipse.jdt.core.formatter.comment.format_html=true
+org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true
+org.eclipse.jdt.core.formatter.comment.format_line_comments=true
+org.eclipse.jdt.core.formatter.comment.format_source_code=true
+org.eclipse.jdt.core.formatter.comment.indent_parameter_description=false
+org.eclipse.jdt.core.formatter.comment.indent_root_tags=true
+org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags=insert
+org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter=do not insert
+org.eclipse.jdt.core.formatter.comment.line_length=100
+org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries=true
+org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries=true
+org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments=false
+org.eclipse.jdt.core.formatter.comment_new_line_at_start_of_html_paragraph=true
+org.eclipse.jdt.core.formatter.compact_else_if=true
+org.eclipse.jdt.core.formatter.continuation_indentation=2
+org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer=2
+org.eclipse.jdt.core.formatter.disabling_tag=@formatter\:off
+org.eclipse.jdt.core.formatter.enabling_tag=@formatter\:on
+org.eclipse.jdt.core.formatter.force_if_else_statement_brace=true
+org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line=false
+org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column=true
+org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header=true
+org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header=true
+org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header=true
+org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header=true
+org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases=true
+org.eclipse.jdt.core.formatter.indent_empty_lines=false
+org.eclipse.jdt.core.formatter.indent_statements_compare_to_block=true
+org.eclipse.jdt.core.formatter.indent_statements_compare_to_body=true
+org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases=true
+org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch=true
+org.eclipse.jdt.core.formatter.indentation.size=4
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field=insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable=insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method=insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package=insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type=insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_label=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing=insert
+org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration=insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block=insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration=insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body=do not insert
+org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter=insert
+org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_binary_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters=insert
+org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block=insert
+org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast=insert
+org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert=insert
+org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case=insert
+org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional=insert
+org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for=insert
+org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters=insert
+org.eclipse.jdt.core.formatter.insert_space_after_comment_prefix=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_ellipsis=insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional=insert
+org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard=do not insert
+org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for=insert
+org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources=insert
+org.eclipse.jdt.core.formatter.insert_space_after_unary_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter=insert
+org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_binary_operator=insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert=insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional=insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for=insert
+org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_ellipsis=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try=insert
+org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while=insert
+org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return=insert
+org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw=insert
+org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional=insert
+org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_semicolon=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources=do not insert
+org.eclipse.jdt.core.formatter.insert_space_before_unary_operator=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration=do not insert
+org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation=do not insert
+org.eclipse.jdt.core.formatter.join_lines_in_comments=true
+org.eclipse.jdt.core.formatter.join_wrapped_lines=true
+org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line=false
+org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line=false
+org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line=false
+org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line=false
+org.eclipse.jdt.core.formatter.lineSplit=100
+org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column=false
+org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column=false
+org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body=0
+org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve=3
+org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line=false
+org.eclipse.jdt.core.formatter.tabulation.char=space
+org.eclipse.jdt.core.formatter.tabulation.size=2
+org.eclipse.jdt.core.formatter.use_on_off_tags=false
+org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations=false
+org.eclipse.jdt.core.formatter.wrap_before_binary_operator=true
+org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch=true
+org.eclipse.jdt.core.formatter.wrap_comment_inline_tags=false
+org.eclipse.jdt.core.formatter.wrap_non_simple_local_variable_annotation=true
+org.eclipse.jdt.core.formatter.wrap_non_simple_member_annotation=true
+org.eclipse.jdt.core.formatter.wrap_non_simple_package_annotation=true
+org.eclipse.jdt.core.formatter.wrap_non_simple_parameter_annotation=false
+org.eclipse.jdt.core.formatter.wrap_non_simple_type_annotation=true
+org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested=true
+org.eclipse.jdt.core.formatter.wrap_prefer_two_fragments=false
diff --git a/dx/.settings/org.eclipse.jdt.ui.prefs b/dx/.settings/org.eclipse.jdt.ui.prefs
new file mode 100644
index 0000000..238808d
--- /dev/null
+++ b/dx/.settings/org.eclipse.jdt.ui.prefs
@@ -0,0 +1,7 @@
+eclipse.preferences.version=1
+formatter_profile=_Jack Format 100
+formatter_settings_version=13
+org.eclipse.jdt.ui.ignorelowercasenames=true
+org.eclipse.jdt.ui.importorder=com.google;android;antenna;antlr;ar;asposewobfuscated;asquare;atg;au;beaver;bibtex;bmsi;bsh;ccl;cern;ChartDirector;checkers;com;COM;common;contribs;corejava;cryptix;cybervillains;dalvik;danbikel;de;EDU;eg;eu;examples;fat;fit;fitlibrary;fmpp;freemarker;gnu;groovy;groovyjarjarantlr;groovyjarjarasm;hak;hep;ie;imageinfo;info;it;jal;Jama;japa;japacheckers;jas;jasmin;javancss;javanet;javassist;javazoom;java_cup;jcifs;jetty;JFlex;jj2000;jline;jp;JSci;jsr166y;junit;jxl;jxxload_help;kawa;kea;libcore;libsvm;lti;memetic;mt;mx4j;net;netscape;nl;nu;oauth;ognl;opennlp;oracle;org;penn2dg;pennconverter;pl;prefuse;proguard;repackage;scm;se;serp;simple;soot;sqlj;src;ssa;sun;sunlabs;tcl;testdata;testshell;testsuite;twitter4j;uk;ViolinStrings;weka;wet;winstone;woolfel;wowza;;java;javax;
+org.eclipse.jdt.ui.ondemandthreshold=99
+org.eclipse.jdt.ui.staticondemandthreshold=99
diff --git a/dx/jackstyle.xml b/dx/jackstyle.xml
new file mode 100644
index 0000000..59286c8
--- /dev/null
+++ b/dx/jackstyle.xml
@@ -0,0 +1,295 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE module PUBLIC
+    "-//Puppy Crawl//DTD Check Configuration 1.3//EN"
+    "http://www.puppycrawl.com/dtds/configuration_1_3.dtd">
+
+<!-- This is a checkstyle configuration file. For descriptions of
+what the following rules do, please see the checkstyle configuration
+page at http://checkstyle.sourceforge.net/config.html -->
+
+<!-- Checks with numbered comments refer to recommendations made
+by Joshua Bloch in his book Effective Java -->
+
+<module name="Checker">
+  <property name="charset" value="UTF-8"/>
+  <module name="FileTabCharacter">
+    <!-- Checks that there are no tab characters in the file.
+    -->
+  </module>
+
+  <module name="RegexpSingleline">
+    <!-- Checks that FIXME is not used in comments.  TODO is preferred.
+    -->
+    <property name="format" value="((//.*)|(\*.*))FIXME" />
+    <property name="message" value='TODO is preferred to FIXME.  e.g. "TODO(johndoe): Refactor when v2 is released."' />
+  </module>
+
+  <module name="RegexpSingleline">
+    <!-- Checks that TODOs are properly formatted.
+
+         The (?&lt;!TODO\(.{0,100}) makes the regex ignore any secondary TODO's on the line
+         so that things like //TODO(bob): remove this TODO on 1/1/2020 don't trigger a warning
+         because of the second TODO.  (The {0,100} is because java doesn't recoginize arbitrary
+         length look backs, but we know each java line should be < 100 chars.)
+    -->
+    <property name="format" value="((//.*)|(\*.*))(?&lt;!TODO\(.{0,100})(TODO[^(])|(TODO\([^)]*$)" />
+    <property name="message" value='All TODOs should be named.  e.g. "TODO(johndoe): Refactor when v2 is released."' />
+  </module>
+
+
+  <!-- All Java AST specific tests live under TreeWalker module. -->
+  <module name="TreeWalker">
+
+    <!--
+
+    IMPORT CHECKS
+
+    -->
+
+    <module name="RedundantImport">
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="AvoidStarImport">
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="UnusedImports">
+      <!-- DPL is a notable violator of this rule. -->
+      <property name="severity" value="error"/>
+      <!-- Imports used only in Javadoc are tolerated. -->
+      <property name="processJavadoc" value="true"/>
+      <message
+          key="import.unused"
+          value="Unused import: {0}." />
+    </module>
+
+    <module name="ImportOrder">
+      <!-- Checks for out of order import statements. -->
+      <property name="severity" value="warning"/>
+      <property name="groups" value="com.google,*,java,javax"/>
+      <!-- This ensures that static imports go first. -->
+      <property name="option" value="top"/>
+      <property name="tokens" value="STATIC_IMPORT, IMPORT"/>
+    </module>
+
+    <!--
+
+    NAMING CHECKS
+
+    -->
+
+    <!-- Item 38 - Adhere to generally accepted naming conventions -->
+
+    <module name="PackageName">
+      <!-- Validates identifiers for package names against the
+        supplied expression. -->
+      <!-- Here the default checkstyle rule restricts package name parts to
+        seven characters, this is not in line with common practice at Google.
+      -->
+      <property name="format" value="^[a-z]+(\.[a-z][a-z0-9]{1,})*$"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="TypeNameCheck">
+      <metadata name="altname" value="TypeName"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="StaticVariableNameCheck">
+      <!-- Validates static, non-final fields against the supplied
+      expression "^[a-z][a-zA-Z0-9]*?$". -->
+      <metadata name="altname" value="StaticVariableName"/>
+      <property name="applyToPublic" value="true"/>
+      <property name="applyToProtected" value="true"/>
+      <property name="applyToPackage" value="true"/>
+      <property name="applyToPrivate" value="true"/>
+      <property name="format" value="^[a-z][a-zA-Z0-9]*?$"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="MemberNameCheck">
+      <!-- Validates non-static members against the supplied expression. -->
+      <metadata name="altname" value="MemberName"/>
+      <property name="applyToPublic" value="true"/>
+      <property name="applyToProtected" value="true"/>
+      <property name="applyToPackage" value="true"/>
+      <property name="applyToPrivate" value="true"/>
+      <property name="format" value="^[a-z][a-zA-Z0-9]*?$"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="MethodNameCheck">
+      <!-- Validates identifiers for method names. -->
+      <metadata name="altname" value="MethodName"/>
+      <property name="format" value="^[a-z][a-zA-Z0-9]*([a-zA-Z0-9]+)*$"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="ParameterName">
+      <!-- Validates identifiers for method parameters against the
+        expression "^[a-z][a-zA-Z0-9]*$". -->
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="LocalFinalVariableName">
+      <!-- Validates identifiers for local final variables against the
+        expression "^[a-z][a-zA-Z0-9]*$". -->
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="LocalVariableName">
+      <!-- Validates identifiers for local variables against the
+        expression "^[a-z][a-zA-Z0-9]*$". -->
+      <property name="severity" value="warning"/>
+    </module>
+
+
+    <!--
+
+    LENGTH and CODING CHECKS
+
+    -->
+
+    <module name="LineLength">
+      <!-- Checks if a line is too long. -->
+      <property name="max" value="${com.puppycrawl.tools.checkstyle.checks.sizes.LineLength.max}" default="100"/>
+      <property name="severity" value="error"/>
+
+      <!--
+        The default ignore pattern exempts the following elements:
+          - import statements
+          - long URLs inside comments
+      -->
+
+      <property name="ignorePattern"
+          value="${com.puppycrawl.tools.checkstyle.checks.sizes.LineLength.ignorePattern}"
+          default="^(package .*;\s*)|(import .*;\s*)|( *\* *https?://.*)|(\s*@[\w\.\$]+::\w+(?:\([^\(]*\)|\(\)\(\))?[,;]?)|(\s+\* \{@(link|see) [^\s][^\}]*\}[\.,;]?)$"/>
+    </module>
+
+    <module name="LeftCurly">
+      <!-- Checks for placement of the left curly brace ('{'). -->
+      <property name="severity" value="warning"/>
+    </module>
+
+    <module name="RightCurly">
+      <!-- Checks right curlies on CATCH, ELSE, and TRY blocks are on
+      the same line. e.g., the following example is fine:
+      <pre>
+        if {
+          ...
+        } else
+      </pre>
+      -->
+      <!-- This next example is not fine:
+      <pre>
+        if {
+          ...
+        }
+        else
+      </pre>
+      -->
+      <property name="option" value="same"/>
+      <property name="severity" value="warning"/>
+    </module>
+
+    <!-- Checks for braces around if and else blocks -->
+    <module name="NeedBraces">
+      <property name="severity" value="warning"/>
+      <property name="tokens" value="LITERAL_IF, LITERAL_ELSE, LITERAL_FOR, LITERAL_WHILE, LITERAL_DO"/>
+    </module>
+
+    <module name="UpperEll">
+      <!-- Checks that long constants are defined with an upper ell.-->
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="FallThrough">
+      <!-- Warn about falling through to the next case statement.  Similar to
+      javac -Xlint:fallthrough, but the check is suppressed if there is a single-line comment
+      on the last non-blank line preceding the fallen-into case.
+      -->
+      <property name="reliefPattern"
+       value=".*"/>
+      <property name="severity" value="error"/>
+    </module>
+
+
+    <!--
+
+    MODIFIERS CHECKS
+
+    -->
+
+    <module name="ModifierOrder">
+      <!-- Warn if modifier order is inconsistent with JLS3 8.1.1, 8.3.1, and
+           8.4.3.  The prescribed order is:
+           public, protected, private, abstract, static, final, transient, volatile,
+           synchronized, native, strictfp
+        -->
+    </module>
+
+
+    <!--
+
+    WHITESPACE CHECKS
+
+    -->
+
+    <module name="WhitespaceAround">
+      <!-- Checks that various tokens are surrounded by whitespace.
+           This includes most binary operators and keywords followed
+           by regular or curly braces.
+      -->
+      <property name="tokens" value="ASSIGN, BAND, BAND_ASSIGN, BOR,
+        BOR_ASSIGN, BSR, BSR_ASSIGN, BXOR, BXOR_ASSIGN, COLON, DIV, DIV_ASSIGN,
+        EQUAL, GE, GT, LAND, LE, LITERAL_CATCH, LITERAL_DO, LITERAL_ELSE,
+        LITERAL_FINALLY, LITERAL_FOR, LITERAL_IF, LITERAL_RETURN,
+        LITERAL_SYNCHRONIZED, LITERAL_TRY, LITERAL_WHILE, LOR, LT, MINUS,
+        MINUS_ASSIGN, MOD, MOD_ASSIGN, NOT_EQUAL, PLUS, PLUS_ASSIGN, QUESTION,
+        SL, SL_ASSIGN, SR_ASSIGN, STAR, STAR_ASSIGN"/>
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="WhitespaceAfter">
+      <!-- Checks that commas, semicolons and typecasts are followed by
+           whitespace.
+      -->
+      <property name="tokens" value="COMMA, SEMI, TYPECAST"/>
+    </module>
+
+    <module name="NoWhitespaceAfter">
+      <!-- Checks that there is no whitespace after various unary operators.
+           Linebreaks are allowed.
+      -->
+      <property name="tokens" value="BNOT, DEC, DOT, INC, LNOT, UNARY_MINUS,
+        UNARY_PLUS"/>
+      <property name="allowLineBreaks" value="true"/>
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="NoWhitespaceBefore">
+      <!-- Checks that there is no whitespace before various unary operators.
+           Linebreaks are allowed.
+      -->
+      <property name="tokens" value="SEMI, DOT, POST_DEC, POST_INC"/>
+      <property name="allowLineBreaks" value="true"/>
+      <property name="severity" value="error"/>
+    </module>
+
+    <module name="ParenPad">
+      <!-- Checks that there is no whitespace before close parens or after
+           open parens.
+      -->
+      <property name="severity" value="warning"/>
+    </module>
+
+    <!--
+
+    MISC CHECKS
+
+    -->
+
+  </module>
+</module>
+
diff --git a/dx/src/com/android/jack/dx/Version.java b/dx/src/com/android/jack/dx/Version.java
index 1152dd8..2158cae 100644
--- a/dx/src/com/android/jack/dx/Version.java
+++ b/dx/src/com/android/jack/dx/Version.java
@@ -20,6 +20,6 @@
  * Version number for dx.
  */
 public class Version {
-    /** {@code non-null;} version string */
-    public static final String VERSION = "1.7";
+  /** {@code non-null;} version string */
+  public static final String VERSION = "1.7";
 }
diff --git a/dx/src/com/android/jack/dx/dex/DexFormat.java b/dx/src/com/android/jack/dx/dex/DexFormat.java
index bf526bc..19da4f6 100644
--- a/dx/src/com/android/jack/dx/dex/DexFormat.java
+++ b/dx/src/com/android/jack/dx/dex/DexFormat.java
@@ -21,78 +21,78 @@
  * files, and helper methods for same.
  */
 public final class DexFormat {
-    private DexFormat() {}
+  private DexFormat() {}
 
-    /**
-     * API level to target in order to produce the most modern file
-     * format
-     */
-    public static final int API_CURRENT = 14;
+  /**
+   * API level to target in order to produce the most modern file
+   * format
+   */
+  public static final int API_CURRENT = 14;
 
-    /** API level to target in order to suppress extended opcode usage */
-    public static final int API_NO_EXTENDED_OPCODES = 13;
+  /** API level to target in order to suppress extended opcode usage */
+  public static final int API_NO_EXTENDED_OPCODES = 13;
 
-    /**
-     * file name of the primary {@code .dex} file inside an
-     * application or library {@code .jar} file
-     */
-    public static final String DEX_IN_JAR_NAME = "classes.dex";
+  /**
+   * file name of the primary {@code .dex} file inside an
+   * application or library {@code .jar} file
+   */
+  public static final String DEX_IN_JAR_NAME = "classes.dex";
 
-    /** common prefix for all dex file "magic numbers" */
-    public static final String MAGIC_PREFIX = "dex\n";
+  /** common prefix for all dex file "magic numbers" */
+  public static final String MAGIC_PREFIX = "dex\n";
 
-    /** common suffix for all dex file "magic numbers" */
-    public static final String MAGIC_SUFFIX = "\0";
+  /** common suffix for all dex file "magic numbers" */
+  public static final String MAGIC_SUFFIX = "\0";
 
-    /** dex file version number for the current format variant */
-    public static final String VERSION_CURRENT = "036";
+  /** dex file version number for the current format variant */
+  public static final String VERSION_CURRENT = "036";
 
-    /** dex file version number for API level 13 and earlier */
-    public static final String VERSION_FOR_API_13 = "035";
+  /** dex file version number for API level 13 and earlier */
+  public static final String VERSION_FOR_API_13 = "035";
 
-    /**
-     * value used to indicate endianness of file contents
-     */
-    public static final int ENDIAN_TAG = 0x12345678;
+  /**
+   * value used to indicate endianness of file contents
+   */
+  public static final int ENDIAN_TAG = 0x12345678;
 
-    /**
-     * Returns the API level corresponding to the given magic number,
-     * or {@code -1} if the given array is not a well-formed dex file
-     * magic number.
-     */
-    public static int magicToApi(byte[] magic) {
-        if (magic.length != 8) {
-            return -1;
-        }
-
-        if ((magic[0] != 'd') || (magic[1] != 'e') || (magic[2] != 'x') || (magic[3] != '\n') ||
-                (magic[7] != '\0')) {
-            return -1;
-        }
-
-        String version = "" + ((char) magic[4]) + ((char) magic[5]) +((char) magic[6]);
-
-        if (version.equals(VERSION_CURRENT)) {
-            return API_CURRENT;
-        } else if (version.equals(VERSION_FOR_API_13)) {
-            return 13;
-        }
-
-        return -1;
+  /**
+   * Returns the API level corresponding to the given magic number,
+   * or {@code -1} if the given array is not a well-formed dex file
+   * magic number.
+   */
+  public static int magicToApi(byte[] magic) {
+    if (magic.length != 8) {
+      return -1;
     }
 
-    /**
-     * Returns the magic number corresponding to the given target API level.
-     */
-    public static String apiToMagic(int targetApiLevel) {
-        String version;
-
-        if (targetApiLevel >= API_CURRENT) {
-            version = VERSION_CURRENT;
-        } else {
-            version = VERSION_FOR_API_13;
-        }
-
-        return MAGIC_PREFIX + version + MAGIC_SUFFIX;
+    if ((magic[0] != 'd') || (magic[1] != 'e') || (magic[2] != 'x') || (magic[3] != '\n')
+        || (magic[7] != '\0')) {
+      return -1;
     }
+
+    String version = "" + ((char) magic[4]) + ((char) magic[5]) + ((char) magic[6]);
+
+    if (version.equals(VERSION_CURRENT)) {
+      return API_CURRENT;
+    } else if (version.equals(VERSION_FOR_API_13)) {
+      return 13;
+    }
+
+    return -1;
+  }
+
+  /**
+   * Returns the magic number corresponding to the given target API level.
+   */
+  public static String apiToMagic(int targetApiLevel) {
+    String version;
+
+    if (targetApiLevel >= API_CURRENT) {
+      version = VERSION_CURRENT;
+    } else {
+      version = VERSION_FOR_API_13;
+    }
+
+    return MAGIC_PREFIX + version + MAGIC_SUFFIX;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/DexOptions.java b/dx/src/com/android/jack/dx/dex/DexOptions.java
index 81cf288..2fda5c1 100644
--- a/dx/src/com/android/jack/dx/dex/DexOptions.java
+++ b/dx/src/com/android/jack/dx/dex/DexOptions.java
@@ -20,16 +20,16 @@
  * Container for options used to control details of dex file generation.
  */
 public class DexOptions {
-    /** target API level */
-    public int targetApiLevel = DexFormat.API_NO_EXTENDED_OPCODES;
+  /** target API level */
+  public int targetApiLevel = DexFormat.API_NO_EXTENDED_OPCODES;
 
-    /** force generation of jumbo opcodes */
-    public boolean forceJumbo = false;
+  /** force generation of jumbo opcodes */
+  public boolean forceJumbo = false;
 
-    /**
-     * Gets the dex file magic number corresponding to this instance.
-     */
-    public String getMagic() {
-        return DexFormat.apiToMagic(targetApiLevel);
-    }
+  /**
+   * Gets the dex file magic number corresponding to this instance.
+   */
+  public String getMagic() {
+    return DexFormat.apiToMagic(targetApiLevel);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/SizeOf.java b/dx/src/com/android/jack/dx/dex/SizeOf.java
index ae118d0..d9441ab 100644
--- a/dx/src/com/android/jack/dx/dex/SizeOf.java
+++ b/dx/src/com/android/jack/dx/dex/SizeOf.java
@@ -16,95 +16,98 @@
 
 package com.android.jack.dx.dex;
 
+/**
+ * TODO(jack team)
+ */
 public final class SizeOf {
-    private SizeOf() {}
+  private SizeOf() {}
 
-    public static final int UBYTE = 1;
-    public static final int USHORT = 2;
-    public static final int UINT = 4;
+  public static final int UBYTE = 1;
+  public static final int USHORT = 2;
+  public static final int UINT = 4;
 
-    public static final int SIGNATURE = UBYTE * 20;
+  public static final int SIGNATURE = UBYTE * 20;
 
-    /**
-     * magic ubyte[8]
-     * checksum uint
-     * signature ubyte[20]
-     * file_size uint
-     * header_size uint
-     * endian_tag uint
-     * link_size uint
-     * link_off uint
-     * map_off uint
-     * string_ids_size uint
-     * string_ids_off uint
-     * type_ids_size uint
-     * type_ids_off uint
-     * proto_ids_size uint
-     * proto_ids_off uint
-     * field_ids_size uint
-     * field_ids_off uint
-     * method_ids_size uint
-     * method_ids_off uint
-     * class_defs_size uint
-     * class_defs_off uint
-     * data_size uint
-     * data_off uint
-     */
-    public static final int HEADER_ITEM = (8 * UBYTE) + UINT + SIGNATURE + (20 * UINT); // 0x70
+  /**
+   * magic ubyte[8]
+   * checksum uint
+   * signature ubyte[20]
+   * file_size uint
+   * header_size uint
+   * endian_tag uint
+   * link_size uint
+   * link_off uint
+   * map_off uint
+   * string_ids_size uint
+   * string_ids_off uint
+   * type_ids_size uint
+   * type_ids_off uint
+   * proto_ids_size uint
+   * proto_ids_off uint
+   * field_ids_size uint
+   * field_ids_off uint
+   * method_ids_size uint
+   * method_ids_off uint
+   * class_defs_size uint
+   * class_defs_off uint
+   * data_size uint
+   * data_off uint
+   */
+  public static final int HEADER_ITEM = (8 * UBYTE) + UINT + SIGNATURE + (20 * UINT); // 0x70
 
-    /**
-     * string_data_off uint
-     */
-    public static final int STRING_ID_ITEM = UINT;
+  /**
+   * string_data_off uint
+   */
+  public static final int STRING_ID_ITEM = UINT;
 
-    /**
-     * descriptor_idx uint
-     */
-    public static final int TYPE_ID_ITEM = UINT;
+  /**
+   * descriptor_idx uint
+   */
+  public static final int TYPE_ID_ITEM = UINT;
 
-    /**
-     * type_idx ushort
-     */
-    public static final int TYPE_ITEM = USHORT;
+  /**
+   * type_idx ushort
+   */
+  public static final int TYPE_ITEM = USHORT;
 
-    /**
-     * shorty_idx uint
-     * return_type_idx uint
-     * return_type_idx uint
-     */
-    public static final int PROTO_ID_ITEM = UINT + UINT + UINT;
+  /**
+   * shorty_idx uint
+   * return_type_idx uint
+   * return_type_idx uint
+   */
+  public static final int PROTO_ID_ITEM = UINT + UINT + UINT;
 
-    /**
-     * class_idx ushort
-     * type_idx/proto_idx ushort
-     * name_idx uint
-     */
-    public static final int MEMBER_ID_ITEM = USHORT + USHORT + UINT;
+  /**
+   * class_idx ushort
+   * type_idx/proto_idx ushort
+   * name_idx uint
+   */
+  public static final int MEMBER_ID_ITEM = USHORT + USHORT + UINT;
 
-    /**
-     * class_idx uint
-     * access_flags uint
-     * superclass_idx uint
-     * interfaces_off uint
-     * source_file_idx uint
-     * annotations_off uint
-     * class_data_off uint
-     * static_values_off uint
-     */
-    public static final int CLASS_DEF_ITEM = 8 * UINT;
+  /**
+   * class_idx uint
+   * access_flags uint
+   * superclass_idx uint
+   * interfaces_off uint
+   * source_file_idx uint
+   * annotations_off uint
+   * class_data_off uint
+   * static_values_off uint
+   */
+  public static final int CLASS_DEF_ITEM = 8 * UINT;
 
-    /**
-     * type ushort
-     * unused ushort
-     * size uint
-     * offset uint
-     */
-    public static final int MAP_ITEM = USHORT + USHORT + UINT + UINT;
+  /**
+   * type ushort
+   * unused ushort
+   * size uint
+   * offset uint
+   */
+  public static final int MAP_ITEM = USHORT + USHORT + UINT + UINT;
 
-    /**
-     * start_addr uint
-     * insn_count ushort
-     * handler_off ushort
-     */
-    public static final int TRY_ITEM = UINT + USHORT + USHORT;
+  /**
+   * start_addr uint
+   * insn_count ushort
+   * handler_off ushort
+   */
+  public static final int TRY_ITEM = UINT + USHORT + USHORT;
 }
diff --git a/dx/src/com/android/jack/dx/dex/TableOfContents.java b/dx/src/com/android/jack/dx/dex/TableOfContents.java
index 11b7bfe..40f6e98 100644
--- a/dx/src/com/android/jack/dx/dex/TableOfContents.java
+++ b/dx/src/com/android/jack/dx/dex/TableOfContents.java
@@ -28,212 +28,230 @@
  */
 public final class TableOfContents {
 
-    /*
-     * TODO: factor out ID constants.
-     */
+  /*
+   * TODO(dx team): factor out ID constants.
+   */
 
-    public final Section header = new Section(0x0000);
-    public final Section stringIds = new Section(0x0001);
-    public final Section typeIds = new Section(0x0002);
-    public final Section protoIds = new Section(0x0003);
-    public final Section fieldIds = new Section(0x0004);
-    public final Section methodIds = new Section(0x0005);
-    public final Section classDefs = new Section(0x0006);
-    public final Section mapList = new Section(0x1000);
-    public final Section typeLists = new Section(0x1001);
-    public final Section annotationSetRefLists = new Section(0x1002);
-    public final Section annotationSets = new Section(0x1003);
-    public final Section classDatas = new Section(0x2000);
-    public final Section codes = new Section(0x2001);
-    public final Section stringDatas = new Section(0x2002);
-    public final Section debugInfos = new Section(0x2003);
-    public final Section annotations = new Section(0x2004);
-    public final Section encodedArrays = new Section(0x2005);
-    public final Section annotationsDirectories = new Section(0x2006);
-    public final Section[] sections = {
-            header, stringIds, typeIds, protoIds, fieldIds, methodIds, classDefs, mapList,
-            typeLists, annotationSetRefLists, annotationSets, classDatas, codes, stringDatas,
-            debugInfos, annotations, encodedArrays, annotationsDirectories
-    };
+  public final Section header = new Section(0x0000);
+  public final Section stringIds = new Section(0x0001);
+  public final Section typeIds = new Section(0x0002);
+  public final Section protoIds = new Section(0x0003);
+  public final Section fieldIds = new Section(0x0004);
+  public final Section methodIds = new Section(0x0005);
+  public final Section classDefs = new Section(0x0006);
+  public final Section mapList = new Section(0x1000);
+  public final Section typeLists = new Section(0x1001);
+  public final Section annotationSetRefLists = new Section(0x1002);
+  public final Section annotationSets = new Section(0x1003);
+  public final Section classDatas = new Section(0x2000);
+  public final Section codes = new Section(0x2001);
+  public final Section stringDatas = new Section(0x2002);
+  public final Section debugInfos = new Section(0x2003);
+  public final Section annotations = new Section(0x2004);
+  public final Section encodedArrays = new Section(0x2005);
+  public final Section annotationsDirectories = new Section(0x2006);
+  public final Section[] sections = {header,
+      stringIds,
+      typeIds,
+      protoIds,
+      fieldIds,
+      methodIds,
+      classDefs,
+      mapList,
+      typeLists,
+      annotationSetRefLists,
+      annotationSets,
+      classDatas,
+      codes,
+      stringDatas,
+      debugInfos,
+      annotations,
+      encodedArrays,
+      annotationsDirectories};
 
-    public int checksum;
-    public byte[] signature;
-    public int fileSize;
-    public int linkSize;
-    public int linkOff;
-    public int dataSize;
-    public int dataOff;
+  public int checksum;
+  public byte[] signature;
+  public int fileSize;
+  public int linkSize;
+  public int linkOff;
+  public int dataSize;
+  public int dataOff;
 
-    public TableOfContents() {
-        signature = new byte[20];
+  public TableOfContents() {
+    signature = new byte[20];
+  }
+
+  public void readFrom(DexBuffer buffer) throws IOException {
+    readHeader(buffer.open(0));
+    readMap(buffer.open(mapList.off));
+    computeSizesFromOffsets();
+  }
+
+  private void readHeader(DexBuffer.Section headerIn) throws UnsupportedEncodingException {
+    byte[] magic = headerIn.readByteArray(8);
+    int apiTarget = DexFormat.magicToApi(magic);
+
+    if (apiTarget != DexFormat.API_NO_EXTENDED_OPCODES) {
+      throw new DexException("Unexpected magic: " + Arrays.toString(magic));
     }
 
-    public void readFrom(DexBuffer buffer) throws IOException {
-        readHeader(buffer.open(0));
-        readMap(buffer.open(mapList.off));
-        computeSizesFromOffsets();
+    checksum = headerIn.readInt();
+    signature = headerIn.readByteArray(20);
+    fileSize = headerIn.readInt();
+    int headerSize = headerIn.readInt();
+    if (headerSize != SizeOf.HEADER_ITEM) {
+      throw new DexException("Unexpected header: 0x" + Integer.toHexString(headerSize));
+    }
+    int endianTag = headerIn.readInt();
+    if (endianTag != DexFormat.ENDIAN_TAG) {
+      throw new DexException("Unexpected endian tag: 0x" + Integer.toHexString(endianTag));
+    }
+    linkSize = headerIn.readInt();
+    linkOff = headerIn.readInt();
+    mapList.off = headerIn.readInt();
+    if (mapList.off == 0) {
+      throw new DexException("Cannot merge dex files that do not contain a map");
+    }
+    stringIds.size = headerIn.readInt();
+    stringIds.off = headerIn.readInt();
+    typeIds.size = headerIn.readInt();
+    typeIds.off = headerIn.readInt();
+    protoIds.size = headerIn.readInt();
+    protoIds.off = headerIn.readInt();
+    fieldIds.size = headerIn.readInt();
+    fieldIds.off = headerIn.readInt();
+    methodIds.size = headerIn.readInt();
+    methodIds.off = headerIn.readInt();
+    classDefs.size = headerIn.readInt();
+    classDefs.off = headerIn.readInt();
+    dataSize = headerIn.readInt();
+    dataOff = headerIn.readInt();
+  }
+
+  private void readMap(DexBuffer.Section in) throws IOException {
+    int mapSize = in.readInt();
+    Section previous = null;
+    for (int i = 0; i < mapSize; i++) {
+      short type = in.readShort();
+      in.readShort(); // unused
+      Section section = getSection(type);
+      int size = in.readInt();
+      int offset = in.readInt();
+
+      if ((section.size != 0 && section.size != size)
+          || (section.off != -1 && section.off != offset)) {
+        throw new DexException("Unexpected map value for 0x" + Integer.toHexString(type));
+      }
+
+      section.size = size;
+      section.off = offset;
+
+      if (previous != null && previous.off > section.off) {
+        throw new DexException("Map is unsorted at " + previous + ", " + section);
+      }
+
+      previous = section;
+    }
+    Arrays.sort(sections);
+  }
+
+  public void computeSizesFromOffsets() {
+    int end = dataOff + dataSize;
+    for (int i = sections.length - 1; i >= 0; i--) {
+      Section section = sections[i];
+      if (section.off == -1) {
+        continue;
+      }
+      if (section.off > end) {
+        throw new DexException("Map is unsorted at " + section);
+      }
+      section.byteCount = end - section.off;
+      end = section.off;
+    }
+  }
+
+  private Section getSection(short type) {
+    for (Section section : sections) {
+      if (section.type == type) {
+        return section;
+      }
+    }
+    throw new IllegalArgumentException("No such map item: " + type);
+  }
+
+  public void writeHeader(DexBuffer.Section out) throws IOException {
+    out.write(DexFormat.apiToMagic(DexFormat.API_NO_EXTENDED_OPCODES).getBytes("UTF-8"));
+    out.writeInt(checksum);
+    out.write(signature);
+    out.writeInt(fileSize);
+    out.writeInt(SizeOf.HEADER_ITEM);
+    out.writeInt(DexFormat.ENDIAN_TAG);
+    out.writeInt(linkSize);
+    out.writeInt(linkOff);
+    out.writeInt(mapList.off);
+    out.writeInt(stringIds.size);
+    out.writeInt(stringIds.off);
+    out.writeInt(typeIds.size);
+    out.writeInt(typeIds.off);
+    out.writeInt(protoIds.size);
+    out.writeInt(protoIds.off);
+    out.writeInt(fieldIds.size);
+    out.writeInt(fieldIds.off);
+    out.writeInt(methodIds.size);
+    out.writeInt(methodIds.off);
+    out.writeInt(classDefs.size);
+    out.writeInt(classDefs.off);
+    out.writeInt(dataSize);
+    out.writeInt(dataOff);
+  }
+
+  public void writeMap(DexBuffer.Section out) throws IOException {
+    int count = 0;
+    for (Section section : sections) {
+      if (section.exists()) {
+        count++;
+      }
     }
 
-    private void readHeader(DexBuffer.Section headerIn) throws UnsupportedEncodingException {
-        byte[] magic = headerIn.readByteArray(8);
-        int apiTarget = DexFormat.magicToApi(magic);
+    out.writeInt(count);
+    for (Section section : sections) {
+      if (section.exists()) {
+        out.writeShort(section.type);
+        out.writeShort((short) 0);
+        out.writeInt(section.size);
+        out.writeInt(section.off);
+      }
+    }
+  }
 
-        if (apiTarget != DexFormat.API_NO_EXTENDED_OPCODES) {
-            throw new DexException("Unexpected magic: " + Arrays.toString(magic));
-        }
+  /**
+   * TODO(jack team)
+   */
+  public static class Section implements Comparable<Section> {
+    public final short type;
+    public int size = 0;
+    public int off = -1;
+    public int byteCount = 0;
 
-        checksum = headerIn.readInt();
-        signature = headerIn.readByteArray(20);
-        fileSize = headerIn.readInt();
-        int headerSize = headerIn.readInt();
-        if (headerSize != SizeOf.HEADER_ITEM) {
-            throw new DexException("Unexpected header: 0x" + Integer.toHexString(headerSize));
-        }
-        int endianTag = headerIn.readInt();
-        if (endianTag != DexFormat.ENDIAN_TAG) {
-            throw new DexException("Unexpected endian tag: 0x" + Integer.toHexString(endianTag));
-        }
-        linkSize = headerIn.readInt();
-        linkOff = headerIn.readInt();
-        mapList.off = headerIn.readInt();
-        if (mapList.off == 0) {
-            throw new DexException("Cannot merge dex files that do not contain a map");
-        }
-        stringIds.size = headerIn.readInt();
-        stringIds.off = headerIn.readInt();
-        typeIds.size = headerIn.readInt();
-        typeIds.off = headerIn.readInt();
-        protoIds.size = headerIn.readInt();
-        protoIds.off = headerIn.readInt();
-        fieldIds.size = headerIn.readInt();
-        fieldIds.off = headerIn.readInt();
-        methodIds.size = headerIn.readInt();
-        methodIds.off = headerIn.readInt();
-        classDefs.size = headerIn.readInt();
-        classDefs.off = headerIn.readInt();
-        dataSize = headerIn.readInt();
-        dataOff = headerIn.readInt();
+    public Section(int type) {
+      this.type = (short) type;
     }
 
-    private void readMap(DexBuffer.Section in) throws IOException {
-        int mapSize = in.readInt();
-        Section previous = null;
-        for (int i = 0; i < mapSize; i++) {
-            short type = in.readShort();
-            in.readShort(); // unused
-            Section section = getSection(type);
-            int size = in.readInt();
-            int offset = in.readInt();
-
-            if ((section.size != 0 && section.size != size)
-                    || (section.off != -1 && section.off != offset)) {
-                throw new DexException("Unexpected map value for 0x" + Integer.toHexString(type));
-            }
-
-            section.size = size;
-            section.off = offset;
-
-            if (previous != null && previous.off > section.off) {
-                throw new DexException("Map is unsorted at " + previous + ", " + section);
-            }
-
-            previous = section;
-        }
-        Arrays.sort(sections);
+    public boolean exists() {
+      return size > 0;
     }
 
-    public void computeSizesFromOffsets() {
-        int end = dataOff + dataSize;
-        for (int i = sections.length - 1; i >= 0; i--) {
-            Section section = sections[i];
-            if (section.off == -1) {
-                continue;
-            }
-            if (section.off > end) {
-                throw new DexException("Map is unsorted at " + section);
-            }
-            section.byteCount = end - section.off;
-            end = section.off;
-        }
+    @Override
+    public int compareTo(Section section) {
+      if (off != section.off) {
+        return off < section.off ? -1 : 1;
+      }
+      return 0;
     }
 
-    private Section getSection(short type) {
-        for (Section section : sections) {
-            if (section.type == type) {
-                return section;
-            }
-        }
-        throw new IllegalArgumentException("No such map item: " + type);
+    @Override
+    public String toString() {
+      return String.format("Section[type=%#x,off=%#x,size=%#x]", type, off, size);
     }
-
-    public void writeHeader(DexBuffer.Section out) throws IOException {
-        out.write(DexFormat.apiToMagic(DexFormat.API_NO_EXTENDED_OPCODES).getBytes("UTF-8"));
-        out.writeInt(checksum);
-        out.write(signature);
-        out.writeInt(fileSize);
-        out.writeInt(SizeOf.HEADER_ITEM);
-        out.writeInt(DexFormat.ENDIAN_TAG);
-        out.writeInt(linkSize);
-        out.writeInt(linkOff);
-        out.writeInt(mapList.off);
-        out.writeInt(stringIds.size);
-        out.writeInt(stringIds.off);
-        out.writeInt(typeIds.size);
-        out.writeInt(typeIds.off);
-        out.writeInt(protoIds.size);
-        out.writeInt(protoIds.off);
-        out.writeInt(fieldIds.size);
-        out.writeInt(fieldIds.off);
-        out.writeInt(methodIds.size);
-        out.writeInt(methodIds.off);
-        out.writeInt(classDefs.size);
-        out.writeInt(classDefs.off);
-        out.writeInt(dataSize);
-        out.writeInt(dataOff);
-    }
-
-    public void writeMap(DexBuffer.Section out) throws IOException {
-        int count = 0;
-        for (Section section : sections) {
-            if (section.exists()) {
-                count++;
-            }
-        }
-
-        out.writeInt(count);
-        for (Section section : sections) {
-            if (section.exists()) {
-                out.writeShort(section.type);
-                out.writeShort((short) 0);
-                out.writeInt(section.size);
-                out.writeInt(section.off);
-            }
-        }
-    }
-
-    public static class Section implements Comparable<Section> {
-        public final short type;
-        public int size = 0;
-        public int off = -1;
-        public int byteCount = 0;
-
-        public Section(int type) {
-            this.type = (short) type;
-        }
-
-        public boolean exists() {
-            return size > 0;
-        }
-
-        public int compareTo(Section section) {
-            if (off != section.off) {
-                return off < section.off ? -1 : 1;
-            }
-            return 0;
-        }
-
-        @Override public String toString() {
-            return String.format("Section[type=%#x,off=%#x,size=%#x]", type, off, size);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/ArrayData.java b/dx/src/com/android/jack/dx/dex/code/ArrayData.java
index f8b7684..81f7ac0 100644
--- a/dx/src/com/android/jack/dx/dex/code/ArrayData.java
+++ b/dx/src/com/android/jack/dx/dex/code/ArrayData.java
@@ -19,8 +19,10 @@
 import com.android.jack.dx.io.Opcodes;
 import com.android.jack.dx.rop.code.RegisterSpecList;
 import com.android.jack.dx.rop.code.SourcePosition;
-import com.android.jack.dx.rop.cst.*;
-import com.android.jack.dx.rop.type.Type;
+import com.android.jack.dx.rop.cst.Constant;
+import com.android.jack.dx.rop.cst.CstLiteral32;
+import com.android.jack.dx.rop.cst.CstLiteral64;
+import com.android.jack.dx.rop.cst.CstType;
 import com.android.jack.dx.util.AnnotatedOutput;
 import com.android.jack.dx.util.Hex;
 
@@ -30,171 +32,166 @@
  * Pseudo-instruction which holds fill array data.
  */
 public final class ArrayData extends VariableSizeInsn {
-    /**
-     * {@code non-null;} address representing the instruction that uses this
-     * instance
-     */
-    private final CodeAddress user;
+  /**
+   * {@code non-null;} address representing the instruction that uses this
+   * instance
+   */
+  private final CodeAddress user;
 
-    /** {@code non-null;} initial values to be filled into an array */
-    private final ArrayList<Constant> values;
+  /** {@code non-null;} initial values to be filled into an array */
+  private final ArrayList<Constant> values;
 
-    /** non-null: type of constant that initializes the array */
-    private final Constant arrayType;
+  /** non-null: type of constant that initializes the array */
+  private final Constant arrayType;
 
-    /** Width of the init value element */
-    private final int elemWidth;
+  /** Width of the init value element */
+  private final int elemWidth;
 
-    /** Length of the init list */
-    private final int initLength;
+  /** Length of the init list */
+  private final int initLength;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param user {@code non-null;} address representing the instruction that
-     * uses this instance
-     * @param values {@code non-null;} initial values to be filled into an array
-     */
-    public ArrayData(SourcePosition position, CodeAddress user,
-                     ArrayList<Constant> values,
-                     Constant arrayType) {
-        super(position, RegisterSpecList.EMPTY);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param user {@code non-null;} address representing the instruction that
+   * uses this instance
+   * @param values {@code non-null;} initial values to be filled into an array
+   */
+  public ArrayData(SourcePosition position, CodeAddress user, ArrayList<Constant> values,
+      Constant arrayType) {
+    super(position, RegisterSpecList.EMPTY);
 
-        if (user == null) {
-            throw new NullPointerException("user == null");
-        }
-
-        if (values == null) {
-            throw new NullPointerException("values == null");
-        }
-
-        int sz = values.size();
-
-        if (sz <= 0) {
-            throw new IllegalArgumentException("Illegal number of init values");
-        }
-
-        this.arrayType = arrayType;
-
-        if (arrayType == CstType.BYTE_ARRAY ||
-                arrayType == CstType.BOOLEAN_ARRAY) {
-            elemWidth = 1;
-        } else if (arrayType == CstType.SHORT_ARRAY ||
-                arrayType == CstType.CHAR_ARRAY) {
-            elemWidth = 2;
-        } else if (arrayType == CstType.INT_ARRAY ||
-                arrayType == CstType.FLOAT_ARRAY) {
-            elemWidth = 4;
-        } else if (arrayType == CstType.LONG_ARRAY ||
-                arrayType == CstType.DOUBLE_ARRAY) {
-            elemWidth = 8;
-        } else {
-            throw new IllegalArgumentException("Unexpected constant type");
-        }
-        this.user = user;
-        this.values = values;
-        initLength = values.size();
+    if (user == null) {
+      throw new NullPointerException("user == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        int sz = initLength;
-        // Note: the unit here is 16-bit
-        return 4 + ((sz * elemWidth) + 1) / 2;
+    if (values == null) {
+      throw new NullPointerException("values == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out) {
-        int sz = values.size();
+    int sz = values.size();
 
-        out.writeShort(Opcodes.FILL_ARRAY_DATA_PAYLOAD);
-        out.writeShort(elemWidth);
-        out.writeInt(initLength);
-
-
-        // For speed reasons, replicate the for loop in each case
-        switch (elemWidth) {
-            case 1: {
-                for (int i = 0; i < sz; i++) {
-                    Constant cst = values.get(i);
-                    out.writeByte((byte) ((CstLiteral32) cst).getIntBits());
-                }
-                break;
-            }
-            case 2: {
-                for (int i = 0; i < sz; i++) {
-                    Constant cst = values.get(i);
-                    out.writeShort((short) ((CstLiteral32) cst).getIntBits());
-                }
-                break;
-            }
-            case 4: {
-                for (int i = 0; i < sz; i++) {
-                    Constant cst = values.get(i);
-                    out.writeInt(((CstLiteral32) cst).getIntBits());
-                }
-                break;
-            }
-            case 8: {
-                for (int i = 0; i < sz; i++) {
-                    Constant cst = values.get(i);
-                    out.writeLong(((CstLiteral64) cst).getLongBits());
-                }
-                break;
-            }
-            default:
-                break;
-        }
-
-        // Pad one byte to make the size of data table multiples of 16-bits
-        if (elemWidth == 1 && (sz % 2 != 0)) {
-            out.writeByte(0x00);
-        }
+    if (sz <= 0) {
+      throw new IllegalArgumentException("Illegal number of init values");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new ArrayData(getPosition(), user, values, arrayType);
+    this.arrayType = arrayType;
+
+    if (arrayType == CstType.BYTE_ARRAY || arrayType == CstType.BOOLEAN_ARRAY) {
+      elemWidth = 1;
+    } else if (arrayType == CstType.SHORT_ARRAY || arrayType == CstType.CHAR_ARRAY) {
+      elemWidth = 2;
+    } else if (arrayType == CstType.INT_ARRAY || arrayType == CstType.FLOAT_ARRAY) {
+      elemWidth = 4;
+    } else if (arrayType == CstType.LONG_ARRAY || arrayType == CstType.DOUBLE_ARRAY) {
+      elemWidth = 8;
+    } else {
+      throw new IllegalArgumentException("Unexpected constant type");
     }
+    this.user = user;
+    this.values = values;
+    initLength = values.size();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        StringBuffer sb = new StringBuffer(100);
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    int sz = initLength;
+    // Note: the unit here is 16-bit
+    return 4 + ((sz * elemWidth) + 1) / 2;
+  }
 
-        int sz = values.size();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out) {
+    int sz = values.size();
+
+    out.writeShort(Opcodes.FILL_ARRAY_DATA_PAYLOAD);
+    out.writeShort(elemWidth);
+    out.writeInt(initLength);
+
+
+    // For speed reasons, replicate the for loop in each case
+    switch (elemWidth) {
+      case 1: {
         for (int i = 0; i < sz; i++) {
-            sb.append("\n    ");
-            sb.append(i);
-            sb.append(": ");
-            sb.append(values.get(i).toHuman());
+          Constant cst = values.get(i);
+          out.writeByte((byte) ((CstLiteral32) cst).getIntBits());
         }
-
-        return sb.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        int baseAddress = user.getAddress();
-        StringBuffer sb = new StringBuffer(100);
-        int sz = values.size();
-
-        sb.append("fill-array-data-payload // for fill-array-data @ ");
-        sb.append(Hex.u2(baseAddress));
-
+        break;
+      }
+      case 2: {
         for (int i = 0; i < sz; i++) {
-            sb.append("\n  ");
-            sb.append(i);
-            sb.append(": ");
-            sb.append(values.get(i).toHuman());
+          Constant cst = values.get(i);
+          out.writeShort((short) ((CstLiteral32) cst).getIntBits());
         }
-
-        return sb.toString();
+        break;
+      }
+      case 4: {
+        for (int i = 0; i < sz; i++) {
+          Constant cst = values.get(i);
+          out.writeInt(((CstLiteral32) cst).getIntBits());
+        }
+        break;
+      }
+      case 8: {
+        for (int i = 0; i < sz; i++) {
+          Constant cst = values.get(i);
+          out.writeLong(((CstLiteral64) cst).getLongBits());
+        }
+        break;
+      }
+      default:
+        break;
     }
+
+    // Pad one byte to make the size of data table multiples of 16-bits
+    if (elemWidth == 1 && (sz % 2 != 0)) {
+      out.writeByte(0x00);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new ArrayData(getPosition(), user, values, arrayType);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    int sz = values.size();
+    for (int i = 0; i < sz; i++) {
+      sb.append("\n    ");
+      sb.append(i);
+      sb.append(": ");
+      sb.append(values.get(i).toHuman());
+    }
+
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    int baseAddress = user.getAddress();
+    StringBuffer sb = new StringBuffer(100);
+    int sz = values.size();
+
+    sb.append("fill-array-data-payload // for fill-array-data @ ");
+    sb.append(Hex.u2(baseAddress));
+
+    for (int i = 0; i < sz; i++) {
+      sb.append("\n  ");
+      sb.append(i);
+      sb.append(": ");
+      sb.append(values.get(i).toHuman());
+    }
+
+    return sb.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/BlockAddresses.java b/dx/src/com/android/jack/dx/dex/code/BlockAddresses.java
index 4ec10f8..693c342 100644
--- a/dx/src/com/android/jack/dx/dex/code/BlockAddresses.java
+++ b/dx/src/com/android/jack/dx/dex/code/BlockAddresses.java
@@ -28,116 +28,116 @@
  * start address, end address, and last instruction address.
  */
 public final class BlockAddresses {
-    /** {@code non-null;} array containing addresses for the start of each basic
-     * block (indexed by basic block label) */
-    private final CodeAddress[] starts;
+  /** {@code non-null;} array containing addresses for the start of each basic
+   * block (indexed by basic block label) */
+  private final CodeAddress[] starts;
 
-    /** {@code non-null;} array containing addresses for the final instruction
-     * of each basic block (indexed by basic block label) */
-    private final CodeAddress[] lasts;
+  /** {@code non-null;} array containing addresses for the final instruction
+   * of each basic block (indexed by basic block label) */
+  private final CodeAddress[] lasts;
 
-    /** {@code non-null;} array containing addresses for the end (just past the
-     * final instruction) of each basic block (indexed by basic block
-     * label) */
-    private final CodeAddress[] ends;
+  /** {@code non-null;} array containing addresses for the end (just past the
+   * final instruction) of each basic block (indexed by basic block
+   * label) */
+  private final CodeAddress[] ends;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the method to have block addresses for
-     */
-    public BlockAddresses(RopMethod method) {
-        BasicBlockList blocks = method.getBlocks();
-        int maxLabel = blocks.getMaxLabel();
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the method to have block addresses for
+   */
+  public BlockAddresses(RopMethod method) {
+    BasicBlockList blocks = method.getBlocks();
+    int maxLabel = blocks.getMaxLabel();
 
-        this.starts = new CodeAddress[maxLabel];
-        this.lasts = new CodeAddress[maxLabel];
-        this.ends = new CodeAddress[maxLabel];
+    this.starts = new CodeAddress[maxLabel];
+    this.lasts = new CodeAddress[maxLabel];
+    this.ends = new CodeAddress[maxLabel];
 
-        setupArrays(method);
+    setupArrays(method);
+  }
+
+  /**
+   * Gets the instance for the start of the given block.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getStart(BasicBlock block) {
+    return starts[block.getLabel()];
+  }
+
+  /**
+   * Gets the instance for the start of the block with the given label.
+   *
+   * @param label {@code non-null;} the label of the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getStart(int label) {
+    return starts[label];
+  }
+
+  /**
+   * Gets the instance for the final instruction of the given block.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getLast(BasicBlock block) {
+    return lasts[block.getLabel()];
+  }
+
+  /**
+   * Gets the instance for the final instruction of the block with
+   * the given label.
+   *
+   * @param label {@code non-null;} the label of the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getLast(int label) {
+    return lasts[label];
+  }
+
+  /**
+   * Gets the instance for the end (address after the final instruction)
+   * of the given block.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getEnd(BasicBlock block) {
+    return ends[block.getLabel()];
+  }
+
+  /**
+   * Gets the instance for the end (address after the final instruction)
+   * of the block with the given label.
+   *
+   * @param label {@code non-null;} the label of the block in question
+   * @return {@code non-null;} the appropriate instance
+   */
+  public CodeAddress getEnd(int label) {
+    return ends[label];
+  }
+
+  /**
+   * Sets up the address arrays.
+   */
+  private void setupArrays(RopMethod method) {
+    BasicBlockList blocks = method.getBlocks();
+    int sz = blocks.size();
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = blocks.get(i);
+      int label = one.getLabel();
+      Insn insn = one.getInsns().get(0);
+
+      starts[label] = new CodeAddress(insn.getPosition());
+
+      SourcePosition pos = one.getLastInsn().getPosition();
+
+      lasts[label] = new CodeAddress(pos);
+      ends[label] = new CodeAddress(pos);
     }
-
-    /**
-     * Gets the instance for the start of the given block.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getStart(BasicBlock block) {
-        return starts[block.getLabel()];
-    }
-
-    /**
-     * Gets the instance for the start of the block with the given label.
-     *
-     * @param label {@code non-null;} the label of the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getStart(int label) {
-        return starts[label];
-    }
-
-    /**
-     * Gets the instance for the final instruction of the given block.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getLast(BasicBlock block) {
-        return lasts[block.getLabel()];
-    }
-
-    /**
-     * Gets the instance for the final instruction of the block with
-     * the given label.
-     *
-     * @param label {@code non-null;} the label of the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getLast(int label) {
-        return lasts[label];
-    }
-
-    /**
-     * Gets the instance for the end (address after the final instruction)
-     * of the given block.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getEnd(BasicBlock block) {
-        return ends[block.getLabel()];
-    }
-
-    /**
-     * Gets the instance for the end (address after the final instruction)
-     * of the block with the given label.
-     *
-     * @param label {@code non-null;} the label of the block in question
-     * @return {@code non-null;} the appropriate instance
-     */
-    public CodeAddress getEnd(int label) {
-        return ends[label];
-    }
-
-    /**
-     * Sets up the address arrays.
-     */
-    private void setupArrays(RopMethod method) {
-        BasicBlockList blocks = method.getBlocks();
-        int sz = blocks.size();
-
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = blocks.get(i);
-            int label = one.getLabel();
-            Insn insn = one.getInsns().get(0);
-
-            starts[label] = new CodeAddress(insn.getPosition());
-
-            SourcePosition pos = one.getLastInsn().getPosition();
-
-            lasts[label] = new CodeAddress(pos);
-            ends[label] = new CodeAddress(pos);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/CatchBuilder.java b/dx/src/com/android/jack/dx/dex/code/CatchBuilder.java
index 9b19792..978fe70 100644
--- a/dx/src/com/android/jack/dx/dex/code/CatchBuilder.java
+++ b/dx/src/com/android/jack/dx/dex/code/CatchBuilder.java
@@ -24,25 +24,25 @@
  * Interface for the construction of {@link CatchTable} instances.
  */
 public interface CatchBuilder {
-    /**
-     * Builds and returns the catch table for this instance.
-     *
-     * @return {@code non-null;} the constructed table
-     */
-    public CatchTable build();
+  /**
+   * Builds and returns the catch table for this instance.
+   *
+   * @return {@code non-null;} the constructed table
+   */
+  public CatchTable build();
 
-    /**
-     * Gets whether this instance has any catches at all (either typed
-     * or catch-all).
-     *
-     * @return whether this instance has any catches at all
-     */
-    public boolean hasAnyCatches();
+  /**
+   * Gets whether this instance has any catches at all (either typed
+   * or catch-all).
+   *
+   * @return whether this instance has any catches at all
+   */
+  public boolean hasAnyCatches();
 
-    /**
-     * Gets the set of catch types associated with this instance.
-     *
-     * @return {@code non-null;} the set of catch types
-     */
-    public HashSet<Type> getCatchTypes();
+  /**
+   * Gets the set of catch types associated with this instance.
+   *
+   * @return {@code non-null;} the set of catch types
+   */
+  public HashSet<Type> getCatchTypes();
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/CatchHandlerList.java b/dx/src/com/android/jack/dx/dex/code/CatchHandlerList.java
index 1f5ae6d..cfec0ab 100644
--- a/dx/src/com/android/jack/dx/dex/code/CatchHandlerList.java
+++ b/dx/src/com/android/jack/dx/dex/code/CatchHandlerList.java
@@ -23,216 +23,218 @@
 /**
  * Ordered list of (exception type, handler address) entries.
  */
-public final class CatchHandlerList extends FixedSizeList
-        implements Comparable<CatchHandlerList> {
-    /** {@code non-null;} empty instance */
-    public static final CatchHandlerList EMPTY = new CatchHandlerList(0);
+public final class CatchHandlerList extends FixedSizeList implements Comparable<CatchHandlerList> {
+  /** {@code non-null;} empty instance */
+  public static final CatchHandlerList EMPTY = new CatchHandlerList(0);
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size {@code >= 0;} the size of the list
-     */
-    public CatchHandlerList(int size) {
-        super(size);
-    }
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size {@code >= 0;} the size of the list
+   */
+  public CatchHandlerList(int size) {
+    super(size);
+  }
 
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public Entry get(int n) {
-        return (Entry) get0(n);
-    }
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Entry get(int n) {
+    return (Entry) get0(n);
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return toHuman("", "");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return toHuman("", "");
+  }
 
-    /**
-     * Get the human form of this instance, prefixed on each line
-     * with the string.
-     *
-     * @param prefix {@code non-null;} the prefix for every line
-     * @param header {@code non-null;} the header for the first line (after the
-     * first prefix)
-     * @return {@code non-null;} the human form
-     */
-    public String toHuman(String prefix, String header) {
-        StringBuilder sb = new StringBuilder(100);
-        int size = size();
+  /**
+   * Get the human form of this instance, prefixed on each line
+   * with the string.
+   *
+   * @param prefix {@code non-null;} the prefix for every line
+   * @param header {@code non-null;} the header for the first line (after the
+   * first prefix)
+   * @return {@code non-null;} the human form
+   */
+  public String toHuman(String prefix, String header) {
+    StringBuilder sb = new StringBuilder(100);
+    int size = size();
 
+    sb.append(prefix);
+    sb.append(header);
+    sb.append("catch ");
+
+    for (int i = 0; i < size; i++) {
+      Entry entry = get(i);
+
+      if (i != 0) {
+        sb.append(",\n");
         sb.append(prefix);
-        sb.append(header);
-        sb.append("catch ");
+        sb.append("  ");
+      }
 
-        for (int i = 0; i < size; i++) {
-            Entry entry = get(i);
+      if ((i == (size - 1)) && catchesAll()) {
+        sb.append("<any>");
+      } else {
+        sb.append(entry.getExceptionType().toHuman());
+      }
 
-            if (i != 0) {
-                sb.append(",\n");
-                sb.append(prefix);
-                sb.append("  ");
-            }
-
-            if ((i == (size - 1)) && catchesAll()) {
-                sb.append("<any>");
-            } else {
-                sb.append(entry.getExceptionType().toHuman());
-            }
-
-            sb.append(" -> ");
-            sb.append(Hex.u2or4(entry.getHandler()));
-        }
-
-        return sb.toString();
+      sb.append(" -> ");
+      sb.append(Hex.u2or4(entry.getHandler()));
     }
 
-    /**
-     * Returns whether or not this instance ends with a "catch-all"
-     * handler.
-     *
-     * @return {@code true} if this instance ends with a "catch-all"
-     * handler or {@code false} if not
-     */
-    public boolean catchesAll() {
-        int size = size();
+    return sb.toString();
+  }
 
-        if (size == 0) {
-            return false;
-        }
+  /**
+   * Returns whether or not this instance ends with a "catch-all"
+   * handler.
+   *
+   * @return {@code true} if this instance ends with a "catch-all"
+   * handler or {@code false} if not
+   */
+  public boolean catchesAll() {
+    int size = size();
 
-        Entry last = get(size - 1);
-        return last.getExceptionType().equals(CstType.OBJECT);
+    if (size == 0) {
+      return false;
     }
 
+    Entry last = get(size - 1);
+    return last.getExceptionType().equals(CstType.OBJECT);
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param exceptionType {@code non-null;} type of exception handled
+   * @param handler {@code >= 0;} exception handler address
+   */
+  public void set(int n, CstType exceptionType, int handler) {
+    set0(n, new Entry(exceptionType, handler));
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param entry {@code non-null;} the entry to set at {@code n}
+   */
+  public void set(int n, Entry entry) {
+    set0(n, entry);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(CatchHandlerList other) {
+    if (this == other) {
+      // Easy out.
+      return 0;
+    }
+
+    int thisSize = size();
+    int otherSize = other.size();
+    int checkSize = Math.min(thisSize, otherSize);
+
+    for (int i = 0; i < checkSize; i++) {
+      Entry thisEntry = get(i);
+      Entry otherEntry = other.get(i);
+      int compare = thisEntry.compareTo(otherEntry);
+      if (compare != 0) {
+        return compare;
+      }
+    }
+
+    if (thisSize < otherSize) {
+      return -1;
+    } else if (thisSize > otherSize) {
+      return 1;
+    }
+
+    return 0;
+  }
+
+  /**
+   * Entry in the list.
+   */
+  public static class Entry implements Comparable<Entry> {
+    /** {@code non-null;} type of exception handled */
+    private final CstType exceptionType;
+
+    /** {@code >= 0;} exception handler address */
+    private final int handler;
+
     /**
-     * Sets the entry at the given index.
+     * Constructs an instance.
      *
-     * @param n {@code >= 0, < size();} which index
      * @param exceptionType {@code non-null;} type of exception handled
      * @param handler {@code >= 0;} exception handler address
      */
-    public void set(int n, CstType exceptionType, int handler) {
-        set0(n, new Entry(exceptionType, handler));
-    }
+    public Entry(CstType exceptionType, int handler) {
+      if (handler < 0) {
+        throw new IllegalArgumentException("handler < 0");
+      }
 
-    /**
-     * Sets the entry at the given index.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param entry {@code non-null;} the entry to set at {@code n}
-     */
-    public void set(int n, Entry entry) {
-        set0(n, entry);
+      if (exceptionType == null) {
+        throw new NullPointerException("exceptionType == null");
+      }
+
+      this.handler = handler;
+      this.exceptionType = exceptionType;
     }
 
     /** {@inheritDoc} */
-    public int compareTo(CatchHandlerList other) {
-        if (this == other) {
-            // Easy out.
-            return 0;
-        }
+    @Override
+    public int hashCode() {
+      return (handler * 31) + exceptionType.hashCode();
+    }
 
-        int thisSize = size();
-        int otherSize = other.size();
-        int checkSize = Math.min(thisSize, otherSize);
+    /** {@inheritDoc} */
+    @Override
+    public boolean equals(Object other) {
+      if (other instanceof Entry) {
+        return (compareTo((Entry) other) == 0);
+      }
 
-        for (int i = 0; i < checkSize; i++) {
-            Entry thisEntry = get(i);
-            Entry otherEntry = other.get(i);
-            int compare = thisEntry.compareTo(otherEntry);
-            if (compare != 0) {
-                return compare;
-            }
-        }
+      return false;
+    }
 
-        if (thisSize < otherSize) {
-            return -1;
-        } else if (thisSize > otherSize) {
-            return 1;
-        }
+    /** {@inheritDoc} */
+    @Override
+    public int compareTo(Entry other) {
+      if (handler < other.handler) {
+        return -1;
+      } else if (handler > other.handler) {
+        return 1;
+      }
 
-        return 0;
+      return exceptionType.compareTo(other.exceptionType);
     }
 
     /**
-     * Entry in the list.
+     * Gets the exception type handled.
+     *
+     * @return {@code non-null;} the exception type
      */
-    public static class Entry implements Comparable<Entry> {
-        /** {@code non-null;} type of exception handled */
-        private final CstType exceptionType;
-
-        /** {@code >= 0;} exception handler address */
-        private final int handler;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param exceptionType {@code non-null;} type of exception handled
-         * @param handler {@code >= 0;} exception handler address
-         */
-        public Entry(CstType exceptionType, int handler) {
-            if (handler < 0) {
-                throw new IllegalArgumentException("handler < 0");
-            }
-
-            if (exceptionType == null) {
-                throw new NullPointerException("exceptionType == null");
-            }
-
-            this.handler = handler;
-            this.exceptionType = exceptionType;
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public int hashCode() {
-            return (handler * 31) + exceptionType.hashCode();
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public boolean equals(Object other) {
-            if (other instanceof Entry) {
-                return (compareTo((Entry) other) == 0);
-            }
-
-            return false;
-        }
-
-        /** {@inheritDoc} */
-        public int compareTo(Entry other) {
-            if (handler < other.handler) {
-                return -1;
-            } else if (handler > other.handler) {
-                return 1;
-            }
-
-            return exceptionType.compareTo(other.exceptionType);
-        }
-
-        /**
-         * Gets the exception type handled.
-         *
-         * @return {@code non-null;} the exception type
-         */
-        public CstType getExceptionType() {
-            return exceptionType;
-        }
-
-        /**
-         * Gets the handler address.
-         *
-         * @return {@code >= 0;} the handler address
-         */
-        public int getHandler() {
-            return handler;
-        }
+    public CstType getExceptionType() {
+      return exceptionType;
     }
+
+    /**
+     * Gets the handler address.
+     *
+     * @return {@code >= 0;} the handler address
+     */
+    public int getHandler() {
+      return handler;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/CatchTable.java b/dx/src/com/android/jack/dx/dex/code/CatchTable.java
index 6e10e8a..54fc432 100644
--- a/dx/src/com/android/jack/dx/dex/code/CatchTable.java
+++ b/dx/src/com/android/jack/dx/dex/code/CatchTable.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.dx.dex.code;
 
-import com.android.jack.dx.rop.cst.CstType;
 import com.android.jack.dx.util.FixedSizeList;
 
 /**
@@ -24,169 +23,170 @@
  * addresses for which it is valid and an associated {@link
  * CatchHandlerList}.
  */
-public final class CatchTable extends FixedSizeList
-        implements Comparable<CatchTable> {
-    /** {@code non-null;} empty instance */
-    public static final CatchTable EMPTY = new CatchTable(0);
+public final class CatchTable extends FixedSizeList implements Comparable<CatchTable> {
+  /** {@code non-null;} empty instance */
+  public static final CatchTable EMPTY = new CatchTable(0);
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size {@code >= 0;} the size of the table
-     */
-    public CatchTable(int size) {
-        super(size);
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size {@code >= 0;} the size of the table
+   */
+  public CatchTable(int size) {
+    super(size);
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Entry get(int n) {
+    return (Entry) get0(n);
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param entry {@code non-null;} the entry to set at {@code n}
+   */
+  public void set(int n, Entry entry) {
+    set0(n, entry);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(CatchTable other) {
+    if (this == other) {
+      // Easy out.
+      return 0;
     }
 
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public Entry get(int n) {
-        return (Entry) get0(n);
+    int thisSize = size();
+    int otherSize = other.size();
+    int checkSize = Math.min(thisSize, otherSize);
+
+    for (int i = 0; i < checkSize; i++) {
+      Entry thisEntry = get(i);
+      Entry otherEntry = other.get(i);
+      int compare = thisEntry.compareTo(otherEntry);
+      if (compare != 0) {
+        return compare;
+      }
     }
 
+    if (thisSize < otherSize) {
+      return -1;
+    } else if (thisSize > otherSize) {
+      return 1;
+    }
+
+    return 0;
+  }
+
+  /**
+   * Entry in a catch list.
+   */
+  public static class Entry implements Comparable<Entry> {
+    /** {@code >= 0;} start address */
+    private final int start;
+
+    /** {@code > start;} end address (exclusive) */
+    private final int end;
+
+    /** {@code non-null;} list of catch handlers */
+    private final CatchHandlerList handlers;
+
     /**
-     * Sets the entry at the given index.
+     * Constructs an instance.
      *
-     * @param n {@code >= 0, < size();} which index
-     * @param entry {@code non-null;} the entry to set at {@code n}
+     * @param start {@code >= 0;} start address
+     * @param end {@code > start;} end address (exclusive)
+     * @param handlers {@code non-null;} list of catch handlers
      */
-    public void set(int n, Entry entry) {
-        set0(n, entry);
+    public Entry(int start, int end, CatchHandlerList handlers) {
+      if (start < 0) {
+        throw new IllegalArgumentException("start < 0");
+      }
+
+      if (end <= start) {
+        throw new IllegalArgumentException("end <= start");
+      }
+
+      if (handlers.isMutable()) {
+        throw new IllegalArgumentException("handlers.isMutable()");
+      }
+
+      this.start = start;
+      this.end = end;
+      this.handlers = handlers;
     }
 
     /** {@inheritDoc} */
-    public int compareTo(CatchTable other) {
-        if (this == other) {
-            // Easy out.
-            return 0;
-        }
+    @Override
+    public int hashCode() {
+      int hash = (start * 31) + end;
+      hash = (hash * 31) + handlers.hashCode();
+      return hash;
+    }
 
-        int thisSize = size();
-        int otherSize = other.size();
-        int checkSize = Math.min(thisSize, otherSize);
+    /** {@inheritDoc} */
+    @Override
+    public boolean equals(Object other) {
+      if (other instanceof Entry) {
+        return (compareTo((Entry) other) == 0);
+      }
 
-        for (int i = 0; i < checkSize; i++) {
-            Entry thisEntry = get(i);
-            Entry otherEntry = other.get(i);
-            int compare = thisEntry.compareTo(otherEntry);
-            if (compare != 0) {
-                return compare;
-            }
-        }
+      return false;
+    }
 
-        if (thisSize < otherSize) {
-            return -1;
-        } else if (thisSize > otherSize) {
-            return 1;
-        }
+    /** {@inheritDoc} */
+    @Override
+    public int compareTo(Entry other) {
+      if (start < other.start) {
+        return -1;
+      } else if (start > other.start) {
+        return 1;
+      }
 
-        return 0;
+      if (end < other.end) {
+        return -1;
+      } else if (end > other.end) {
+        return 1;
+      }
+
+      return handlers.compareTo(other.handlers);
     }
 
     /**
-     * Entry in a catch list.
+     * Gets the start address.
+     *
+     * @return {@code >= 0;} the start address
      */
-    public static class Entry implements Comparable<Entry> {
-        /** {@code >= 0;} start address */
-        private final int start;
-
-        /** {@code > start;} end address (exclusive) */
-        private final int end;
-
-        /** {@code non-null;} list of catch handlers */
-        private final CatchHandlerList handlers;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param start {@code >= 0;} start address
-         * @param end {@code > start;} end address (exclusive)
-         * @param handlers {@code non-null;} list of catch handlers
-         */
-        public Entry(int start, int end, CatchHandlerList handlers) {
-            if (start < 0) {
-                throw new IllegalArgumentException("start < 0");
-            }
-
-            if (end <= start) {
-                throw new IllegalArgumentException("end <= start");
-            }
-
-            if (handlers.isMutable()) {
-                throw new IllegalArgumentException("handlers.isMutable()");
-            }
-
-            this.start = start;
-            this.end = end;
-            this.handlers = handlers;
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public int hashCode() {
-            int hash = (start * 31) + end;
-            hash = (hash * 31) + handlers.hashCode();
-            return hash;
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public boolean equals(Object other) {
-            if (other instanceof Entry) {
-                return (compareTo((Entry) other) == 0);
-            }
-
-            return false;
-        }
-
-        /** {@inheritDoc} */
-        public int compareTo(Entry other) {
-            if (start < other.start) {
-                return -1;
-            } else if (start > other.start) {
-                return 1;
-            }
-
-            if (end < other.end) {
-                return -1;
-            } else if (end > other.end) {
-                return 1;
-            }
-
-            return handlers.compareTo(other.handlers);
-        }
-
-        /**
-         * Gets the start address.
-         *
-         * @return {@code >= 0;} the start address
-         */
-        public int getStart() {
-            return start;
-        }
-
-        /**
-         * Gets the end address (exclusive).
-         *
-         * @return {@code > start;} the end address (exclusive)
-         */
-        public int getEnd() {
-            return end;
-        }
-
-        /**
-         * Gets the handlers.
-         *
-         * @return {@code non-null;} the handlers
-         */
-        public CatchHandlerList getHandlers() {
-            return handlers;
-        }
+    public int getStart() {
+      return start;
     }
+
+    /**
+     * Gets the end address (exclusive).
+     *
+     * @return {@code > start;} the end address (exclusive)
+     */
+    public int getEnd() {
+      return end;
+    }
+
+    /**
+     * Gets the handlers.
+     *
+     * @return {@code non-null;} the handlers
+     */
+    public CatchHandlerList getHandlers() {
+      return handlers;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/CodeAddress.java b/dx/src/com/android/jack/dx/dex/code/CodeAddress.java
index bb4904d..28a3c9a 100644
--- a/dx/src/com/android/jack/dx/dex/code/CodeAddress.java
+++ b/dx/src/com/android/jack/dx/dex/code/CodeAddress.java
@@ -27,65 +27,65 @@
  * human-oriented or binary file).
  */
 public final class CodeAddress extends ZeroSizeInsn {
-    /** If this address should bind closely to the following real instruction */
-    private final boolean bindsClosely;
+  /** If this address should bind closely to the following real instruction */
+  private final boolean bindsClosely;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     */
-    public CodeAddress(SourcePosition position) {
-        this(position, false);
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   */
+  public CodeAddress(SourcePosition position) {
+    this(position, false);
+  }
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param bindsClosely if the address should bind closely to the following
-     *                     real instruction.
-     */
-    public CodeAddress(SourcePosition position, boolean bindsClosely) {
-        super(position);
-        this.bindsClosely = bindsClosely;
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param bindsClosely if the address should bind closely to the following
+   *                     real instruction.
+   */
+  public CodeAddress(SourcePosition position, boolean bindsClosely) {
+    super(position);
+    this.bindsClosely = bindsClosely;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final DalvInsn withRegisters(RegisterSpecList registers) {
-        return new CodeAddress(getPosition());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final DalvInsn withRegisters(RegisterSpecList registers) {
+    return new CodeAddress(getPosition());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return null;
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return null;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        return "code-address";
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    return "code-address";
+  }
 
-    /**
-     * Gets whether this address binds closely to the following "real"
-     * (non-zero-length) instruction.
-     *
-     * When a prefix is added to an instruction (for example, to move a value
-     * from a high register to a low register), this determines whether this
-     * {@code CodeAddress} will point to the prefix, or to the instruction
-     * itself.
-     *
-     * If bindsClosely is true, the address will point to the instruction
-     * itself, otherwise it will point to the prefix (if any)
-     *
-     * @return true if this address binds closely to the next real instruction
-     */
-    public boolean getBindsClosely() {
-        return bindsClosely;
-    }
+  /**
+   * Gets whether this address binds closely to the following "real"
+   * (non-zero-length) instruction.
+   *
+   * When a prefix is added to an instruction (for example, to move a value
+   * from a high register to a low register), this determines whether this
+   * {@code CodeAddress} will point to the prefix, or to the instruction
+   * itself.
+   *
+   * If bindsClosely is true, the address will point to the instruction
+   * itself, otherwise it will point to the prefix (if any)
+   *
+   * @return true if this address binds closely to the next real instruction
+   */
+  public boolean getBindsClosely() {
+    return bindsClosely;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/CstInsn.java b/dx/src/com/android/jack/dx/dex/code/CstInsn.java
index a83e485..bf3cdb2 100644
--- a/dx/src/com/android/jack/dx/dex/code/CstInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/CstInsn.java
@@ -25,181 +25,179 @@
  * to all the normal instruction information.
  */
 public final class CstInsn extends FixedSizeInsn {
-    /** {@code non-null;} the constant argument for this instruction */
-    private final Constant constant;
+  /** {@code non-null;} the constant argument for this instruction */
+  private final Constant constant;
 
-    /**
-     * {@code >= -1;} the constant pool index for {@link #constant}, or
-     * {@code -1} if not yet set
-     */
-    private int index;
+  /**
+   * {@code >= -1;} the constant pool index for {@link #constant}, or
+   * {@code -1} if not yet set
+   */
+  private int index;
 
-    /**
-     * {@code >= -1;} the constant pool index for the class reference in
-     * {@link #constant} if any, or {@code -1} if not yet set
-     */
-    private int classIndex;
+  /**
+   * {@code >= -1;} the constant pool index for the class reference in
+   * {@link #constant} if any, or {@code -1} if not yet set
+   */
+  private int classIndex;
 
-    /**
-     * Constructs an instance. The output address of this instance is
-     * initially unknown ({@code -1}) as is the constant pool index.
-     *
-     * @param opcode the opcode; one of the constants from {@link Dops}
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} register list, including a
-     * result register if appropriate (that is, registers may be either
-     * ins or outs)
-     * @param constant {@code non-null;} constant argument
-     */
-    public CstInsn(Dop opcode, SourcePosition position,
-                   RegisterSpecList registers, Constant constant) {
-        super(opcode, position, registers);
+  /**
+   * Constructs an instance. The output address of this instance is
+   * initially unknown ({@code -1}) as is the constant pool index.
+   *
+   * @param opcode the opcode; one of the constants from {@link Dops}
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} register list, including a
+   * result register if appropriate (that is, registers may be either
+   * ins or outs)
+   * @param constant {@code non-null;} constant argument
+   */
+  public CstInsn(Dop opcode, SourcePosition position, RegisterSpecList registers,
+      Constant constant) {
+    super(opcode, position, registers);
 
-        if (constant == null) {
-            throw new NullPointerException("constant == null");
-        }
-
-        this.constant = constant;
-        this.index = -1;
-        this.classIndex = -1;
+    if (constant == null) {
+      throw new NullPointerException("constant == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withOpcode(Dop opcode) {
-        CstInsn result =
-            new CstInsn(opcode, getPosition(), getRegisters(), constant);
+    this.constant = constant;
+    this.index = -1;
+    this.classIndex = -1;
+  }
 
-        if (index >= 0) {
-            result.setIndex(index);
-        }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withOpcode(Dop opcode) {
+    CstInsn result = new CstInsn(opcode, getPosition(), getRegisters(), constant);
 
-        if (classIndex >= 0) {
-            result.setClassIndex(classIndex);
-        }
-
-        return result;
+    if (index >= 0) {
+      result.setIndex(index);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        CstInsn result =
-            new CstInsn(getOpcode(), getPosition(), registers, constant);
-
-        if (index >= 0) {
-            result.setIndex(index);
-        }
-
-        if (classIndex >= 0) {
-            result.setClassIndex(classIndex);
-        }
-
-        return result;
+    if (classIndex >= 0) {
+      result.setClassIndex(classIndex);
     }
 
-    /**
-     * Gets the constant argument.
-     *
-     * @return {@code non-null;} the constant argument
-     */
-    public Constant getConstant() {
-        return constant;
+    return result;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    CstInsn result = new CstInsn(getOpcode(), getPosition(), registers, constant);
+
+    if (index >= 0) {
+      result.setIndex(index);
     }
 
-    /**
-     * Gets the constant's index. It is only valid to call this after
-     * {@link #setIndex} has been called.
-     *
-     * @return {@code >= 0;} the constant pool index
-     */
-    public int getIndex() {
-        if (index < 0) {
-            throw new RuntimeException("index not yet set for " + constant);
-        }
-
-        return index;
+    if (classIndex >= 0) {
+      result.setClassIndex(classIndex);
     }
 
-    /**
-     * Returns whether the constant's index has been set for this instance.
-     *
-     * @see #setIndex
-     *
-     * @return {@code true} iff the index has been set
-     */
-    public boolean hasIndex() {
-        return (index >= 0);
+    return result;
+  }
+
+  /**
+   * Gets the constant argument.
+   *
+   * @return {@code non-null;} the constant argument
+   */
+  public Constant getConstant() {
+    return constant;
+  }
+
+  /**
+   * Gets the constant's index. It is only valid to call this after
+   * {@link #setIndex} has been called.
+   *
+   * @return {@code >= 0;} the constant pool index
+   */
+  public int getIndex() {
+    if (index < 0) {
+      throw new RuntimeException("index not yet set for " + constant);
     }
 
-    /**
-     * Sets the constant's index. It is only valid to call this method once
-     * per instance.
-     *
-     * @param index {@code >= 0;} the constant pool index
-     */
-    public void setIndex(int index) {
-        if (index < 0) {
-            throw new IllegalArgumentException("index < 0");
-        }
+    return index;
+  }
 
-        if (this.index >= 0) {
-            throw new RuntimeException("index already set");
-        }
+  /**
+   * Returns whether the constant's index has been set for this instance.
+   *
+   * @see #setIndex
+   *
+   * @return {@code true} iff the index has been set
+   */
+  public boolean hasIndex() {
+    return (index >= 0);
+  }
 
-        this.index = index;
+  /**
+   * Sets the constant's index. It is only valid to call this method once
+   * per instance.
+   *
+   * @param index {@code >= 0;} the constant pool index
+   */
+  public void setIndex(int index) {
+    if (index < 0) {
+      throw new IllegalArgumentException("index < 0");
     }
 
-    /**
-     * Gets the constant's class index. It is only valid to call this after
-     * {@link #setClassIndex} has been called.
-     *
-     * @return {@code >= 0;} the constant's class's constant pool index
-     */
-    public int getClassIndex() {
-        if (classIndex < 0) {
-            throw new RuntimeException("class index not yet set");
-        }
-
-        return classIndex;
+    if (this.index >= 0) {
+      throw new RuntimeException("index already set");
     }
 
-    /**
-     * Returns whether the constant's class index has been set for this
-     * instance.
-     *
-     * @see #setClassIndex
-     *
-     * @return {@code true} iff the index has been set
-     */
-    public boolean hasClassIndex() {
-        return (classIndex >= 0);
+    this.index = index;
+  }
+
+  /**
+   * Gets the constant's class index. It is only valid to call this after
+   * {@link #setClassIndex} has been called.
+   *
+   * @return {@code >= 0;} the constant's class's constant pool index
+   */
+  public int getClassIndex() {
+    if (classIndex < 0) {
+      throw new RuntimeException("class index not yet set");
     }
 
-    /**
-     * Sets the constant's class index. This is the constant pool index
-     * for the class referred to by this instance's constant. Only
-     * reference constants have a class, so it is only on instances
-     * with reference constants that this method should ever be
-     * called. It is only valid to call this method once per instance.
-     *
-     * @param index {@code >= 0;} the constant's class's constant pool index
-     */
-    public void setClassIndex(int index) {
-        if (index < 0) {
-            throw new IllegalArgumentException("index < 0");
-        }
+    return classIndex;
+  }
 
-        if (this.classIndex >= 0) {
-            throw new RuntimeException("class index already set");
-        }
+  /**
+   * Returns whether the constant's class index has been set for this
+   * instance.
+   *
+   * @see #setClassIndex
+   *
+   * @return {@code true} iff the index has been set
+   */
+  public boolean hasClassIndex() {
+    return (classIndex >= 0);
+  }
 
-        this.classIndex = index;
+  /**
+   * Sets the constant's class index. This is the constant pool index
+   * for the class referred to by this instance's constant. Only
+   * reference constants have a class, so it is only on instances
+   * with reference constants that this method should ever be
+   * called. It is only valid to call this method once per instance.
+   *
+   * @param index {@code >= 0;} the constant's class's constant pool index
+   */
+  public void setClassIndex(int index) {
+    if (index < 0) {
+      throw new IllegalArgumentException("index < 0");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return constant.toHuman();
+    if (this.classIndex >= 0) {
+      throw new RuntimeException("class index already set");
     }
+
+    this.classIndex = index;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return constant.toHuman();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/DalvCode.java b/dx/src/com/android/jack/dx/dex/code/DalvCode.java
index e691ef1..bf92ad4 100644
--- a/dx/src/com/android/jack/dx/dex/code/DalvCode.java
+++ b/dx/src/com/android/jack/dx/dex/code/DalvCode.java
@@ -26,207 +26,206 @@
  * corresponds to a {@code code} structure in a {@code .dex} file.
  */
 public final class DalvCode {
-    /**
-     * how much position info to preserve; one of the static
-     * constants in {@link PositionList}
-     */
-    private final int positionInfo;
+  /**
+   * how much position info to preserve; one of the static
+   * constants in {@link PositionList}
+   */
+  private final int positionInfo;
 
-    /**
-     * {@code null-ok;} the instruction list, ready for final processing;
-     * nulled out in {@link #finishProcessingIfNecessary}
-     */
-    private OutputFinisher unprocessedInsns;
+  /**
+   * {@code null-ok;} the instruction list, ready for final processing;
+   * nulled out in {@link #finishProcessingIfNecessary}
+   */
+  private OutputFinisher unprocessedInsns;
 
-    /**
-     * {@code non-null;} unprocessed catch table;
-     * nulled out in {@link #finishProcessingIfNecessary}
-     */
-    private CatchBuilder unprocessedCatches;
+  /**
+   * {@code non-null;} unprocessed catch table;
+   * nulled out in {@link #finishProcessingIfNecessary}
+   */
+  private CatchBuilder unprocessedCatches;
 
-    /**
-     * {@code null-ok;} catch table; set in
-     * {@link #finishProcessingIfNecessary}
-     */
-    private CatchTable catches;
+  /**
+   * {@code null-ok;} catch table; set in
+   * {@link #finishProcessingIfNecessary}
+   */
+  private CatchTable catches;
 
-    /**
-     * {@code null-ok;} source positions list; set in
-     * {@link #finishProcessingIfNecessary}
-     */
-    private PositionList positions;
+  /**
+   * {@code null-ok;} source positions list; set in
+   * {@link #finishProcessingIfNecessary}
+   */
+  private PositionList positions;
 
-    /**
-     * {@code null-ok;} local variable list; set in
-     * {@link #finishProcessingIfNecessary}
-     */
-    private LocalList locals;
+  /**
+   * {@code null-ok;} local variable list; set in
+   * {@link #finishProcessingIfNecessary}
+   */
+  private LocalList locals;
 
-    /**
-     * {@code null-ok;} the processed instruction list; set in
-     * {@link #finishProcessingIfNecessary}
-     */
-    private DalvInsnList insns;
+  /**
+   * {@code null-ok;} the processed instruction list; set in
+   * {@link #finishProcessingIfNecessary}
+   */
+  private DalvInsnList insns;
 
+  /**
+   * Constructs an instance.
+   *
+   * @param positionInfo how much position info to preserve; one of the
+   * static constants in {@link PositionList}
+   * @param unprocessedInsns {@code non-null;} the instruction list, ready
+   * for final processing
+   * @param unprocessedCatches {@code non-null;} unprocessed catch
+   * (exception handler) table
+   */
+  public DalvCode(int positionInfo, OutputFinisher unprocessedInsns,
+      CatchBuilder unprocessedCatches) {
+    if (unprocessedInsns == null) {
+      throw new NullPointerException("unprocessedInsns == null");
+    }
+
+    if (unprocessedCatches == null) {
+      throw new NullPointerException("unprocessedCatches == null");
+    }
+
+    this.positionInfo = positionInfo;
+    this.unprocessedInsns = unprocessedInsns;
+    this.unprocessedCatches = unprocessedCatches;
+    this.catches = null;
+    this.positions = null;
+    this.locals = null;
+    this.insns = null;
+  }
+
+  /**
+   * Finish up processing of the method.
+   */
+  private void finishProcessingIfNecessary() {
+    if (insns != null) {
+      return;
+    }
+
+    insns = unprocessedInsns.finishProcessingAndGetList();
+    positions = PositionList.make(insns, positionInfo);
+    locals = LocalList.make(insns);
+    catches = unprocessedCatches.build();
+
+    // Let them be gc'ed.
+    unprocessedInsns = null;
+    unprocessedCatches = null;
+  }
+
+  /**
+   * Assign indices in all instructions that need them, using the
+   * given callback to perform lookups. This must be called before
+   * {@link #getInsns}.
+   *
+   * @param callback {@code non-null;} callback object
+   */
+  public void assignIndices(AssignIndicesCallback callback) {
+    unprocessedInsns.assignIndices(callback);
+  }
+
+  /**
+   * Gets whether this instance has any position data to represent.
+   *
+   * @return {@code true} iff this instance has any position
+   * data to represent
+   */
+  public boolean hasPositions() {
+    return (positionInfo != PositionList.NONE) && unprocessedInsns.hasAnyPositionInfo();
+  }
+
+  /**
+   * Gets whether this instance has any local variable data to represent.
+   *
+   * @return {@code true} iff this instance has any local variable
+   * data to represent
+   */
+  public boolean hasLocals() {
+    return unprocessedInsns.hasAnyLocalInfo();
+  }
+
+  /**
+   * Gets whether this instance has any catches at all (either typed
+   * or catch-all).
+   *
+   * @return whether this instance has any catches at all
+   */
+  public boolean hasAnyCatches() {
+    return unprocessedCatches.hasAnyCatches();
+  }
+
+  /**
+   * Gets the set of catch types handled anywhere in the code.
+   *
+   * @return {@code non-null;} the set of catch types
+   */
+  public HashSet<Type> getCatchTypes() {
+    return unprocessedCatches.getCatchTypes();
+  }
+
+  /**
+   * Gets the set of all constants referred to by instructions in
+   * the code.
+   *
+   * @return {@code non-null;} the set of constants
+   */
+  public HashSet<Constant> getInsnConstants() {
+    return unprocessedInsns.getAllConstants();
+  }
+
+  /**
+   * Gets the list of instructions.
+   *
+   * @return {@code non-null;} the instruction list
+   */
+  public DalvInsnList getInsns() {
+    finishProcessingIfNecessary();
+    return insns;
+  }
+
+  /**
+   * Gets the catch (exception handler) table.
+   *
+   * @return {@code non-null;} the catch table
+   */
+  public CatchTable getCatches() {
+    finishProcessingIfNecessary();
+    return catches;
+  }
+
+  /**
+   * Gets the source positions list.
+   *
+   * @return {@code non-null;} the source positions list
+   */
+  public PositionList getPositions() {
+    finishProcessingIfNecessary();
+    return positions;
+  }
+
+  /**
+   * Gets the source positions list.
+   *
+   * @return {@code non-null;} the source positions list
+   */
+  public LocalList getLocals() {
+    finishProcessingIfNecessary();
+    return locals;
+  }
+
+  /**
+   * Class used as a callback for {@link #assignIndices}.
+   */
+  public static interface AssignIndicesCallback {
     /**
-     * Constructs an instance.
+     * Gets the index for the given constant.
      *
-     * @param positionInfo how much position info to preserve; one of the
-     * static constants in {@link PositionList}
-     * @param unprocessedInsns {@code non-null;} the instruction list, ready
-     * for final processing
-     * @param unprocessedCatches {@code non-null;} unprocessed catch
-     * (exception handler) table
+     * @param cst {@code non-null;} the constant
+     * @return {@code >= -1;} the index or {@code -1} if the constant
+     * shouldn't actually be reified with an index
      */
-    public DalvCode(int positionInfo, OutputFinisher unprocessedInsns,
-            CatchBuilder unprocessedCatches) {
-        if (unprocessedInsns == null) {
-            throw new NullPointerException("unprocessedInsns == null");
-        }
-
-        if (unprocessedCatches == null) {
-            throw new NullPointerException("unprocessedCatches == null");
-        }
-
-        this.positionInfo = positionInfo;
-        this.unprocessedInsns = unprocessedInsns;
-        this.unprocessedCatches = unprocessedCatches;
-        this.catches = null;
-        this.positions = null;
-        this.locals = null;
-        this.insns = null;
-    }
-
-    /**
-     * Finish up processing of the method.
-     */
-    private void finishProcessingIfNecessary() {
-        if (insns != null) {
-            return;
-        }
-
-        insns = unprocessedInsns.finishProcessingAndGetList();
-        positions = PositionList.make(insns, positionInfo);
-        locals = LocalList.make(insns);
-        catches = unprocessedCatches.build();
-
-        // Let them be gc'ed.
-        unprocessedInsns = null;
-        unprocessedCatches = null;
-    }
-
-    /**
-     * Assign indices in all instructions that need them, using the
-     * given callback to perform lookups. This must be called before
-     * {@link #getInsns}.
-     *
-     * @param callback {@code non-null;} callback object
-     */
-    public void assignIndices(AssignIndicesCallback callback) {
-        unprocessedInsns.assignIndices(callback);
-    }
-
-    /**
-     * Gets whether this instance has any position data to represent.
-     *
-     * @return {@code true} iff this instance has any position
-     * data to represent
-     */
-    public boolean hasPositions() {
-        return (positionInfo != PositionList.NONE)
-            && unprocessedInsns.hasAnyPositionInfo();
-    }
-
-    /**
-     * Gets whether this instance has any local variable data to represent.
-     *
-     * @return {@code true} iff this instance has any local variable
-     * data to represent
-     */
-    public boolean hasLocals() {
-        return unprocessedInsns.hasAnyLocalInfo();
-    }
-
-    /**
-     * Gets whether this instance has any catches at all (either typed
-     * or catch-all).
-     *
-     * @return whether this instance has any catches at all
-     */
-    public boolean hasAnyCatches() {
-        return unprocessedCatches.hasAnyCatches();
-    }
-
-    /**
-     * Gets the set of catch types handled anywhere in the code.
-     *
-     * @return {@code non-null;} the set of catch types
-     */
-    public HashSet<Type> getCatchTypes() {
-        return unprocessedCatches.getCatchTypes();
-    }
-
-    /**
-     * Gets the set of all constants referred to by instructions in
-     * the code.
-     *
-     * @return {@code non-null;} the set of constants
-     */
-    public HashSet<Constant> getInsnConstants() {
-        return unprocessedInsns.getAllConstants();
-    }
-
-    /**
-     * Gets the list of instructions.
-     *
-     * @return {@code non-null;} the instruction list
-     */
-    public DalvInsnList getInsns() {
-        finishProcessingIfNecessary();
-        return insns;
-    }
-
-    /**
-     * Gets the catch (exception handler) table.
-     *
-     * @return {@code non-null;} the catch table
-     */
-    public CatchTable getCatches() {
-        finishProcessingIfNecessary();
-        return catches;
-    }
-
-    /**
-     * Gets the source positions list.
-     *
-     * @return {@code non-null;} the source positions list
-     */
-    public PositionList getPositions() {
-        finishProcessingIfNecessary();
-        return positions;
-    }
-
-    /**
-     * Gets the source positions list.
-     *
-     * @return {@code non-null;} the source positions list
-     */
-    public LocalList getLocals() {
-        finishProcessingIfNecessary();
-        return locals;
-    }
-
-    /**
-     * Class used as a callback for {@link #assignIndices}.
-     */
-    public static interface AssignIndicesCallback {
-        /**
-         * Gets the index for the given constant.
-         *
-         * @param cst {@code non-null;} the constant
-         * @return {@code >= -1;} the index or {@code -1} if the constant
-         * shouldn't actually be reified with an index
-         */
-        public int getIndex(Constant cst);
-    }
+    public int getIndex(Constant cst);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/DalvInsn.java b/dx/src/com/android/jack/dx/dex/code/DalvInsn.java
index a6a501e..4667d2f 100644
--- a/dx/src/com/android/jack/dx/dex/code/DalvInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/DalvInsn.java
@@ -29,422 +29,420 @@
  * Base class for Dalvik instructions.
  */
 public abstract class DalvInsn {
-    /**
-     * the actual output address of this instance, if known, or
-     * {@code -1} if not
-     */
-    private int address;
+  /**
+   * the actual output address of this instance, if known, or
+   * {@code -1} if not
+   */
+  private int address;
 
-    /** the opcode; one of the constants from {@link Dops} */
-    private final Dop opcode;
+  /** the opcode; one of the constants from {@link Dops} */
+  private final Dop opcode;
 
-    /** {@code non-null;} source position */
-    private final SourcePosition position;
+  /** {@code non-null;} source position */
+  private final SourcePosition position;
 
-    /** {@code non-null;} list of register arguments */
-    private final RegisterSpecList registers;
+  /** {@code non-null;} list of register arguments */
+  private final RegisterSpecList registers;
 
-    /**
-     * Makes a move instruction, appropriate and ideal for the given arguments.
-     *
-     * @param position {@code non-null;} source position information
-     * @param dest {@code non-null;} destination register
-     * @param src {@code non-null;} source register
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static SimpleInsn makeMove(SourcePosition position,
-            RegisterSpec dest, RegisterSpec src) {
-        boolean category1 = dest.getCategory() == 1;
-        boolean reference = dest.getType().isReference();
-        int destReg = dest.getReg();
-        int srcReg = src.getReg();
-        Dop opcode;
+  /**
+   * Makes a move instruction, appropriate and ideal for the given arguments.
+   *
+   * @param position {@code non-null;} source position information
+   * @param dest {@code non-null;} destination register
+   * @param src {@code non-null;} source register
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static SimpleInsn makeMove(SourcePosition position, RegisterSpec dest, RegisterSpec src) {
+    boolean category1 = dest.getCategory() == 1;
+    boolean reference = dest.getType().isReference();
+    int destReg = dest.getReg();
+    int srcReg = src.getReg();
+    Dop opcode;
 
-        if ((srcReg | destReg) < 16) {
-            opcode = reference ? Dops.MOVE_OBJECT :
-                (category1 ? Dops.MOVE : Dops.MOVE_WIDE);
-        } else if (destReg < 256) {
-            opcode = reference ? Dops.MOVE_OBJECT_FROM16 :
-                (category1 ? Dops.MOVE_FROM16 : Dops.MOVE_WIDE_FROM16);
-        } else {
-            opcode = reference ? Dops.MOVE_OBJECT_16 :
-                (category1 ? Dops.MOVE_16 : Dops.MOVE_WIDE_16);
-        }
-
-        return new SimpleInsn(opcode, position,
-                              RegisterSpecList.make(dest, src));
+    if ((srcReg | destReg) < 16) {
+      opcode = reference ? Dops.MOVE_OBJECT : (category1 ? Dops.MOVE : Dops.MOVE_WIDE);
+    } else if (destReg < 256) {
+      opcode = reference ? Dops.MOVE_OBJECT_FROM16
+          : (category1 ? Dops.MOVE_FROM16 : Dops.MOVE_WIDE_FROM16);
+    } else {
+      opcode = reference ? Dops.MOVE_OBJECT_16 : (category1 ? Dops.MOVE_16 : Dops.MOVE_WIDE_16);
     }
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * <p><b>Note:</b> In the unlikely event that an instruction takes
-     * absolutely no registers (e.g., a {@code nop} or a
-     * no-argument no-result static method call), then the given
-     * register list may be passed as {@link
-     * RegisterSpecList#EMPTY}.</p>
-     *
-     * @param opcode the opcode; one of the constants from {@link Dops}
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} register list, including a
-     * result register if appropriate (that is, registers may be either
-     * ins and outs)
-     */
-    public DalvInsn(Dop opcode, SourcePosition position,
-                    RegisterSpecList registers) {
-        if (opcode == null) {
-            throw new NullPointerException("opcode == null");
-        }
+    return new SimpleInsn(opcode, position, RegisterSpecList.make(dest, src));
+  }
 
-        if (position == null) {
-            throw new NullPointerException("position == null");
-        }
-
-        if (registers == null) {
-            throw new NullPointerException("registers == null");
-        }
-
-        this.address = -1;
-        this.opcode = opcode;
-        this.position = position;
-        this.registers = registers;
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * <p><b>Note:</b> In the unlikely event that an instruction takes
+   * absolutely no registers (e.g., a {@code nop} or a
+   * no-argument no-result static method call), then the given
+   * register list may be passed as {@link
+   * RegisterSpecList#EMPTY}.</p>
+   *
+   * @param opcode the opcode; one of the constants from {@link Dops}
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} register list, including a
+   * result register if appropriate (that is, registers may be either
+   * ins and outs)
+   */
+  public DalvInsn(Dop opcode, SourcePosition position, RegisterSpecList registers) {
+    if (opcode == null) {
+      throw new NullPointerException("opcode == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final String toString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        sb.append(identifierString());
-        sb.append(' ');
-        sb.append(position);
-
-        sb.append(": ");
-        sb.append(opcode.getName());
-
-        boolean needComma = false;
-        if (registers.size() != 0) {
-            sb.append(registers.toHuman(" ", ", ", null));
-            needComma = true;
-        }
-
-        String extra = argString();
-        if (extra != null) {
-            if (needComma) {
-                sb.append(',');
-            }
-            sb.append(' ');
-            sb.append(extra);
-        }
-
-        return sb.toString();
+    if (position == null) {
+      throw new NullPointerException("position == null");
     }
 
-    /**
-     * Gets whether the address of this instruction is known.
-     *
-     * @see #getAddress
-     * @see #setAddress
-     */
-    public final boolean hasAddress() {
-        return (address >= 0);
+    if (registers == null) {
+      throw new NullPointerException("registers == null");
     }
 
-    /**
-     * Gets the output address of this instruction, if it is known. This throws
-     * a {@code RuntimeException} if it has not yet been set.
-     *
-     * @see #setAddress
-     *
-     * @return {@code >= 0;} the output address
-     */
-    public final int getAddress() {
-        if (address < 0) {
-            throw new RuntimeException("address not yet known");
-        }
+    this.address = -1;
+    this.opcode = opcode;
+    this.position = position;
+    this.registers = registers;
+  }
 
-        return address;
+  /** {@inheritDoc} */
+  @Override
+  public final String toString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append(identifierString());
+    sb.append(' ');
+    sb.append(position);
+
+    sb.append(": ");
+    sb.append(opcode.getName());
+
+    boolean needComma = false;
+    if (registers.size() != 0) {
+      sb.append(registers.toHuman(" ", ", ", null));
+      needComma = true;
     }
 
-    /**
-     * Gets the opcode.
-     *
-     * @return {@code non-null;} the opcode
-     */
-    public final Dop getOpcode() {
-        return opcode;
+    String extra = argString();
+    if (extra != null) {
+      if (needComma) {
+        sb.append(',');
+      }
+      sb.append(' ');
+      sb.append(extra);
     }
 
-    /**
-     * Gets the source position.
-     *
-     * @return {@code non-null;} the source position
-     */
-    public final SourcePosition getPosition() {
-        return position;
+    return sb.toString();
+  }
+
+  /**
+   * Gets whether the address of this instruction is known.
+   *
+   * @see #getAddress
+   * @see #setAddress
+   */
+  public final boolean hasAddress() {
+    return (address >= 0);
+  }
+
+  /**
+   * Gets the output address of this instruction, if it is known. This throws
+   * a {@code RuntimeException} if it has not yet been set.
+   *
+   * @see #setAddress
+   *
+   * @return {@code >= 0;} the output address
+   */
+  public final int getAddress() {
+    if (address < 0) {
+      throw new RuntimeException("address not yet known");
     }
 
-    /**
-     * Gets the register list for this instruction.
-     *
-     * @return {@code non-null;} the registers
-     */
-    public final RegisterSpecList getRegisters() {
-        return registers;
+    return address;
+  }
+
+  /**
+   * Gets the opcode.
+   *
+   * @return {@code non-null;} the opcode
+   */
+  public final Dop getOpcode() {
+    return opcode;
+  }
+
+  /**
+   * Gets the source position.
+   *
+   * @return {@code non-null;} the source position
+   */
+  public final SourcePosition getPosition() {
+    return position;
+  }
+
+  /**
+   * Gets the register list for this instruction.
+   *
+   * @return {@code non-null;} the registers
+   */
+  public final RegisterSpecList getRegisters() {
+    return registers;
+  }
+
+  /**
+   * Returns whether this instance's opcode uses a result register.
+   * This method is a convenient shorthand for
+   * {@code getOpcode().hasResult()}.
+   *
+   * @return {@code true} iff this opcode uses a result register
+   */
+  public final boolean hasResult() {
+    return opcode.hasResult();
+  }
+
+  /**
+   * Gets the minimum distinct registers required for this instruction.
+   * Uses the given BitSet to determine which registers require
+   * replacement, and ignores registers that are already compatible.
+   * This assumes that the result (if any) can share registers with the
+   * sources (if any), that each source register is unique, and that
+   * (to be explicit here) category-2 values take up two consecutive
+   * registers.
+   *
+   * @param compatRegs {@code non-null;} set of compatible registers
+   * @return {@code >= 0;} the minimum distinct register requirement
+   */
+  public final int getMinimumRegisterRequirement(BitSet compatRegs) {
+    boolean hasResult = hasResult();
+    int regSz = registers.size();
+    int resultRequirement = 0;
+    int sourceRequirement = 0;
+
+    if (hasResult && !compatRegs.get(0)) {
+      resultRequirement = registers.get(0).getCategory();
     }
 
-    /**
-     * Returns whether this instance's opcode uses a result register.
-     * This method is a convenient shorthand for
-     * {@code getOpcode().hasResult()}.
-     *
-     * @return {@code true} iff this opcode uses a result register
-     */
-    public final boolean hasResult() {
-        return opcode.hasResult();
+    for (int i = hasResult ? 1 : 0; i < regSz; i++) {
+      if (!compatRegs.get(i)) {
+        sourceRequirement += registers.get(i).getCategory();
+      }
     }
 
-    /**
-     * Gets the minimum distinct registers required for this instruction.
-     * Uses the given BitSet to determine which registers require
-     * replacement, and ignores registers that are already compatible.
-     * This assumes that the result (if any) can share registers with the
-     * sources (if any), that each source register is unique, and that
-     * (to be explicit here) category-2 values take up two consecutive
-     * registers.
-     *
-     * @param compatRegs {@code non-null;} set of compatible registers
-     * @return {@code >= 0;} the minimum distinct register requirement
-     */
-    public final int getMinimumRegisterRequirement(BitSet compatRegs) {
-        boolean hasResult = hasResult();
-        int regSz = registers.size();
-        int resultRequirement = 0;
-        int sourceRequirement = 0;
+    return Math.max(sourceRequirement, resultRequirement);
+  }
 
-        if (hasResult && !compatRegs.get(0)) {
-            resultRequirement = registers.get(0).getCategory();
-        }
+  /**
+   * Gets the instruction that is equivalent to this one, except that
+   * it uses sequential registers starting at {@code 0} (storing
+   * the result, if any, in register {@code 0} as well).
+   *
+   * @return {@code non-null;} the replacement
+   */
+  public DalvInsn getLowRegVersion() {
+    RegisterSpecList regs = registers.withExpandedRegisters(0, hasResult(), null);
+    return withRegisters(regs);
+  }
 
-        for (int i = hasResult ? 1 : 0; i < regSz; i++) {
-            if (!compatRegs.get(i)) {
-                sourceRequirement += registers.get(i).getCategory();
-            }
-        }
+  /**
+   * Gets the instruction prefix required, if any, to use in an expanded
+   * version of this instance. Will not generate moves for registers
+   * marked compatible to the format by the given BitSet.
+   *
+   * @see #expandedVersion
+   *
+   * @param compatRegs {@code non-null;} set of compatible registers
+   * @return {@code null-ok;} the prefix, if any
+   */
+  public DalvInsn expandedPrefix(BitSet compatRegs) {
+    RegisterSpecList regs = registers;
+    boolean firstBit = compatRegs.get(0);
 
-        return Math.max(sourceRequirement, resultRequirement);
+    if (hasResult()) {
+      compatRegs.set(0);
     }
 
-    /**
-     * Gets the instruction that is equivalent to this one, except that
-     * it uses sequential registers starting at {@code 0} (storing
-     * the result, if any, in register {@code 0} as well).
-     *
-     * @return {@code non-null;} the replacement
-     */
-    public DalvInsn getLowRegVersion() {
-        RegisterSpecList regs =
-            registers.withExpandedRegisters(0, hasResult(), null);
-        return withRegisters(regs);
+    regs = regs.subset(compatRegs);
+
+    if (hasResult()) {
+      compatRegs.set(0, firstBit);
     }
 
-    /**
-     * Gets the instruction prefix required, if any, to use in an expanded
-     * version of this instance. Will not generate moves for registers
-     * marked compatible to the format by the given BitSet.
-     *
-     * @see #expandedVersion
-     *
-     * @param compatRegs {@code non-null;} set of compatible registers
-     * @return {@code null-ok;} the prefix, if any
-     */
-    public DalvInsn expandedPrefix(BitSet compatRegs) {
-        RegisterSpecList regs = registers;
-        boolean firstBit = compatRegs.get(0);
-
-        if (hasResult()) compatRegs.set(0);
-
-        regs = regs.subset(compatRegs);
-
-        if (hasResult()) compatRegs.set(0, firstBit);
-
-        if (regs.size() == 0) return null;
-
-        return new HighRegisterPrefix(position, regs);
+    if (regs.size() == 0) {
+      return null;
     }
 
-    /**
-     * Gets the instruction suffix required, if any, to use in an expanded
-     * version of this instance. Will not generate a move for a register
-     * marked compatible to the format by the given BitSet.
-     *
-     * @see #expandedVersion
-     *
-     * @param compatRegs {@code non-null;} set of compatible registers
-     * @return {@code null-ok;} the suffix, if any
-     */
-    public DalvInsn expandedSuffix(BitSet compatRegs) {
-        if (hasResult() && !compatRegs.get(0)) {
-            RegisterSpec r = registers.get(0);
-            return makeMove(position, r, r.withReg(0));
-        } else {
-            return null;
-        }
+    return new HighRegisterPrefix(position, regs);
+  }
+
+  /**
+   * Gets the instruction suffix required, if any, to use in an expanded
+   * version of this instance. Will not generate a move for a register
+   * marked compatible to the format by the given BitSet.
+   *
+   * @see #expandedVersion
+   *
+   * @param compatRegs {@code non-null;} set of compatible registers
+   * @return {@code null-ok;} the suffix, if any
+   */
+  public DalvInsn expandedSuffix(BitSet compatRegs) {
+    if (hasResult() && !compatRegs.get(0)) {
+      RegisterSpec r = registers.get(0);
+      return makeMove(position, r, r.withReg(0));
+    } else {
+      return null;
+    }
+  }
+
+  /**
+   * Gets the instruction that is equivalent to this one, except that
+   * it replaces incompatible registers with sequential registers
+   * starting at {@code 0} (storing the result, if any, in register
+   * {@code 0} as well). The sequence of instructions from
+   * {@link #expandedPrefix} and {@link #expandedSuffix} (if non-null)
+   * surrounding the result of a call to this method are the expanded
+   * transformation of this instance, and it is guaranteed that the
+   * number of low registers used will be the number returned by
+   * {@link #getMinimumRegisterRequirement}.
+   *
+   * @param compatRegs {@code non-null;} set of compatible registers
+   * @return {@code non-null;} the replacement
+   */
+  public DalvInsn expandedVersion(BitSet compatRegs) {
+    RegisterSpecList regs = registers.withExpandedRegisters(0, hasResult(), compatRegs);
+    return withRegisters(regs);
+  }
+
+  /**
+   * Gets the short identifier for this instruction. This is its
+   * address, if assigned, or its identity hashcode if not.
+   *
+   * @return {@code non-null;} the identifier
+   */
+  public final String identifierString() {
+    if (address != -1) {
+      return String.format("%04x", address);
     }
 
-    /**
-     * Gets the instruction that is equivalent to this one, except that
-     * it replaces incompatible registers with sequential registers
-     * starting at {@code 0} (storing the result, if any, in register
-     * {@code 0} as well). The sequence of instructions from
-     * {@link #expandedPrefix} and {@link #expandedSuffix} (if non-null)
-     * surrounding the result of a call to this method are the expanded
-     * transformation of this instance, and it is guaranteed that the
-     * number of low registers used will be the number returned by
-     * {@link #getMinimumRegisterRequirement}.
-     *
-     * @param compatRegs {@code non-null;} set of compatible registers
-     * @return {@code non-null;} the replacement
-     */
-    public DalvInsn expandedVersion(BitSet compatRegs) {
-        RegisterSpecList regs =
-            registers.withExpandedRegisters(0, hasResult(), compatRegs);
-        return withRegisters(regs);
+    return Hex.u4(System.identityHashCode(this));
+  }
+
+  /**
+   * Returns the string form of this instance suitable for inclusion in
+   * a human-oriented listing dump. This method will return {@code null}
+   * if this instance should not appear in a listing.
+   *
+   * @param prefix {@code non-null;} prefix before the address; each follow-on
+   * line will be indented to match as well
+   * @param width {@code >= 0;} the width of the output or {@code 0} for
+   * unlimited width
+   * @param noteIndices whether to include an explicit notation of
+   * constant pool indices
+   * @return {@code null-ok;} the string form or {@code null} if this
+   * instance should not appear in a listing
+   */
+  public final String listingString(String prefix, int width, boolean noteIndices) {
+    String insnPerSe = listingString0(noteIndices);
+
+    if (insnPerSe == null) {
+      return null;
     }
 
-    /**
-     * Gets the short identifier for this instruction. This is its
-     * address, if assigned, or its identity hashcode if not.
-     *
-     * @return {@code non-null;} the identifier
-     */
-    public final String identifierString() {
-        if (address != -1) {
-            return String.format("%04x", address);
-        }
+    String addr = prefix + identifierString() + ": ";
+    int w1 = addr.length();
+    int w2 = (width == 0) ? insnPerSe.length() : (width - w1);
 
-        return Hex.u4(System.identityHashCode(this));
+    return TwoColumnOutput.toString(addr, w1, "", insnPerSe, w2);
+  }
+
+  /**
+   * Sets the output address.
+   *
+   * @param address {@code >= 0;} the output address
+   */
+  public final void setAddress(int address) {
+    if (address < 0) {
+      throw new IllegalArgumentException("address < 0");
     }
 
-    /**
-     * Returns the string form of this instance suitable for inclusion in
-     * a human-oriented listing dump. This method will return {@code null}
-     * if this instance should not appear in a listing.
-     *
-     * @param prefix {@code non-null;} prefix before the address; each follow-on
-     * line will be indented to match as well
-     * @param width {@code >= 0;} the width of the output or {@code 0} for
-     * unlimited width
-     * @param noteIndices whether to include an explicit notation of
-     * constant pool indices
-     * @return {@code null-ok;} the string form or {@code null} if this
-     * instance should not appear in a listing
-     */
-    public final String listingString(String prefix, int width,
-            boolean noteIndices) {
-        String insnPerSe = listingString0(noteIndices);
+    this.address = address;
+  }
 
-        if (insnPerSe == null) {
-            return null;
-        }
+  /**
+   * Gets the address immediately after this instance. This is only
+   * calculable if this instance's address is known, and it is equal
+   * to the address plus the length of the instruction format of this
+   * instance's opcode.
+   *
+   * @return {@code >= 0;} the next address
+   */
+  public final int getNextAddress() {
+    return getAddress() + codeSize();
+  }
 
-        String addr = prefix + identifierString() + ": ";
-        int w1 = addr.length();
-        int w2 = (width == 0) ? insnPerSe.length() : (width - w1);
+  /**
+   * Gets the size of this instruction, in 16-bit code units.
+   *
+   * @return {@code >= 0;} the code size of this instruction
+   */
+  public abstract int codeSize();
 
-        return TwoColumnOutput.toString(addr, w1, "", insnPerSe, w2);
-    }
+  /**
+   * Writes this instance to the given output. This method should
+   * never annotate the output.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  public abstract void writeTo(AnnotatedOutput out);
 
-    /**
-     * Sets the output address.
-     *
-     * @param address {@code >= 0;} the output address
-     */
-    public final void setAddress(int address) {
-        if (address < 0) {
-            throw new IllegalArgumentException("address < 0");
-        }
+  /**
+   * Returns an instance that is just like this one, except that its
+   * opcode is replaced by the one given, and its address is reset.
+   *
+   * @param opcode {@code non-null;} the new opcode
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract DalvInsn withOpcode(Dop opcode);
 
-        this.address = address;
-    }
+  /**
+   * Returns an instance that is just like this one, except that all
+   * register references have been offset by the given delta, and its
+   * address is reset.
+   *
+   * @param delta the amount to offset register references by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract DalvInsn withRegisterOffset(int delta);
 
-    /**
-     * Gets the address immediately after this instance. This is only
-     * calculable if this instance's address is known, and it is equal
-     * to the address plus the length of the instruction format of this
-     * instance's opcode.
-     *
-     * @return {@code >= 0;} the next address
-     */
-    public final int getNextAddress() {
-        return getAddress() + codeSize();
-    }
+  /**
+   * Returns an instance that is just like this one, except that the
+   * register list is replaced by the given one, and its address is
+   * reset.
+   *
+   * @param registers {@code non-null;} new register list
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract DalvInsn withRegisters(RegisterSpecList registers);
 
-    /**
-     * Gets the size of this instruction, in 16-bit code units.
-     *
-     * @return {@code >= 0;} the code size of this instruction
-     */
-    public abstract int codeSize();
+  /**
+   * Gets the string form for any arguments to this instance. Subclasses
+   * must override this.
+   *
+   * @return {@code null-ok;} the string version of any arguments or
+   * {@code null} if there are none
+   */
+  protected abstract String argString();
 
-    /**
-     * Writes this instance to the given output. This method should
-     * never annotate the output.
-     *
-     * @param out {@code non-null;} where to write to
-     */
-    public abstract void writeTo(AnnotatedOutput out);
-
-    /**
-     * Returns an instance that is just like this one, except that its
-     * opcode is replaced by the one given, and its address is reset.
-     *
-     * @param opcode {@code non-null;} the new opcode
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract DalvInsn withOpcode(Dop opcode);
-
-    /**
-     * Returns an instance that is just like this one, except that all
-     * register references have been offset by the given delta, and its
-     * address is reset.
-     *
-     * @param delta the amount to offset register references by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract DalvInsn withRegisterOffset(int delta);
-
-    /**
-     * Returns an instance that is just like this one, except that the
-     * register list is replaced by the given one, and its address is
-     * reset.
-     *
-     * @param registers {@code non-null;} new register list
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract DalvInsn withRegisters(RegisterSpecList registers);
-
-    /**
-     * Gets the string form for any arguments to this instance. Subclasses
-     * must override this.
-     *
-     * @return {@code null-ok;} the string version of any arguments or
-     * {@code null} if there are none
-     */
-    protected abstract String argString();
-
-    /**
-     * Helper for {@link #listingString}, which returns the string
-     * form of this instance suitable for inclusion in a
-     * human-oriented listing dump, not including the instruction
-     * address and without respect for any output formatting. This
-     * method should return {@code null} if this instance should
-     * not appear in a listing.
-     *
-     * @param noteIndices whether to include an explicit notation of
-     * constant pool indices
-     * @return {@code null-ok;} the listing string
-     */
-    protected abstract String listingString0(boolean noteIndices);
+  /**
+   * Helper for {@link #listingString}, which returns the string
+   * form of this instance suitable for inclusion in a
+   * human-oriented listing dump, not including the instruction
+   * address and without respect for any output formatting. This
+   * method should return {@code null} if this instance should
+   * not appear in a listing.
+   *
+   * @param noteIndices whether to include an explicit notation of
+   * constant pool indices
+   * @return {@code null-ok;} the listing string
+   */
+  protected abstract String listingString0(boolean noteIndices);
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/DalvInsnList.java b/dx/src/com/android/jack/dx/dex/code/DalvInsnList.java
index 80fe920..1d453d9 100644
--- a/dx/src/com/android/jack/dx/dex/code/DalvInsnList.java
+++ b/dx/src/com/android/jack/dx/dex/code/DalvInsnList.java
@@ -35,235 +35,231 @@
  */
 public final class DalvInsnList extends FixedSizeList {
 
-    /**
-     * The amount of register space, in register units, required for this
-     * code block. This may be greater than the largest observed register+
-     * category because the method this code block exists in may
-     * specify arguments that are unused by the method.
-     */
-    private final int regCount;
+  /**
+   * The amount of register space, in register units, required for this
+   * code block. This may be greater than the largest observed register+
+   * category because the method this code block exists in may
+   * specify arguments that are unused by the method.
+   */
+  private final int regCount;
 
-    /**
-     * Constructs and returns an immutable instance whose elements are
-     * identical to the ones in the given list, in the same order.
-     *
-     * @param list {@code non-null;} the list to use for elements
-     * @param regCount count, in register-units, of the number of registers
-     * this code block requires.
-     * @return {@code non-null;} an appropriately-constructed instance of this
-     * class
-     */
-    public static DalvInsnList makeImmutable(ArrayList<DalvInsn> list,
-            int regCount) {
-        int size = list.size();
-        DalvInsnList result = new DalvInsnList(size, regCount);
+  /**
+   * Constructs and returns an immutable instance whose elements are
+   * identical to the ones in the given list, in the same order.
+   *
+   * @param list {@code non-null;} the list to use for elements
+   * @param regCount count, in register-units, of the number of registers
+   * this code block requires.
+   * @return {@code non-null;} an appropriately-constructed instance of this
+   * class
+   */
+  public static DalvInsnList makeImmutable(ArrayList<DalvInsn> list, int regCount) {
+    int size = list.size();
+    DalvInsnList result = new DalvInsnList(size, regCount);
 
-        for (int i = 0; i < size; i++) {
-            result.set(i, list.get(i));
+    for (int i = 0; i < size; i++) {
+      result.set(i, list.get(i));
+    }
+
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public DalvInsnList(int size, int regCount) {
+    super(size);
+    this.regCount = regCount;
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public DalvInsn get(int n) {
+    return (DalvInsn) get0(n);
+  }
+
+  /**
+   * Sets the instruction at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param insn {@code non-null;} the instruction to set at {@code n}
+   */
+  public void set(int n, DalvInsn insn) {
+    set0(n, insn);
+  }
+
+  /**
+   * Gets the size of this instance, in 16-bit code units. This will only
+   * return a meaningful result if the instructions in this instance all
+   * have valid addresses.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int codeSize() {
+    int sz = size();
+
+    if (sz == 0) {
+      return 0;
+    }
+
+    DalvInsn last = get(sz - 1);
+    return last.getNextAddress();
+  }
+
+  /**
+   * Writes all the instructions in this instance to the given output
+   * destination.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  public void writeTo(AnnotatedOutput out) {
+    int startCursor = out.getCursor();
+    int sz = size();
+
+    if (out.annotates()) {
+      boolean verbose = out.isVerbose();
+
+      for (int i = 0; i < sz; i++) {
+        DalvInsn insn = (DalvInsn) get0(i);
+        int codeBytes = insn.codeSize() * 2;
+        String s;
+
+        if ((codeBytes != 0) || verbose) {
+          s = insn.listingString("  ", out.getAnnotationWidth(), true);
+        } else {
+          s = null;
         }
 
-        result.setImmutable();
-        return result;
+        if (s != null) {
+          out.annotate(codeBytes, s);
+        } else if (codeBytes != 0) {
+          out.annotate(codeBytes, "");
+        }
+      }
     }
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public DalvInsnList(int size, int regCount) {
-        super(size);
-        this.regCount = regCount;
+    for (int i = 0; i < sz; i++) {
+      DalvInsn insn = (DalvInsn) get0(i);
+      try {
+        insn.writeTo(out);
+      } catch (RuntimeException ex) {
+        throw ExceptionWithContext.withContext(ex, "...while writing " + insn);
+      }
     }
 
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public DalvInsn get(int n) {
-        return (DalvInsn) get0(n);
+    // Sanity check of the amount written.
+    int written = (out.getCursor() - startCursor) / 2;
+    if (written != codeSize()) {
+      throw new RuntimeException(
+          "write length mismatch; expected " + codeSize() + " but actually wrote " + written);
+    }
+  }
+
+  /**
+   * Gets the minimum required register count implied by this
+   * instance.  This includes any unused parameters that could
+   * potentially be at the top of the register space.
+   * @return {@code >= 0;} the required registers size
+   */
+  public int getRegistersSize() {
+    return regCount;
+  }
+
+  /**
+   * Gets the size of the outgoing arguments area required by this
+   * method. This is equal to the largest argument word count of any
+   * method referred to by this instance.
+   *
+   * @return {@code >= 0;} the required outgoing arguments size
+   */
+  public int getOutsSize() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      DalvInsn insn = (DalvInsn) get0(i);
+
+      if (!(insn instanceof CstInsn)) {
+        continue;
+      }
+
+      Constant cst = ((CstInsn) insn).getConstant();
+
+      if (!(cst instanceof CstBaseMethodRef)) {
+        continue;
+      }
+
+      boolean isStatic = (insn.getOpcode().getFamily() == Opcodes.INVOKE_STATIC);
+      int count = ((CstBaseMethodRef) cst).getParameterWordCount(isStatic);
+
+      if (count > result) {
+        result = count;
+      }
     }
 
-    /**
-     * Sets the instruction at the given index.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param insn {@code non-null;} the instruction to set at {@code n}
-     */
-    public void set(int n, DalvInsn insn) {
-        set0(n, insn);
-    }
+    return result;
+  }
 
-    /**
-     * Gets the size of this instance, in 16-bit code units. This will only
-     * return a meaningful result if the instructions in this instance all
-     * have valid addresses.
-     *
-     * @return {@code >= 0;} the size
-     */
-    public int codeSize() {
-        int sz = size();
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} prefix to attach to each line of output
+   * @param verbose whether to be verbose; verbose output includes
+   * lines for zero-size instructions and explicit constant pool indices
+   */
+  public void debugPrint(Writer out, String prefix, boolean verbose) {
+    @SuppressWarnings("resource")
+    IndentingWriter iw = new IndentingWriter(out, 0, prefix);
+    int sz = size();
 
-        if (sz == 0) {
-            return 0;
+    try {
+      for (int i = 0; i < sz; i++) {
+        DalvInsn insn = (DalvInsn) get0(i);
+        String s;
+
+        if ((insn.codeSize() != 0) || verbose) {
+          s = insn.listingString("", 0, verbose);
+        } else {
+          s = null;
         }
 
-        DalvInsn last = get(sz - 1);
-        return last.getNextAddress();
-    }
-
-    /**
-     * Writes all the instructions in this instance to the given output
-     * destination.
-     *
-     * @param out {@code non-null;} where to write to
-     */
-    public void writeTo(AnnotatedOutput out) {
-        int startCursor = out.getCursor();
-        int sz = size();
-
-        if (out.annotates()) {
-            boolean verbose = out.isVerbose();
-
-            for (int i = 0; i < sz; i++) {
-                DalvInsn insn = (DalvInsn) get0(i);
-                int codeBytes = insn.codeSize() * 2;
-                String s;
-
-                if ((codeBytes != 0) || verbose) {
-                    s = insn.listingString("  ", out.getAnnotationWidth(),
-                            true);
-                } else {
-                    s = null;
-                }
-
-                if (s != null) {
-                    out.annotate(codeBytes, s);
-                } else if (codeBytes != 0) {
-                    out.annotate(codeBytes, "");
-                }
-            }
+        if (s != null) {
+          iw.write(s);
         }
+      }
 
-        for (int i = 0; i < sz; i++) {
-            DalvInsn insn = (DalvInsn) get0(i);
-            try {
-                insn.writeTo(out);
-            } catch (RuntimeException ex) {
-                throw ExceptionWithContext.withContext(ex,
-                        "...while writing " + insn);
-            }
-        }
-
-        // Sanity check of the amount written.
-        int written = (out.getCursor() - startCursor) / 2;
-        if (written != codeSize()) {
-            throw new RuntimeException("write length mismatch; expected " +
-                    codeSize() + " but actually wrote " + written);
-        }
+      iw.flush();
+    } catch (IOException ex) {
+      throw new RuntimeException(ex);
     }
+  }
 
-    /**
-     * Gets the minimum required register count implied by this
-     * instance.  This includes any unused parameters that could
-     * potentially be at the top of the register space.
-     * @return {@code >= 0;} the required registers size
-     */
-    public int getRegistersSize() {
-        return regCount;
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} prefix to attach to each line of output
+   * @param verbose whether to be verbose; verbose output includes
+   * lines for zero-size instructions
+   */
+  public void debugPrint(OutputStream out, String prefix, boolean verbose) {
+    Writer w = new OutputStreamWriter(out);
+    debugPrint(w, prefix, verbose);
+
+    try {
+      w.flush();
+    } catch (IOException ex) {
+      throw new RuntimeException(ex);
     }
-
-    /**
-     * Gets the size of the outgoing arguments area required by this
-     * method. This is equal to the largest argument word count of any
-     * method referred to by this instance.
-     *
-     * @return {@code >= 0;} the required outgoing arguments size
-     */
-    public int getOutsSize() {
-        int sz = size();
-        int result = 0;
-
-        for (int i = 0; i < sz; i++) {
-            DalvInsn insn = (DalvInsn) get0(i);
-
-            if (!(insn instanceof CstInsn)) {
-                continue;
-            }
-
-            Constant cst = ((CstInsn) insn).getConstant();
-
-            if (!(cst instanceof CstBaseMethodRef)) {
-                continue;
-            }
-
-            boolean isStatic =
-                (insn.getOpcode().getFamily() == Opcodes.INVOKE_STATIC);
-            int count =
-                ((CstBaseMethodRef) cst).getParameterWordCount(isStatic);
-
-            if (count > result) {
-                result = count;
-            }
-        }
-
-        return result;
-    }
-
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} prefix to attach to each line of output
-     * @param verbose whether to be verbose; verbose output includes
-     * lines for zero-size instructions and explicit constant pool indices
-     */
-    public void debugPrint(Writer out, String prefix, boolean verbose) {
-        IndentingWriter iw = new IndentingWriter(out, 0, prefix);
-        int sz = size();
-
-        try {
-            for (int i = 0; i < sz; i++) {
-                DalvInsn insn = (DalvInsn) get0(i);
-                String s;
-
-                if ((insn.codeSize() != 0) || verbose) {
-                    s = insn.listingString("", 0, verbose);
-                } else {
-                    s = null;
-                }
-
-                if (s != null) {
-                    iw.write(s);
-                }
-            }
-
-            iw.flush();
-        } catch (IOException ex) {
-            throw new RuntimeException(ex);
-        }
-    }
-
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} prefix to attach to each line of output
-     * @param verbose whether to be verbose; verbose output includes
-     * lines for zero-size instructions
-     */
-    public void debugPrint(OutputStream out, String prefix, boolean verbose) {
-        Writer w = new OutputStreamWriter(out);
-        debugPrint(w, prefix, verbose);
-
-        try {
-            w.flush();
-        } catch (IOException ex) {
-            throw new RuntimeException(ex);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/Dop.java b/dx/src/com/android/jack/dx/dex/code/Dop.java
index 5b390aa..0a0cbc2 100644
--- a/dx/src/com/android/jack/dx/dex/code/Dop.java
+++ b/dx/src/com/android/jack/dx/dex/code/Dop.java
@@ -23,151 +23,162 @@
  * Representation of an opcode.
  */
 public final class Dop {
-    /** {@code Opcodes.isValid();} the opcode value itself */
-    private final int opcode;
+  /** {@code Opcodes.isValid();} the opcode value itself */
+  private final int opcode;
 
-    /** {@code Opcodes.isValid();} the opcode family */
-    private final int family;
+  /** {@code Opcodes.isValid();} the opcode family */
+  private final int family;
 
-    /**
-     * {@code Opcodes.isValid();} what opcode (by number) to try next
-     * when attempting to match an opcode to particular arguments;
-     * {@code Opcodes.NO_NEXT} to indicate that this is the last
-     * opcode to try in a particular chain
-     */
-    private final int nextOpcode;
+  /**
+   * {@code Opcodes.isValid();} what opcode (by number) to try next
+   * when attempting to match an opcode to particular arguments;
+   * {@code Opcodes.NO_NEXT} to indicate that this is the last
+   * opcode to try in a particular chain
+   */
+  private final int nextOpcode;
 
-    /** {@code non-null;} the instruction format */
-    private final InsnFormat format;
+  /** {@code non-null;} the instruction format */
+  private final InsnFormat format;
 
-    /** whether this opcode uses a result register */
-    private final boolean hasResult;
+  /** whether this opcode uses a result register */
+  private final boolean hasResult;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code Opcodes.isValid();} the opcode value
-     * itself
-     * @param family {@code Opcodes.isValid();} the opcode family
-     * @param nextOpcode {@code Opcodes.isValid();} what opcode (by
-     * number) to try next when attempting to match an opcode to
-     * particular arguments; {@code Opcodes.NO_NEXT} to indicate that
-     * this is the last opcode to try in a particular chain
-     * @param format {@code non-null;} the instruction format
-     * @param hasResult whether the opcode has a result register; if so it
-     * is always the first register
-     */
-    public Dop(int opcode, int family, int nextOpcode, InsnFormat format,
-            boolean hasResult) {
-        if (!Opcodes.isValidShape(opcode)) {
-            throw new IllegalArgumentException("bogus opcode");
-        }
-
-        if (!Opcodes.isValidShape(family)) {
-            throw new IllegalArgumentException("bogus family");
-        }
-
-        if (!Opcodes.isValidShape(nextOpcode)) {
-            throw new IllegalArgumentException("bogus nextOpcode");
-        }
-
-        if (format == null) {
-            throw new NullPointerException("format == null");
-        }
-
-        this.opcode = opcode;
-        this.family = family;
-        this.nextOpcode = nextOpcode;
-        this.format = format;
-        this.hasResult = hasResult;
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code Opcodes.isValid();} the opcode value
+   * itself
+   * @param family {@code Opcodes.isValid();} the opcode family
+   * @param nextOpcode {@code Opcodes.isValid();} what opcode (by
+   * number) to try next when attempting to match an opcode to
+   * particular arguments; {@code Opcodes.NO_NEXT} to indicate that
+   * this is the last opcode to try in a particular chain
+   * @param format {@code non-null;} the instruction format
+   * @param hasResult whether the opcode has a result register; if so it
+   * is always the first register
+   */
+  public Dop(int opcode, int family, int nextOpcode, InsnFormat format, boolean hasResult) {
+    if (!Opcodes.isValidShape(opcode)) {
+      throw new IllegalArgumentException("bogus opcode");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return getName();
+    if (!Opcodes.isValidShape(family)) {
+      throw new IllegalArgumentException("bogus family");
     }
 
-    /**
-     * Gets the opcode value.
-     *
-     * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode value
-     */
-    public int getOpcode() {
-        return opcode;
+    if (!Opcodes.isValidShape(nextOpcode)) {
+      throw new IllegalArgumentException("bogus nextOpcode");
     }
 
-    /**
-     * Gets the opcode family. The opcode family is the unmarked (no
-     * "/...") opcode that has equivalent semantics to this one.
-     *
-     * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode family
-     */
-    public int getFamily() {
-        return family;
+    if (format == null) {
+      throw new NullPointerException("format == null");
     }
 
-    /**
-     * Gets the instruction format.
-     *
-     * @return {@code non-null;} the instruction format
-     */
-    public InsnFormat getFormat() {
-        return format;
+    this.opcode = opcode;
+    this.family = family;
+    this.nextOpcode = nextOpcode;
+    this.format = format;
+    this.hasResult = hasResult;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return getName();
+  }
+
+  /**
+   * Gets the opcode value.
+   *
+   * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode value
+   */
+  public int getOpcode() {
+    return opcode;
+  }
+
+  /**
+   * Gets the opcode family. The opcode family is the unmarked (no
+   * "/...") opcode that has equivalent semantics to this one.
+   *
+   * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode family
+   */
+  public int getFamily() {
+    return family;
+  }
+
+  /**
+   * Gets the instruction format.
+   *
+   * @return {@code non-null;} the instruction format
+   */
+  public InsnFormat getFormat() {
+    return format;
+  }
+
+  /**
+   * Returns whether this opcode uses a result register.
+   *
+   * @return {@code true} iff this opcode uses a result register
+   */
+  public boolean hasResult() {
+    return hasResult;
+  }
+
+  /**
+   * Gets the opcode name.
+   *
+   * @return {@code non-null;} the opcode name
+   */
+  public String getName() {
+    return OpcodeInfo.getName(opcode);
+  }
+
+  /**
+   * Gets the opcode value to try next when attempting to match an
+   * opcode to particular arguments. This returns {@code
+   * Opcodes.NO_NEXT} to indicate that this is the last opcode to
+   * try in a particular chain.
+   *
+   * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode value
+   */
+  public int getNextOpcode() {
+    return nextOpcode;
+  }
+
+  /**
+   * Gets the opcode for the opposite test of this instance. This is only
+   * valid for opcodes which are in fact tests.
+   *
+   * @return {@code non-null;} the opposite test
+   */
+  public Dop getOppositeTest() {
+    switch (opcode) {
+      case Opcodes.IF_EQ:
+        return Dops.IF_NE;
+      case Opcodes.IF_NE:
+        return Dops.IF_EQ;
+      case Opcodes.IF_LT:
+        return Dops.IF_GE;
+      case Opcodes.IF_GE:
+        return Dops.IF_LT;
+      case Opcodes.IF_GT:
+        return Dops.IF_LE;
+      case Opcodes.IF_LE:
+        return Dops.IF_GT;
+      case Opcodes.IF_EQZ:
+        return Dops.IF_NEZ;
+      case Opcodes.IF_NEZ:
+        return Dops.IF_EQZ;
+      case Opcodes.IF_LTZ:
+        return Dops.IF_GEZ;
+      case Opcodes.IF_GEZ:
+        return Dops.IF_LTZ;
+      case Opcodes.IF_GTZ:
+        return Dops.IF_LEZ;
+      case Opcodes.IF_LEZ:
+        return Dops.IF_GTZ;
     }
 
-    /**
-     * Returns whether this opcode uses a result register.
-     *
-     * @return {@code true} iff this opcode uses a result register
-     */
-    public boolean hasResult() {
-        return hasResult;
-    }
-
-    /**
-     * Gets the opcode name.
-     *
-     * @return {@code non-null;} the opcode name
-     */
-    public String getName() {
-        return OpcodeInfo.getName(opcode);
-    }
-
-    /**
-     * Gets the opcode value to try next when attempting to match an
-     * opcode to particular arguments. This returns {@code
-     * Opcodes.NO_NEXT} to indicate that this is the last opcode to
-     * try in a particular chain.
-     *
-     * @return {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the opcode value
-     */
-    public int getNextOpcode() {
-        return nextOpcode;
-    }
-
-    /**
-     * Gets the opcode for the opposite test of this instance. This is only
-     * valid for opcodes which are in fact tests.
-     *
-     * @return {@code non-null;} the opposite test
-     */
-    public Dop getOppositeTest() {
-        switch (opcode) {
-            case Opcodes.IF_EQ:  return Dops.IF_NE;
-            case Opcodes.IF_NE:  return Dops.IF_EQ;
-            case Opcodes.IF_LT:  return Dops.IF_GE;
-            case Opcodes.IF_GE:  return Dops.IF_LT;
-            case Opcodes.IF_GT:  return Dops.IF_LE;
-            case Opcodes.IF_LE:  return Dops.IF_GT;
-            case Opcodes.IF_EQZ: return Dops.IF_NEZ;
-            case Opcodes.IF_NEZ: return Dops.IF_EQZ;
-            case Opcodes.IF_LTZ: return Dops.IF_GEZ;
-            case Opcodes.IF_GEZ: return Dops.IF_LTZ;
-            case Opcodes.IF_GTZ: return Dops.IF_LEZ;
-            case Opcodes.IF_LEZ: return Dops.IF_GTZ;
-        }
-
-        throw new IllegalArgumentException("bogus opcode: " + this);
-    }
+    throw new IllegalArgumentException("bogus opcode: " + this);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/Dops.java b/dx/src/com/android/jack/dx/dex/code/Dops.java
index 39ea0d3..acaff76 100644
--- a/dx/src/com/android/jack/dx/dex/code/Dops.java
+++ b/dx/src/com/android/jack/dx/dex/code/Dops.java
@@ -49,1181 +49,962 @@
  * them.
  */
 public final class Dops {
-    /** {@code non-null;} array containing all the standard instances */
-    private static final Dop[] DOPS;
+  /** {@code non-null;} array containing all the standard instances */
+  private static final Dop[] DOPS;
 
-    /**
-     * pseudo-opcode used for nonstandard formatted "instructions"
-     * (which are mostly not actually instructions, though they do
-     * appear in instruction lists). TODO: Retire the usage of this
-     * constant.
-     */
-    public static final Dop SPECIAL_FORMAT =
-        new Dop(Opcodes.SPECIAL_FORMAT, Opcodes.SPECIAL_FORMAT,
-                Opcodes.NO_NEXT, SpecialFormat.THE_ONE, false);
+  /**
+   * pseudo-opcode used for nonstandard formatted "instructions"
+   * (which are mostly not actually instructions, though they do
+   * appear in instruction lists). TODO(dx team): Retire the usage of this
+   * constant.
+   */
+  public static final Dop SPECIAL_FORMAT = new Dop(Opcodes.SPECIAL_FORMAT, Opcodes.SPECIAL_FORMAT,
+      Opcodes.NO_NEXT, SpecialFormat.THE_ONE, false);
 
-    // BEGIN(dops); GENERATED AUTOMATICALLY BY opcode-gen
-    public static final Dop NOP =
-        new Dop(Opcodes.NOP, Opcodes.NOP,
-            Opcodes.NO_NEXT, Form10x.THE_ONE, false);
+  // BEGIN(dops); GENERATED AUTOMATICALLY BY opcode-gen
+  public static final Dop NOP =
+      new Dop(Opcodes.NOP, Opcodes.NOP, Opcodes.NO_NEXT, Form10x.THE_ONE, false);
 
-    public static final Dop MOVE =
-        new Dop(Opcodes.MOVE, Opcodes.MOVE,
-            Opcodes.MOVE_FROM16, Form12x.THE_ONE, true);
+  public static final Dop MOVE =
+      new Dop(Opcodes.MOVE, Opcodes.MOVE, Opcodes.MOVE_FROM16, Form12x.THE_ONE, true);
 
-    public static final Dop MOVE_FROM16 =
-        new Dop(Opcodes.MOVE_FROM16, Opcodes.MOVE,
-            Opcodes.MOVE_16, Form22x.THE_ONE, true);
+  public static final Dop MOVE_FROM16 =
+      new Dop(Opcodes.MOVE_FROM16, Opcodes.MOVE, Opcodes.MOVE_16, Form22x.THE_ONE, true);
 
-    public static final Dop MOVE_16 =
-        new Dop(Opcodes.MOVE_16, Opcodes.MOVE,
-            Opcodes.NO_NEXT, Form32x.THE_ONE, true);
+  public static final Dop MOVE_16 =
+      new Dop(Opcodes.MOVE_16, Opcodes.MOVE, Opcodes.NO_NEXT, Form32x.THE_ONE, true);
 
-    public static final Dop MOVE_WIDE =
-        new Dop(Opcodes.MOVE_WIDE, Opcodes.MOVE_WIDE,
-            Opcodes.MOVE_WIDE_FROM16, Form12x.THE_ONE, true);
+  public static final Dop MOVE_WIDE = new Dop(Opcodes.MOVE_WIDE, Opcodes.MOVE_WIDE,
+      Opcodes.MOVE_WIDE_FROM16, Form12x.THE_ONE, true);
 
-    public static final Dop MOVE_WIDE_FROM16 =
-        new Dop(Opcodes.MOVE_WIDE_FROM16, Opcodes.MOVE_WIDE,
-            Opcodes.MOVE_WIDE_16, Form22x.THE_ONE, true);
+  public static final Dop MOVE_WIDE_FROM16 = new Dop(Opcodes.MOVE_WIDE_FROM16, Opcodes.MOVE_WIDE,
+      Opcodes.MOVE_WIDE_16, Form22x.THE_ONE, true);
 
-    public static final Dop MOVE_WIDE_16 =
-        new Dop(Opcodes.MOVE_WIDE_16, Opcodes.MOVE_WIDE,
-            Opcodes.NO_NEXT, Form32x.THE_ONE, true);
+  public static final Dop MOVE_WIDE_16 =
+      new Dop(Opcodes.MOVE_WIDE_16, Opcodes.MOVE_WIDE, Opcodes.NO_NEXT, Form32x.THE_ONE, true);
 
-    public static final Dop MOVE_OBJECT =
-        new Dop(Opcodes.MOVE_OBJECT, Opcodes.MOVE_OBJECT,
-            Opcodes.MOVE_OBJECT_FROM16, Form12x.THE_ONE, true);
+  public static final Dop MOVE_OBJECT = new Dop(Opcodes.MOVE_OBJECT, Opcodes.MOVE_OBJECT,
+      Opcodes.MOVE_OBJECT_FROM16, Form12x.THE_ONE, true);
 
-    public static final Dop MOVE_OBJECT_FROM16 =
-        new Dop(Opcodes.MOVE_OBJECT_FROM16, Opcodes.MOVE_OBJECT,
-            Opcodes.MOVE_OBJECT_16, Form22x.THE_ONE, true);
+  public static final Dop MOVE_OBJECT_FROM16 = new Dop(Opcodes.MOVE_OBJECT_FROM16,
+      Opcodes.MOVE_OBJECT, Opcodes.MOVE_OBJECT_16, Form22x.THE_ONE, true);
 
-    public static final Dop MOVE_OBJECT_16 =
-        new Dop(Opcodes.MOVE_OBJECT_16, Opcodes.MOVE_OBJECT,
-            Opcodes.NO_NEXT, Form32x.THE_ONE, true);
+  public static final Dop MOVE_OBJECT_16 =
+      new Dop(Opcodes.MOVE_OBJECT_16, Opcodes.MOVE_OBJECT, Opcodes.NO_NEXT, Form32x.THE_ONE, true);
 
-    public static final Dop MOVE_RESULT =
-        new Dop(Opcodes.MOVE_RESULT, Opcodes.MOVE_RESULT,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, true);
+  public static final Dop MOVE_RESULT =
+      new Dop(Opcodes.MOVE_RESULT, Opcodes.MOVE_RESULT, Opcodes.NO_NEXT, Form11x.THE_ONE, true);
 
-    public static final Dop MOVE_RESULT_WIDE =
-        new Dop(Opcodes.MOVE_RESULT_WIDE, Opcodes.MOVE_RESULT_WIDE,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, true);
+  public static final Dop MOVE_RESULT_WIDE = new Dop(Opcodes.MOVE_RESULT_WIDE,
+      Opcodes.MOVE_RESULT_WIDE, Opcodes.NO_NEXT, Form11x.THE_ONE, true);
 
-    public static final Dop MOVE_RESULT_OBJECT =
-        new Dop(Opcodes.MOVE_RESULT_OBJECT, Opcodes.MOVE_RESULT_OBJECT,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, true);
+  public static final Dop MOVE_RESULT_OBJECT = new Dop(Opcodes.MOVE_RESULT_OBJECT,
+      Opcodes.MOVE_RESULT_OBJECT, Opcodes.NO_NEXT, Form11x.THE_ONE, true);
 
-    public static final Dop MOVE_EXCEPTION =
-        new Dop(Opcodes.MOVE_EXCEPTION, Opcodes.MOVE_EXCEPTION,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, true);
+  public static final Dop MOVE_EXCEPTION = new Dop(Opcodes.MOVE_EXCEPTION, Opcodes.MOVE_EXCEPTION,
+      Opcodes.NO_NEXT, Form11x.THE_ONE, true);
 
-    public static final Dop RETURN_VOID =
-        new Dop(Opcodes.RETURN_VOID, Opcodes.RETURN_VOID,
-            Opcodes.NO_NEXT, Form10x.THE_ONE, false);
+  public static final Dop RETURN_VOID =
+      new Dop(Opcodes.RETURN_VOID, Opcodes.RETURN_VOID, Opcodes.NO_NEXT, Form10x.THE_ONE, false);
 
-    public static final Dop RETURN =
-        new Dop(Opcodes.RETURN, Opcodes.RETURN,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop RETURN =
+      new Dop(Opcodes.RETURN, Opcodes.RETURN, Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop RETURN_WIDE =
-        new Dop(Opcodes.RETURN_WIDE, Opcodes.RETURN_WIDE,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop RETURN_WIDE =
+      new Dop(Opcodes.RETURN_WIDE, Opcodes.RETURN_WIDE, Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop RETURN_OBJECT =
-        new Dop(Opcodes.RETURN_OBJECT, Opcodes.RETURN_OBJECT,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop RETURN_OBJECT = new Dop(Opcodes.RETURN_OBJECT, Opcodes.RETURN_OBJECT,
+      Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop CONST_4 =
-        new Dop(Opcodes.CONST_4, Opcodes.CONST,
-            Opcodes.CONST_16, Form11n.THE_ONE, true);
+  public static final Dop CONST_4 =
+      new Dop(Opcodes.CONST_4, Opcodes.CONST, Opcodes.CONST_16, Form11n.THE_ONE, true);
 
-    public static final Dop CONST_16 =
-        new Dop(Opcodes.CONST_16, Opcodes.CONST,
-            Opcodes.CONST_HIGH16, Form21s.THE_ONE, true);
+  public static final Dop CONST_16 =
+      new Dop(Opcodes.CONST_16, Opcodes.CONST, Opcodes.CONST_HIGH16, Form21s.THE_ONE, true);
 
-    public static final Dop CONST =
-        new Dop(Opcodes.CONST, Opcodes.CONST,
-            Opcodes.NO_NEXT, Form31i.THE_ONE, true);
+  public static final Dop CONST =
+      new Dop(Opcodes.CONST, Opcodes.CONST, Opcodes.NO_NEXT, Form31i.THE_ONE, true);
 
-    public static final Dop CONST_HIGH16 =
-        new Dop(Opcodes.CONST_HIGH16, Opcodes.CONST,
-            Opcodes.CONST, Form21h.THE_ONE, true);
+  public static final Dop CONST_HIGH16 =
+      new Dop(Opcodes.CONST_HIGH16, Opcodes.CONST, Opcodes.CONST, Form21h.THE_ONE, true);
 
-    public static final Dop CONST_WIDE_16 =
-        new Dop(Opcodes.CONST_WIDE_16, Opcodes.CONST_WIDE,
-            Opcodes.CONST_WIDE_HIGH16, Form21s.THE_ONE, true);
+  public static final Dop CONST_WIDE_16 = new Dop(Opcodes.CONST_WIDE_16, Opcodes.CONST_WIDE,
+      Opcodes.CONST_WIDE_HIGH16, Form21s.THE_ONE, true);
 
-    public static final Dop CONST_WIDE_32 =
-        new Dop(Opcodes.CONST_WIDE_32, Opcodes.CONST_WIDE,
-            Opcodes.CONST_WIDE, Form31i.THE_ONE, true);
+  public static final Dop CONST_WIDE_32 =
+      new Dop(Opcodes.CONST_WIDE_32, Opcodes.CONST_WIDE, Opcodes.CONST_WIDE, Form31i.THE_ONE, true);
 
-    public static final Dop CONST_WIDE =
-        new Dop(Opcodes.CONST_WIDE, Opcodes.CONST_WIDE,
-            Opcodes.NO_NEXT, Form51l.THE_ONE, true);
+  public static final Dop CONST_WIDE =
+      new Dop(Opcodes.CONST_WIDE, Opcodes.CONST_WIDE, Opcodes.NO_NEXT, Form51l.THE_ONE, true);
 
-    public static final Dop CONST_WIDE_HIGH16 =
-        new Dop(Opcodes.CONST_WIDE_HIGH16, Opcodes.CONST_WIDE,
-            Opcodes.CONST_WIDE_32, Form21h.THE_ONE, true);
+  public static final Dop CONST_WIDE_HIGH16 = new Dop(Opcodes.CONST_WIDE_HIGH16, Opcodes.CONST_WIDE,
+      Opcodes.CONST_WIDE_32, Form21h.THE_ONE, true);
 
-    public static final Dop CONST_STRING =
-        new Dop(Opcodes.CONST_STRING, Opcodes.CONST_STRING,
-            Opcodes.CONST_STRING_JUMBO, Form21c.THE_ONE, true);
+  public static final Dop CONST_STRING = new Dop(Opcodes.CONST_STRING, Opcodes.CONST_STRING,
+      Opcodes.CONST_STRING_JUMBO, Form21c.THE_ONE, true);
 
-    public static final Dop CONST_STRING_JUMBO =
-        new Dop(Opcodes.CONST_STRING_JUMBO, Opcodes.CONST_STRING,
-            Opcodes.NO_NEXT, Form31c.THE_ONE, true);
+  public static final Dop CONST_STRING_JUMBO = new Dop(Opcodes.CONST_STRING_JUMBO,
+      Opcodes.CONST_STRING, Opcodes.NO_NEXT, Form31c.THE_ONE, true);
 
-    public static final Dop CONST_CLASS =
-        new Dop(Opcodes.CONST_CLASS, Opcodes.CONST_CLASS,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop CONST_CLASS =
+      new Dop(Opcodes.CONST_CLASS, Opcodes.CONST_CLASS, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop MONITOR_ENTER =
-        new Dop(Opcodes.MONITOR_ENTER, Opcodes.MONITOR_ENTER,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop MONITOR_ENTER = new Dop(Opcodes.MONITOR_ENTER, Opcodes.MONITOR_ENTER,
+      Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop MONITOR_EXIT =
-        new Dop(Opcodes.MONITOR_EXIT, Opcodes.MONITOR_EXIT,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop MONITOR_EXIT =
+      new Dop(Opcodes.MONITOR_EXIT, Opcodes.MONITOR_EXIT, Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop CHECK_CAST =
-        new Dop(Opcodes.CHECK_CAST, Opcodes.CHECK_CAST,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop CHECK_CAST =
+      new Dop(Opcodes.CHECK_CAST, Opcodes.CHECK_CAST, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop INSTANCE_OF =
-        new Dop(Opcodes.INSTANCE_OF, Opcodes.INSTANCE_OF,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop INSTANCE_OF =
+      new Dop(Opcodes.INSTANCE_OF, Opcodes.INSTANCE_OF, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop ARRAY_LENGTH =
-        new Dop(Opcodes.ARRAY_LENGTH, Opcodes.ARRAY_LENGTH,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop ARRAY_LENGTH =
+      new Dop(Opcodes.ARRAY_LENGTH, Opcodes.ARRAY_LENGTH, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NEW_INSTANCE =
-        new Dop(Opcodes.NEW_INSTANCE, Opcodes.NEW_INSTANCE,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop NEW_INSTANCE =
+      new Dop(Opcodes.NEW_INSTANCE, Opcodes.NEW_INSTANCE, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop NEW_ARRAY =
-        new Dop(Opcodes.NEW_ARRAY, Opcodes.NEW_ARRAY,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop NEW_ARRAY =
+      new Dop(Opcodes.NEW_ARRAY, Opcodes.NEW_ARRAY, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop FILLED_NEW_ARRAY =
-        new Dop(Opcodes.FILLED_NEW_ARRAY, Opcodes.FILLED_NEW_ARRAY,
-            Opcodes.FILLED_NEW_ARRAY_RANGE, Form35c.THE_ONE, false);
+  public static final Dop FILLED_NEW_ARRAY = new Dop(Opcodes.FILLED_NEW_ARRAY,
+      Opcodes.FILLED_NEW_ARRAY, Opcodes.FILLED_NEW_ARRAY_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop FILLED_NEW_ARRAY_RANGE =
-        new Dop(Opcodes.FILLED_NEW_ARRAY_RANGE, Opcodes.FILLED_NEW_ARRAY,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop FILLED_NEW_ARRAY_RANGE = new Dop(Opcodes.FILLED_NEW_ARRAY_RANGE,
+      Opcodes.FILLED_NEW_ARRAY, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop FILL_ARRAY_DATA =
-        new Dop(Opcodes.FILL_ARRAY_DATA, Opcodes.FILL_ARRAY_DATA,
-            Opcodes.NO_NEXT, Form31t.THE_ONE, false);
+  public static final Dop FILL_ARRAY_DATA = new Dop(Opcodes.FILL_ARRAY_DATA,
+      Opcodes.FILL_ARRAY_DATA, Opcodes.NO_NEXT, Form31t.THE_ONE, false);
 
-    public static final Dop THROW =
-        new Dop(Opcodes.THROW, Opcodes.THROW,
-            Opcodes.NO_NEXT, Form11x.THE_ONE, false);
+  public static final Dop THROW =
+      new Dop(Opcodes.THROW, Opcodes.THROW, Opcodes.NO_NEXT, Form11x.THE_ONE, false);
 
-    public static final Dop GOTO =
-        new Dop(Opcodes.GOTO, Opcodes.GOTO,
-            Opcodes.GOTO_16, Form10t.THE_ONE, false);
+  public static final Dop GOTO =
+      new Dop(Opcodes.GOTO, Opcodes.GOTO, Opcodes.GOTO_16, Form10t.THE_ONE, false);
 
-    public static final Dop GOTO_16 =
-        new Dop(Opcodes.GOTO_16, Opcodes.GOTO,
-            Opcodes.GOTO_32, Form20t.THE_ONE, false);
+  public static final Dop GOTO_16 =
+      new Dop(Opcodes.GOTO_16, Opcodes.GOTO, Opcodes.GOTO_32, Form20t.THE_ONE, false);
 
-    public static final Dop GOTO_32 =
-        new Dop(Opcodes.GOTO_32, Opcodes.GOTO,
-            Opcodes.NO_NEXT, Form30t.THE_ONE, false);
+  public static final Dop GOTO_32 =
+      new Dop(Opcodes.GOTO_32, Opcodes.GOTO, Opcodes.NO_NEXT, Form30t.THE_ONE, false);
 
-    public static final Dop PACKED_SWITCH =
-        new Dop(Opcodes.PACKED_SWITCH, Opcodes.PACKED_SWITCH,
-            Opcodes.NO_NEXT, Form31t.THE_ONE, false);
+  public static final Dop PACKED_SWITCH = new Dop(Opcodes.PACKED_SWITCH, Opcodes.PACKED_SWITCH,
+      Opcodes.NO_NEXT, Form31t.THE_ONE, false);
 
-    public static final Dop SPARSE_SWITCH =
-        new Dop(Opcodes.SPARSE_SWITCH, Opcodes.SPARSE_SWITCH,
-            Opcodes.NO_NEXT, Form31t.THE_ONE, false);
+  public static final Dop SPARSE_SWITCH = new Dop(Opcodes.SPARSE_SWITCH, Opcodes.SPARSE_SWITCH,
+      Opcodes.NO_NEXT, Form31t.THE_ONE, false);
 
-    public static final Dop CMPL_FLOAT =
-        new Dop(Opcodes.CMPL_FLOAT, Opcodes.CMPL_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop CMPL_FLOAT =
+      new Dop(Opcodes.CMPL_FLOAT, Opcodes.CMPL_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop CMPG_FLOAT =
-        new Dop(Opcodes.CMPG_FLOAT, Opcodes.CMPG_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop CMPG_FLOAT =
+      new Dop(Opcodes.CMPG_FLOAT, Opcodes.CMPG_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop CMPL_DOUBLE =
-        new Dop(Opcodes.CMPL_DOUBLE, Opcodes.CMPL_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop CMPL_DOUBLE =
+      new Dop(Opcodes.CMPL_DOUBLE, Opcodes.CMPL_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop CMPG_DOUBLE =
-        new Dop(Opcodes.CMPG_DOUBLE, Opcodes.CMPG_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop CMPG_DOUBLE =
+      new Dop(Opcodes.CMPG_DOUBLE, Opcodes.CMPG_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop CMP_LONG =
-        new Dop(Opcodes.CMP_LONG, Opcodes.CMP_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop CMP_LONG =
+      new Dop(Opcodes.CMP_LONG, Opcodes.CMP_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop IF_EQ =
-        new Dop(Opcodes.IF_EQ, Opcodes.IF_EQ,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_EQ =
+      new Dop(Opcodes.IF_EQ, Opcodes.IF_EQ, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_NE =
-        new Dop(Opcodes.IF_NE, Opcodes.IF_NE,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_NE =
+      new Dop(Opcodes.IF_NE, Opcodes.IF_NE, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_LT =
-        new Dop(Opcodes.IF_LT, Opcodes.IF_LT,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_LT =
+      new Dop(Opcodes.IF_LT, Opcodes.IF_LT, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_GE =
-        new Dop(Opcodes.IF_GE, Opcodes.IF_GE,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_GE =
+      new Dop(Opcodes.IF_GE, Opcodes.IF_GE, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_GT =
-        new Dop(Opcodes.IF_GT, Opcodes.IF_GT,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_GT =
+      new Dop(Opcodes.IF_GT, Opcodes.IF_GT, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_LE =
-        new Dop(Opcodes.IF_LE, Opcodes.IF_LE,
-            Opcodes.NO_NEXT, Form22t.THE_ONE, false);
+  public static final Dop IF_LE =
+      new Dop(Opcodes.IF_LE, Opcodes.IF_LE, Opcodes.NO_NEXT, Form22t.THE_ONE, false);
 
-    public static final Dop IF_EQZ =
-        new Dop(Opcodes.IF_EQZ, Opcodes.IF_EQZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_EQZ =
+      new Dop(Opcodes.IF_EQZ, Opcodes.IF_EQZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop IF_NEZ =
-        new Dop(Opcodes.IF_NEZ, Opcodes.IF_NEZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_NEZ =
+      new Dop(Opcodes.IF_NEZ, Opcodes.IF_NEZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop IF_LTZ =
-        new Dop(Opcodes.IF_LTZ, Opcodes.IF_LTZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_LTZ =
+      new Dop(Opcodes.IF_LTZ, Opcodes.IF_LTZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop IF_GEZ =
-        new Dop(Opcodes.IF_GEZ, Opcodes.IF_GEZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_GEZ =
+      new Dop(Opcodes.IF_GEZ, Opcodes.IF_GEZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop IF_GTZ =
-        new Dop(Opcodes.IF_GTZ, Opcodes.IF_GTZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_GTZ =
+      new Dop(Opcodes.IF_GTZ, Opcodes.IF_GTZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop IF_LEZ =
-        new Dop(Opcodes.IF_LEZ, Opcodes.IF_LEZ,
-            Opcodes.NO_NEXT, Form21t.THE_ONE, false);
+  public static final Dop IF_LEZ =
+      new Dop(Opcodes.IF_LEZ, Opcodes.IF_LEZ, Opcodes.NO_NEXT, Form21t.THE_ONE, false);
 
-    public static final Dop AGET =
-        new Dop(Opcodes.AGET, Opcodes.AGET,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET =
+      new Dop(Opcodes.AGET, Opcodes.AGET, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_WIDE =
-        new Dop(Opcodes.AGET_WIDE, Opcodes.AGET_WIDE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_WIDE =
+      new Dop(Opcodes.AGET_WIDE, Opcodes.AGET_WIDE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_OBJECT =
-        new Dop(Opcodes.AGET_OBJECT, Opcodes.AGET_OBJECT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_OBJECT =
+      new Dop(Opcodes.AGET_OBJECT, Opcodes.AGET_OBJECT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_BOOLEAN =
-        new Dop(Opcodes.AGET_BOOLEAN, Opcodes.AGET_BOOLEAN,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_BOOLEAN =
+      new Dop(Opcodes.AGET_BOOLEAN, Opcodes.AGET_BOOLEAN, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_BYTE =
-        new Dop(Opcodes.AGET_BYTE, Opcodes.AGET_BYTE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_BYTE =
+      new Dop(Opcodes.AGET_BYTE, Opcodes.AGET_BYTE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_CHAR =
-        new Dop(Opcodes.AGET_CHAR, Opcodes.AGET_CHAR,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_CHAR =
+      new Dop(Opcodes.AGET_CHAR, Opcodes.AGET_CHAR, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AGET_SHORT =
-        new Dop(Opcodes.AGET_SHORT, Opcodes.AGET_SHORT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AGET_SHORT =
+      new Dop(Opcodes.AGET_SHORT, Opcodes.AGET_SHORT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop APUT =
-        new Dop(Opcodes.APUT, Opcodes.APUT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT =
+      new Dop(Opcodes.APUT, Opcodes.APUT, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_WIDE =
-        new Dop(Opcodes.APUT_WIDE, Opcodes.APUT_WIDE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_WIDE =
+      new Dop(Opcodes.APUT_WIDE, Opcodes.APUT_WIDE, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_OBJECT =
-        new Dop(Opcodes.APUT_OBJECT, Opcodes.APUT_OBJECT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_OBJECT =
+      new Dop(Opcodes.APUT_OBJECT, Opcodes.APUT_OBJECT, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_BOOLEAN =
-        new Dop(Opcodes.APUT_BOOLEAN, Opcodes.APUT_BOOLEAN,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_BOOLEAN =
+      new Dop(Opcodes.APUT_BOOLEAN, Opcodes.APUT_BOOLEAN, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_BYTE =
-        new Dop(Opcodes.APUT_BYTE, Opcodes.APUT_BYTE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_BYTE =
+      new Dop(Opcodes.APUT_BYTE, Opcodes.APUT_BYTE, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_CHAR =
-        new Dop(Opcodes.APUT_CHAR, Opcodes.APUT_CHAR,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_CHAR =
+      new Dop(Opcodes.APUT_CHAR, Opcodes.APUT_CHAR, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop APUT_SHORT =
-        new Dop(Opcodes.APUT_SHORT, Opcodes.APUT_SHORT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, false);
+  public static final Dop APUT_SHORT =
+      new Dop(Opcodes.APUT_SHORT, Opcodes.APUT_SHORT, Opcodes.NO_NEXT, Form23x.THE_ONE, false);
 
-    public static final Dop IGET =
-        new Dop(Opcodes.IGET, Opcodes.IGET,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET =
+      new Dop(Opcodes.IGET, Opcodes.IGET, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_WIDE =
-        new Dop(Opcodes.IGET_WIDE, Opcodes.IGET_WIDE,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_WIDE =
+      new Dop(Opcodes.IGET_WIDE, Opcodes.IGET_WIDE, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_OBJECT =
-        new Dop(Opcodes.IGET_OBJECT, Opcodes.IGET_OBJECT,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_OBJECT =
+      new Dop(Opcodes.IGET_OBJECT, Opcodes.IGET_OBJECT, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_BOOLEAN =
-        new Dop(Opcodes.IGET_BOOLEAN, Opcodes.IGET_BOOLEAN,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_BOOLEAN =
+      new Dop(Opcodes.IGET_BOOLEAN, Opcodes.IGET_BOOLEAN, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_BYTE =
-        new Dop(Opcodes.IGET_BYTE, Opcodes.IGET_BYTE,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_BYTE =
+      new Dop(Opcodes.IGET_BYTE, Opcodes.IGET_BYTE, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_CHAR =
-        new Dop(Opcodes.IGET_CHAR, Opcodes.IGET_CHAR,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_CHAR =
+      new Dop(Opcodes.IGET_CHAR, Opcodes.IGET_CHAR, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IGET_SHORT =
-        new Dop(Opcodes.IGET_SHORT, Opcodes.IGET_SHORT,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, true);
+  public static final Dop IGET_SHORT =
+      new Dop(Opcodes.IGET_SHORT, Opcodes.IGET_SHORT, Opcodes.NO_NEXT, Form22c.THE_ONE, true);
 
-    public static final Dop IPUT =
-        new Dop(Opcodes.IPUT, Opcodes.IPUT,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT =
+      new Dop(Opcodes.IPUT, Opcodes.IPUT, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_WIDE =
-        new Dop(Opcodes.IPUT_WIDE, Opcodes.IPUT_WIDE,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_WIDE =
+      new Dop(Opcodes.IPUT_WIDE, Opcodes.IPUT_WIDE, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_OBJECT =
-        new Dop(Opcodes.IPUT_OBJECT, Opcodes.IPUT_OBJECT,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_OBJECT =
+      new Dop(Opcodes.IPUT_OBJECT, Opcodes.IPUT_OBJECT, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_BOOLEAN =
-        new Dop(Opcodes.IPUT_BOOLEAN, Opcodes.IPUT_BOOLEAN,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_BOOLEAN =
+      new Dop(Opcodes.IPUT_BOOLEAN, Opcodes.IPUT_BOOLEAN, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_BYTE =
-        new Dop(Opcodes.IPUT_BYTE, Opcodes.IPUT_BYTE,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_BYTE =
+      new Dop(Opcodes.IPUT_BYTE, Opcodes.IPUT_BYTE, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_CHAR =
-        new Dop(Opcodes.IPUT_CHAR, Opcodes.IPUT_CHAR,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_CHAR =
+      new Dop(Opcodes.IPUT_CHAR, Opcodes.IPUT_CHAR, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop IPUT_SHORT =
-        new Dop(Opcodes.IPUT_SHORT, Opcodes.IPUT_SHORT,
-            Opcodes.NO_NEXT, Form22c.THE_ONE, false);
+  public static final Dop IPUT_SHORT =
+      new Dop(Opcodes.IPUT_SHORT, Opcodes.IPUT_SHORT, Opcodes.NO_NEXT, Form22c.THE_ONE, false);
 
-    public static final Dop SGET =
-        new Dop(Opcodes.SGET, Opcodes.SGET,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET =
+      new Dop(Opcodes.SGET, Opcodes.SGET, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_WIDE =
-        new Dop(Opcodes.SGET_WIDE, Opcodes.SGET_WIDE,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_WIDE =
+      new Dop(Opcodes.SGET_WIDE, Opcodes.SGET_WIDE, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_OBJECT =
-        new Dop(Opcodes.SGET_OBJECT, Opcodes.SGET_OBJECT,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_OBJECT =
+      new Dop(Opcodes.SGET_OBJECT, Opcodes.SGET_OBJECT, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_BOOLEAN =
-        new Dop(Opcodes.SGET_BOOLEAN, Opcodes.SGET_BOOLEAN,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_BOOLEAN =
+      new Dop(Opcodes.SGET_BOOLEAN, Opcodes.SGET_BOOLEAN, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_BYTE =
-        new Dop(Opcodes.SGET_BYTE, Opcodes.SGET_BYTE,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_BYTE =
+      new Dop(Opcodes.SGET_BYTE, Opcodes.SGET_BYTE, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_CHAR =
-        new Dop(Opcodes.SGET_CHAR, Opcodes.SGET_CHAR,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_CHAR =
+      new Dop(Opcodes.SGET_CHAR, Opcodes.SGET_CHAR, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SGET_SHORT =
-        new Dop(Opcodes.SGET_SHORT, Opcodes.SGET_SHORT,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, true);
+  public static final Dop SGET_SHORT =
+      new Dop(Opcodes.SGET_SHORT, Opcodes.SGET_SHORT, Opcodes.NO_NEXT, Form21c.THE_ONE, true);
 
-    public static final Dop SPUT =
-        new Dop(Opcodes.SPUT, Opcodes.SPUT,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT =
+      new Dop(Opcodes.SPUT, Opcodes.SPUT, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_WIDE =
-        new Dop(Opcodes.SPUT_WIDE, Opcodes.SPUT_WIDE,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_WIDE =
+      new Dop(Opcodes.SPUT_WIDE, Opcodes.SPUT_WIDE, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_OBJECT =
-        new Dop(Opcodes.SPUT_OBJECT, Opcodes.SPUT_OBJECT,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_OBJECT =
+      new Dop(Opcodes.SPUT_OBJECT, Opcodes.SPUT_OBJECT, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_BOOLEAN =
-        new Dop(Opcodes.SPUT_BOOLEAN, Opcodes.SPUT_BOOLEAN,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_BOOLEAN =
+      new Dop(Opcodes.SPUT_BOOLEAN, Opcodes.SPUT_BOOLEAN, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_BYTE =
-        new Dop(Opcodes.SPUT_BYTE, Opcodes.SPUT_BYTE,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_BYTE =
+      new Dop(Opcodes.SPUT_BYTE, Opcodes.SPUT_BYTE, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_CHAR =
-        new Dop(Opcodes.SPUT_CHAR, Opcodes.SPUT_CHAR,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_CHAR =
+      new Dop(Opcodes.SPUT_CHAR, Opcodes.SPUT_CHAR, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop SPUT_SHORT =
-        new Dop(Opcodes.SPUT_SHORT, Opcodes.SPUT_SHORT,
-            Opcodes.NO_NEXT, Form21c.THE_ONE, false);
+  public static final Dop SPUT_SHORT =
+      new Dop(Opcodes.SPUT_SHORT, Opcodes.SPUT_SHORT, Opcodes.NO_NEXT, Form21c.THE_ONE, false);
 
-    public static final Dop INVOKE_VIRTUAL =
-        new Dop(Opcodes.INVOKE_VIRTUAL, Opcodes.INVOKE_VIRTUAL,
-            Opcodes.INVOKE_VIRTUAL_RANGE, Form35c.THE_ONE, false);
+  public static final Dop INVOKE_VIRTUAL = new Dop(Opcodes.INVOKE_VIRTUAL, Opcodes.INVOKE_VIRTUAL,
+      Opcodes.INVOKE_VIRTUAL_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop INVOKE_SUPER =
-        new Dop(Opcodes.INVOKE_SUPER, Opcodes.INVOKE_SUPER,
-            Opcodes.INVOKE_SUPER_RANGE, Form35c.THE_ONE, false);
+  public static final Dop INVOKE_SUPER = new Dop(Opcodes.INVOKE_SUPER, Opcodes.INVOKE_SUPER,
+      Opcodes.INVOKE_SUPER_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop INVOKE_DIRECT =
-        new Dop(Opcodes.INVOKE_DIRECT, Opcodes.INVOKE_DIRECT,
-            Opcodes.INVOKE_DIRECT_RANGE, Form35c.THE_ONE, false);
+  public static final Dop INVOKE_DIRECT = new Dop(Opcodes.INVOKE_DIRECT, Opcodes.INVOKE_DIRECT,
+      Opcodes.INVOKE_DIRECT_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop INVOKE_STATIC =
-        new Dop(Opcodes.INVOKE_STATIC, Opcodes.INVOKE_STATIC,
-            Opcodes.INVOKE_STATIC_RANGE, Form35c.THE_ONE, false);
+  public static final Dop INVOKE_STATIC = new Dop(Opcodes.INVOKE_STATIC, Opcodes.INVOKE_STATIC,
+      Opcodes.INVOKE_STATIC_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop INVOKE_INTERFACE =
-        new Dop(Opcodes.INVOKE_INTERFACE, Opcodes.INVOKE_INTERFACE,
-            Opcodes.INVOKE_INTERFACE_RANGE, Form35c.THE_ONE, false);
+  public static final Dop INVOKE_INTERFACE = new Dop(Opcodes.INVOKE_INTERFACE,
+      Opcodes.INVOKE_INTERFACE, Opcodes.INVOKE_INTERFACE_RANGE, Form35c.THE_ONE, false);
 
-    public static final Dop INVOKE_VIRTUAL_RANGE =
-        new Dop(Opcodes.INVOKE_VIRTUAL_RANGE, Opcodes.INVOKE_VIRTUAL,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop INVOKE_VIRTUAL_RANGE = new Dop(Opcodes.INVOKE_VIRTUAL_RANGE,
+      Opcodes.INVOKE_VIRTUAL, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop INVOKE_SUPER_RANGE =
-        new Dop(Opcodes.INVOKE_SUPER_RANGE, Opcodes.INVOKE_SUPER,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop INVOKE_SUPER_RANGE = new Dop(Opcodes.INVOKE_SUPER_RANGE,
+      Opcodes.INVOKE_SUPER, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop INVOKE_DIRECT_RANGE =
-        new Dop(Opcodes.INVOKE_DIRECT_RANGE, Opcodes.INVOKE_DIRECT,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop INVOKE_DIRECT_RANGE = new Dop(Opcodes.INVOKE_DIRECT_RANGE,
+      Opcodes.INVOKE_DIRECT, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop INVOKE_STATIC_RANGE =
-        new Dop(Opcodes.INVOKE_STATIC_RANGE, Opcodes.INVOKE_STATIC,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop INVOKE_STATIC_RANGE = new Dop(Opcodes.INVOKE_STATIC_RANGE,
+      Opcodes.INVOKE_STATIC, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop INVOKE_INTERFACE_RANGE =
-        new Dop(Opcodes.INVOKE_INTERFACE_RANGE, Opcodes.INVOKE_INTERFACE,
-            Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
+  public static final Dop INVOKE_INTERFACE_RANGE = new Dop(Opcodes.INVOKE_INTERFACE_RANGE,
+      Opcodes.INVOKE_INTERFACE, Opcodes.NO_NEXT, Form3rc.THE_ONE, false);
 
-    public static final Dop NEG_INT =
-        new Dop(Opcodes.NEG_INT, Opcodes.NEG_INT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NEG_INT =
+      new Dop(Opcodes.NEG_INT, Opcodes.NEG_INT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NOT_INT =
-        new Dop(Opcodes.NOT_INT, Opcodes.NOT_INT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NOT_INT =
+      new Dop(Opcodes.NOT_INT, Opcodes.NOT_INT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NEG_LONG =
-        new Dop(Opcodes.NEG_LONG, Opcodes.NEG_LONG,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NEG_LONG =
+      new Dop(Opcodes.NEG_LONG, Opcodes.NEG_LONG, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NOT_LONG =
-        new Dop(Opcodes.NOT_LONG, Opcodes.NOT_LONG,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NOT_LONG =
+      new Dop(Opcodes.NOT_LONG, Opcodes.NOT_LONG, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NEG_FLOAT =
-        new Dop(Opcodes.NEG_FLOAT, Opcodes.NEG_FLOAT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NEG_FLOAT =
+      new Dop(Opcodes.NEG_FLOAT, Opcodes.NEG_FLOAT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop NEG_DOUBLE =
-        new Dop(Opcodes.NEG_DOUBLE, Opcodes.NEG_DOUBLE,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop NEG_DOUBLE =
+      new Dop(Opcodes.NEG_DOUBLE, Opcodes.NEG_DOUBLE, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_LONG =
-        new Dop(Opcodes.INT_TO_LONG, Opcodes.INT_TO_LONG,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_LONG =
+      new Dop(Opcodes.INT_TO_LONG, Opcodes.INT_TO_LONG, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_FLOAT =
-        new Dop(Opcodes.INT_TO_FLOAT, Opcodes.INT_TO_FLOAT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_FLOAT =
+      new Dop(Opcodes.INT_TO_FLOAT, Opcodes.INT_TO_FLOAT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_DOUBLE =
-        new Dop(Opcodes.INT_TO_DOUBLE, Opcodes.INT_TO_DOUBLE,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_DOUBLE =
+      new Dop(Opcodes.INT_TO_DOUBLE, Opcodes.INT_TO_DOUBLE, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop LONG_TO_INT =
-        new Dop(Opcodes.LONG_TO_INT, Opcodes.LONG_TO_INT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop LONG_TO_INT =
+      new Dop(Opcodes.LONG_TO_INT, Opcodes.LONG_TO_INT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop LONG_TO_FLOAT =
-        new Dop(Opcodes.LONG_TO_FLOAT, Opcodes.LONG_TO_FLOAT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop LONG_TO_FLOAT =
+      new Dop(Opcodes.LONG_TO_FLOAT, Opcodes.LONG_TO_FLOAT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop LONG_TO_DOUBLE =
-        new Dop(Opcodes.LONG_TO_DOUBLE, Opcodes.LONG_TO_DOUBLE,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop LONG_TO_DOUBLE = new Dop(Opcodes.LONG_TO_DOUBLE, Opcodes.LONG_TO_DOUBLE,
+      Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop FLOAT_TO_INT =
-        new Dop(Opcodes.FLOAT_TO_INT, Opcodes.FLOAT_TO_INT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop FLOAT_TO_INT =
+      new Dop(Opcodes.FLOAT_TO_INT, Opcodes.FLOAT_TO_INT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop FLOAT_TO_LONG =
-        new Dop(Opcodes.FLOAT_TO_LONG, Opcodes.FLOAT_TO_LONG,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop FLOAT_TO_LONG =
+      new Dop(Opcodes.FLOAT_TO_LONG, Opcodes.FLOAT_TO_LONG, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop FLOAT_TO_DOUBLE =
-        new Dop(Opcodes.FLOAT_TO_DOUBLE, Opcodes.FLOAT_TO_DOUBLE,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop FLOAT_TO_DOUBLE = new Dop(Opcodes.FLOAT_TO_DOUBLE,
+      Opcodes.FLOAT_TO_DOUBLE, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop DOUBLE_TO_INT =
-        new Dop(Opcodes.DOUBLE_TO_INT, Opcodes.DOUBLE_TO_INT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop DOUBLE_TO_INT =
+      new Dop(Opcodes.DOUBLE_TO_INT, Opcodes.DOUBLE_TO_INT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop DOUBLE_TO_LONG =
-        new Dop(Opcodes.DOUBLE_TO_LONG, Opcodes.DOUBLE_TO_LONG,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop DOUBLE_TO_LONG = new Dop(Opcodes.DOUBLE_TO_LONG, Opcodes.DOUBLE_TO_LONG,
+      Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop DOUBLE_TO_FLOAT =
-        new Dop(Opcodes.DOUBLE_TO_FLOAT, Opcodes.DOUBLE_TO_FLOAT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop DOUBLE_TO_FLOAT = new Dop(Opcodes.DOUBLE_TO_FLOAT,
+      Opcodes.DOUBLE_TO_FLOAT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_BYTE =
-        new Dop(Opcodes.INT_TO_BYTE, Opcodes.INT_TO_BYTE,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_BYTE =
+      new Dop(Opcodes.INT_TO_BYTE, Opcodes.INT_TO_BYTE, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_CHAR =
-        new Dop(Opcodes.INT_TO_CHAR, Opcodes.INT_TO_CHAR,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_CHAR =
+      new Dop(Opcodes.INT_TO_CHAR, Opcodes.INT_TO_CHAR, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop INT_TO_SHORT =
-        new Dop(Opcodes.INT_TO_SHORT, Opcodes.INT_TO_SHORT,
-            Opcodes.NO_NEXT, Form12x.THE_ONE, true);
+  public static final Dop INT_TO_SHORT =
+      new Dop(Opcodes.INT_TO_SHORT, Opcodes.INT_TO_SHORT, Opcodes.NO_NEXT, Form12x.THE_ONE, true);
 
-    public static final Dop ADD_INT =
-        new Dop(Opcodes.ADD_INT, Opcodes.ADD_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop ADD_INT =
+      new Dop(Opcodes.ADD_INT, Opcodes.ADD_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SUB_INT =
-        new Dop(Opcodes.SUB_INT, Opcodes.SUB_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SUB_INT =
+      new Dop(Opcodes.SUB_INT, Opcodes.SUB_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop MUL_INT =
-        new Dop(Opcodes.MUL_INT, Opcodes.MUL_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop MUL_INT =
+      new Dop(Opcodes.MUL_INT, Opcodes.MUL_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop DIV_INT =
-        new Dop(Opcodes.DIV_INT, Opcodes.DIV_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop DIV_INT =
+      new Dop(Opcodes.DIV_INT, Opcodes.DIV_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop REM_INT =
-        new Dop(Opcodes.REM_INT, Opcodes.REM_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop REM_INT =
+      new Dop(Opcodes.REM_INT, Opcodes.REM_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AND_INT =
-        new Dop(Opcodes.AND_INT, Opcodes.AND_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AND_INT =
+      new Dop(Opcodes.AND_INT, Opcodes.AND_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop OR_INT =
-        new Dop(Opcodes.OR_INT, Opcodes.OR_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop OR_INT =
+      new Dop(Opcodes.OR_INT, Opcodes.OR_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop XOR_INT =
-        new Dop(Opcodes.XOR_INT, Opcodes.XOR_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop XOR_INT =
+      new Dop(Opcodes.XOR_INT, Opcodes.XOR_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SHL_INT =
-        new Dop(Opcodes.SHL_INT, Opcodes.SHL_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SHL_INT =
+      new Dop(Opcodes.SHL_INT, Opcodes.SHL_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SHR_INT =
-        new Dop(Opcodes.SHR_INT, Opcodes.SHR_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SHR_INT =
+      new Dop(Opcodes.SHR_INT, Opcodes.SHR_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop USHR_INT =
-        new Dop(Opcodes.USHR_INT, Opcodes.USHR_INT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop USHR_INT =
+      new Dop(Opcodes.USHR_INT, Opcodes.USHR_INT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop ADD_LONG =
-        new Dop(Opcodes.ADD_LONG, Opcodes.ADD_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop ADD_LONG =
+      new Dop(Opcodes.ADD_LONG, Opcodes.ADD_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SUB_LONG =
-        new Dop(Opcodes.SUB_LONG, Opcodes.SUB_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SUB_LONG =
+      new Dop(Opcodes.SUB_LONG, Opcodes.SUB_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop MUL_LONG =
-        new Dop(Opcodes.MUL_LONG, Opcodes.MUL_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop MUL_LONG =
+      new Dop(Opcodes.MUL_LONG, Opcodes.MUL_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop DIV_LONG =
-        new Dop(Opcodes.DIV_LONG, Opcodes.DIV_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop DIV_LONG =
+      new Dop(Opcodes.DIV_LONG, Opcodes.DIV_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop REM_LONG =
-        new Dop(Opcodes.REM_LONG, Opcodes.REM_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop REM_LONG =
+      new Dop(Opcodes.REM_LONG, Opcodes.REM_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop AND_LONG =
-        new Dop(Opcodes.AND_LONG, Opcodes.AND_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop AND_LONG =
+      new Dop(Opcodes.AND_LONG, Opcodes.AND_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop OR_LONG =
-        new Dop(Opcodes.OR_LONG, Opcodes.OR_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop OR_LONG =
+      new Dop(Opcodes.OR_LONG, Opcodes.OR_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop XOR_LONG =
-        new Dop(Opcodes.XOR_LONG, Opcodes.XOR_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop XOR_LONG =
+      new Dop(Opcodes.XOR_LONG, Opcodes.XOR_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SHL_LONG =
-        new Dop(Opcodes.SHL_LONG, Opcodes.SHL_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SHL_LONG =
+      new Dop(Opcodes.SHL_LONG, Opcodes.SHL_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SHR_LONG =
-        new Dop(Opcodes.SHR_LONG, Opcodes.SHR_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SHR_LONG =
+      new Dop(Opcodes.SHR_LONG, Opcodes.SHR_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop USHR_LONG =
-        new Dop(Opcodes.USHR_LONG, Opcodes.USHR_LONG,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop USHR_LONG =
+      new Dop(Opcodes.USHR_LONG, Opcodes.USHR_LONG, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop ADD_FLOAT =
-        new Dop(Opcodes.ADD_FLOAT, Opcodes.ADD_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop ADD_FLOAT =
+      new Dop(Opcodes.ADD_FLOAT, Opcodes.ADD_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SUB_FLOAT =
-        new Dop(Opcodes.SUB_FLOAT, Opcodes.SUB_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
-
-    public static final Dop MUL_FLOAT =
-        new Dop(Opcodes.MUL_FLOAT, Opcodes.MUL_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
-
-    public static final Dop DIV_FLOAT =
-        new Dop(Opcodes.DIV_FLOAT, Opcodes.DIV_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
-
-    public static final Dop REM_FLOAT =
-        new Dop(Opcodes.REM_FLOAT, Opcodes.REM_FLOAT,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SUB_FLOAT =
+      new Dop(Opcodes.SUB_FLOAT, Opcodes.SUB_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop ADD_DOUBLE =
-        new Dop(Opcodes.ADD_DOUBLE, Opcodes.ADD_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop MUL_FLOAT =
+      new Dop(Opcodes.MUL_FLOAT, Opcodes.MUL_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SUB_DOUBLE =
-        new Dop(Opcodes.SUB_DOUBLE, Opcodes.SUB_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop DIV_FLOAT =
+      new Dop(Opcodes.DIV_FLOAT, Opcodes.DIV_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop MUL_DOUBLE =
-        new Dop(Opcodes.MUL_DOUBLE, Opcodes.MUL_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop REM_FLOAT =
+      new Dop(Opcodes.REM_FLOAT, Opcodes.REM_FLOAT, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop DIV_DOUBLE =
-        new Dop(Opcodes.DIV_DOUBLE, Opcodes.DIV_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop ADD_DOUBLE =
+      new Dop(Opcodes.ADD_DOUBLE, Opcodes.ADD_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop REM_DOUBLE =
-        new Dop(Opcodes.REM_DOUBLE, Opcodes.REM_DOUBLE,
-            Opcodes.NO_NEXT, Form23x.THE_ONE, true);
+  public static final Dop SUB_DOUBLE =
+      new Dop(Opcodes.SUB_DOUBLE, Opcodes.SUB_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop ADD_INT_2ADDR =
-        new Dop(Opcodes.ADD_INT_2ADDR, Opcodes.ADD_INT,
-            Opcodes.ADD_INT, Form12x.THE_ONE, true);
+  public static final Dop MUL_DOUBLE =
+      new Dop(Opcodes.MUL_DOUBLE, Opcodes.MUL_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop SUB_INT_2ADDR =
-        new Dop(Opcodes.SUB_INT_2ADDR, Opcodes.SUB_INT,
-            Opcodes.SUB_INT, Form12x.THE_ONE, true);
+  public static final Dop DIV_DOUBLE =
+      new Dop(Opcodes.DIV_DOUBLE, Opcodes.DIV_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop MUL_INT_2ADDR =
-        new Dop(Opcodes.MUL_INT_2ADDR, Opcodes.MUL_INT,
-            Opcodes.MUL_INT, Form12x.THE_ONE, true);
+  public static final Dop REM_DOUBLE =
+      new Dop(Opcodes.REM_DOUBLE, Opcodes.REM_DOUBLE, Opcodes.NO_NEXT, Form23x.THE_ONE, true);
 
-    public static final Dop DIV_INT_2ADDR =
-        new Dop(Opcodes.DIV_INT_2ADDR, Opcodes.DIV_INT,
-            Opcodes.DIV_INT, Form12x.THE_ONE, true);
+  public static final Dop ADD_INT_2ADDR =
+      new Dop(Opcodes.ADD_INT_2ADDR, Opcodes.ADD_INT, Opcodes.ADD_INT, Form12x.THE_ONE, true);
 
-    public static final Dop REM_INT_2ADDR =
-        new Dop(Opcodes.REM_INT_2ADDR, Opcodes.REM_INT,
-            Opcodes.REM_INT, Form12x.THE_ONE, true);
+  public static final Dop SUB_INT_2ADDR =
+      new Dop(Opcodes.SUB_INT_2ADDR, Opcodes.SUB_INT, Opcodes.SUB_INT, Form12x.THE_ONE, true);
 
-    public static final Dop AND_INT_2ADDR =
-        new Dop(Opcodes.AND_INT_2ADDR, Opcodes.AND_INT,
-            Opcodes.AND_INT, Form12x.THE_ONE, true);
+  public static final Dop MUL_INT_2ADDR =
+      new Dop(Opcodes.MUL_INT_2ADDR, Opcodes.MUL_INT, Opcodes.MUL_INT, Form12x.THE_ONE, true);
 
-    public static final Dop OR_INT_2ADDR =
-        new Dop(Opcodes.OR_INT_2ADDR, Opcodes.OR_INT,
-            Opcodes.OR_INT, Form12x.THE_ONE, true);
+  public static final Dop DIV_INT_2ADDR =
+      new Dop(Opcodes.DIV_INT_2ADDR, Opcodes.DIV_INT, Opcodes.DIV_INT, Form12x.THE_ONE, true);
 
-    public static final Dop XOR_INT_2ADDR =
-        new Dop(Opcodes.XOR_INT_2ADDR, Opcodes.XOR_INT,
-            Opcodes.XOR_INT, Form12x.THE_ONE, true);
+  public static final Dop REM_INT_2ADDR =
+      new Dop(Opcodes.REM_INT_2ADDR, Opcodes.REM_INT, Opcodes.REM_INT, Form12x.THE_ONE, true);
 
-    public static final Dop SHL_INT_2ADDR =
-        new Dop(Opcodes.SHL_INT_2ADDR, Opcodes.SHL_INT,
-            Opcodes.SHL_INT, Form12x.THE_ONE, true);
+  public static final Dop AND_INT_2ADDR =
+      new Dop(Opcodes.AND_INT_2ADDR, Opcodes.AND_INT, Opcodes.AND_INT, Form12x.THE_ONE, true);
 
-    public static final Dop SHR_INT_2ADDR =
-        new Dop(Opcodes.SHR_INT_2ADDR, Opcodes.SHR_INT,
-            Opcodes.SHR_INT, Form12x.THE_ONE, true);
+  public static final Dop OR_INT_2ADDR =
+      new Dop(Opcodes.OR_INT_2ADDR, Opcodes.OR_INT, Opcodes.OR_INT, Form12x.THE_ONE, true);
 
-    public static final Dop USHR_INT_2ADDR =
-        new Dop(Opcodes.USHR_INT_2ADDR, Opcodes.USHR_INT,
-            Opcodes.USHR_INT, Form12x.THE_ONE, true);
+  public static final Dop XOR_INT_2ADDR =
+      new Dop(Opcodes.XOR_INT_2ADDR, Opcodes.XOR_INT, Opcodes.XOR_INT, Form12x.THE_ONE, true);
 
-    public static final Dop ADD_LONG_2ADDR =
-        new Dop(Opcodes.ADD_LONG_2ADDR, Opcodes.ADD_LONG,
-            Opcodes.ADD_LONG, Form12x.THE_ONE, true);
+  public static final Dop SHL_INT_2ADDR =
+      new Dop(Opcodes.SHL_INT_2ADDR, Opcodes.SHL_INT, Opcodes.SHL_INT, Form12x.THE_ONE, true);
 
-    public static final Dop SUB_LONG_2ADDR =
-        new Dop(Opcodes.SUB_LONG_2ADDR, Opcodes.SUB_LONG,
-            Opcodes.SUB_LONG, Form12x.THE_ONE, true);
+  public static final Dop SHR_INT_2ADDR =
+      new Dop(Opcodes.SHR_INT_2ADDR, Opcodes.SHR_INT, Opcodes.SHR_INT, Form12x.THE_ONE, true);
 
-    public static final Dop MUL_LONG_2ADDR =
-        new Dop(Opcodes.MUL_LONG_2ADDR, Opcodes.MUL_LONG,
-            Opcodes.MUL_LONG, Form12x.THE_ONE, true);
+  public static final Dop USHR_INT_2ADDR =
+      new Dop(Opcodes.USHR_INT_2ADDR, Opcodes.USHR_INT, Opcodes.USHR_INT, Form12x.THE_ONE, true);
 
-    public static final Dop DIV_LONG_2ADDR =
-        new Dop(Opcodes.DIV_LONG_2ADDR, Opcodes.DIV_LONG,
-            Opcodes.DIV_LONG, Form12x.THE_ONE, true);
+  public static final Dop ADD_LONG_2ADDR =
+      new Dop(Opcodes.ADD_LONG_2ADDR, Opcodes.ADD_LONG, Opcodes.ADD_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop REM_LONG_2ADDR =
-        new Dop(Opcodes.REM_LONG_2ADDR, Opcodes.REM_LONG,
-            Opcodes.REM_LONG, Form12x.THE_ONE, true);
+  public static final Dop SUB_LONG_2ADDR =
+      new Dop(Opcodes.SUB_LONG_2ADDR, Opcodes.SUB_LONG, Opcodes.SUB_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop AND_LONG_2ADDR =
-        new Dop(Opcodes.AND_LONG_2ADDR, Opcodes.AND_LONG,
-            Opcodes.AND_LONG, Form12x.THE_ONE, true);
+  public static final Dop MUL_LONG_2ADDR =
+      new Dop(Opcodes.MUL_LONG_2ADDR, Opcodes.MUL_LONG, Opcodes.MUL_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop OR_LONG_2ADDR =
-        new Dop(Opcodes.OR_LONG_2ADDR, Opcodes.OR_LONG,
-            Opcodes.OR_LONG, Form12x.THE_ONE, true);
+  public static final Dop DIV_LONG_2ADDR =
+      new Dop(Opcodes.DIV_LONG_2ADDR, Opcodes.DIV_LONG, Opcodes.DIV_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop XOR_LONG_2ADDR =
-        new Dop(Opcodes.XOR_LONG_2ADDR, Opcodes.XOR_LONG,
-            Opcodes.XOR_LONG, Form12x.THE_ONE, true);
+  public static final Dop REM_LONG_2ADDR =
+      new Dop(Opcodes.REM_LONG_2ADDR, Opcodes.REM_LONG, Opcodes.REM_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop SHL_LONG_2ADDR =
-        new Dop(Opcodes.SHL_LONG_2ADDR, Opcodes.SHL_LONG,
-            Opcodes.SHL_LONG, Form12x.THE_ONE, true);
+  public static final Dop AND_LONG_2ADDR =
+      new Dop(Opcodes.AND_LONG_2ADDR, Opcodes.AND_LONG, Opcodes.AND_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop SHR_LONG_2ADDR =
-        new Dop(Opcodes.SHR_LONG_2ADDR, Opcodes.SHR_LONG,
-            Opcodes.SHR_LONG, Form12x.THE_ONE, true);
+  public static final Dop OR_LONG_2ADDR =
+      new Dop(Opcodes.OR_LONG_2ADDR, Opcodes.OR_LONG, Opcodes.OR_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop USHR_LONG_2ADDR =
-        new Dop(Opcodes.USHR_LONG_2ADDR, Opcodes.USHR_LONG,
-            Opcodes.USHR_LONG, Form12x.THE_ONE, true);
+  public static final Dop XOR_LONG_2ADDR =
+      new Dop(Opcodes.XOR_LONG_2ADDR, Opcodes.XOR_LONG, Opcodes.XOR_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop ADD_FLOAT_2ADDR =
-        new Dop(Opcodes.ADD_FLOAT_2ADDR, Opcodes.ADD_FLOAT,
-            Opcodes.ADD_FLOAT, Form12x.THE_ONE, true);
+  public static final Dop SHL_LONG_2ADDR =
+      new Dop(Opcodes.SHL_LONG_2ADDR, Opcodes.SHL_LONG, Opcodes.SHL_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop SUB_FLOAT_2ADDR =
-        new Dop(Opcodes.SUB_FLOAT_2ADDR, Opcodes.SUB_FLOAT,
-            Opcodes.SUB_FLOAT, Form12x.THE_ONE, true);
+  public static final Dop SHR_LONG_2ADDR =
+      new Dop(Opcodes.SHR_LONG_2ADDR, Opcodes.SHR_LONG, Opcodes.SHR_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop MUL_FLOAT_2ADDR =
-        new Dop(Opcodes.MUL_FLOAT_2ADDR, Opcodes.MUL_FLOAT,
-            Opcodes.MUL_FLOAT, Form12x.THE_ONE, true);
+  public static final Dop USHR_LONG_2ADDR =
+      new Dop(Opcodes.USHR_LONG_2ADDR, Opcodes.USHR_LONG, Opcodes.USHR_LONG, Form12x.THE_ONE, true);
 
-    public static final Dop DIV_FLOAT_2ADDR =
-        new Dop(Opcodes.DIV_FLOAT_2ADDR, Opcodes.DIV_FLOAT,
-            Opcodes.DIV_FLOAT, Form12x.THE_ONE, true);
+  public static final Dop ADD_FLOAT_2ADDR =
+      new Dop(Opcodes.ADD_FLOAT_2ADDR, Opcodes.ADD_FLOAT, Opcodes.ADD_FLOAT, Form12x.THE_ONE, true);
 
-    public static final Dop REM_FLOAT_2ADDR =
-        new Dop(Opcodes.REM_FLOAT_2ADDR, Opcodes.REM_FLOAT,
-            Opcodes.REM_FLOAT, Form12x.THE_ONE, true);
+  public static final Dop SUB_FLOAT_2ADDR =
+      new Dop(Opcodes.SUB_FLOAT_2ADDR, Opcodes.SUB_FLOAT, Opcodes.SUB_FLOAT, Form12x.THE_ONE, true);
 
-    public static final Dop ADD_DOUBLE_2ADDR =
-        new Dop(Opcodes.ADD_DOUBLE_2ADDR, Opcodes.ADD_DOUBLE,
-            Opcodes.ADD_DOUBLE, Form12x.THE_ONE, true);
+  public static final Dop MUL_FLOAT_2ADDR =
+      new Dop(Opcodes.MUL_FLOAT_2ADDR, Opcodes.MUL_FLOAT, Opcodes.MUL_FLOAT, Form12x.THE_ONE, true);
 
-    public static final Dop SUB_DOUBLE_2ADDR =
-        new Dop(Opcodes.SUB_DOUBLE_2ADDR, Opcodes.SUB_DOUBLE,
-            Opcodes.SUB_DOUBLE, Form12x.THE_ONE, true);
+  public static final Dop DIV_FLOAT_2ADDR =
+      new Dop(Opcodes.DIV_FLOAT_2ADDR, Opcodes.DIV_FLOAT, Opcodes.DIV_FLOAT, Form12x.THE_ONE, true);
 
-    public static final Dop MUL_DOUBLE_2ADDR =
-        new Dop(Opcodes.MUL_DOUBLE_2ADDR, Opcodes.MUL_DOUBLE,
-            Opcodes.MUL_DOUBLE, Form12x.THE_ONE, true);
+  public static final Dop REM_FLOAT_2ADDR =
+      new Dop(Opcodes.REM_FLOAT_2ADDR, Opcodes.REM_FLOAT, Opcodes.REM_FLOAT, Form12x.THE_ONE, true);
 
-    public static final Dop DIV_DOUBLE_2ADDR =
-        new Dop(Opcodes.DIV_DOUBLE_2ADDR, Opcodes.DIV_DOUBLE,
-            Opcodes.DIV_DOUBLE, Form12x.THE_ONE, true);
+  public static final Dop ADD_DOUBLE_2ADDR = new Dop(Opcodes.ADD_DOUBLE_2ADDR, Opcodes.ADD_DOUBLE,
+      Opcodes.ADD_DOUBLE, Form12x.THE_ONE, true);
 
-    public static final Dop REM_DOUBLE_2ADDR =
-        new Dop(Opcodes.REM_DOUBLE_2ADDR, Opcodes.REM_DOUBLE,
-            Opcodes.REM_DOUBLE, Form12x.THE_ONE, true);
+  public static final Dop SUB_DOUBLE_2ADDR = new Dop(Opcodes.SUB_DOUBLE_2ADDR, Opcodes.SUB_DOUBLE,
+      Opcodes.SUB_DOUBLE, Form12x.THE_ONE, true);
 
-    public static final Dop ADD_INT_LIT16 =
-        new Dop(Opcodes.ADD_INT_LIT16, Opcodes.ADD_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop MUL_DOUBLE_2ADDR = new Dop(Opcodes.MUL_DOUBLE_2ADDR, Opcodes.MUL_DOUBLE,
+      Opcodes.MUL_DOUBLE, Form12x.THE_ONE, true);
 
-    public static final Dop RSUB_INT =
-        new Dop(Opcodes.RSUB_INT, Opcodes.RSUB_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop DIV_DOUBLE_2ADDR = new Dop(Opcodes.DIV_DOUBLE_2ADDR, Opcodes.DIV_DOUBLE,
+      Opcodes.DIV_DOUBLE, Form12x.THE_ONE, true);
 
-    public static final Dop MUL_INT_LIT16 =
-        new Dop(Opcodes.MUL_INT_LIT16, Opcodes.MUL_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop REM_DOUBLE_2ADDR = new Dop(Opcodes.REM_DOUBLE_2ADDR, Opcodes.REM_DOUBLE,
+      Opcodes.REM_DOUBLE, Form12x.THE_ONE, true);
 
-    public static final Dop DIV_INT_LIT16 =
-        new Dop(Opcodes.DIV_INT_LIT16, Opcodes.DIV_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop ADD_INT_LIT16 =
+      new Dop(Opcodes.ADD_INT_LIT16, Opcodes.ADD_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop REM_INT_LIT16 =
-        new Dop(Opcodes.REM_INT_LIT16, Opcodes.REM_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop RSUB_INT =
+      new Dop(Opcodes.RSUB_INT, Opcodes.RSUB_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop AND_INT_LIT16 =
-        new Dop(Opcodes.AND_INT_LIT16, Opcodes.AND_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop MUL_INT_LIT16 =
+      new Dop(Opcodes.MUL_INT_LIT16, Opcodes.MUL_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop OR_INT_LIT16 =
-        new Dop(Opcodes.OR_INT_LIT16, Opcodes.OR_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop DIV_INT_LIT16 =
+      new Dop(Opcodes.DIV_INT_LIT16, Opcodes.DIV_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop XOR_INT_LIT16 =
-        new Dop(Opcodes.XOR_INT_LIT16, Opcodes.XOR_INT,
-            Opcodes.NO_NEXT, Form22s.THE_ONE, true);
+  public static final Dop REM_INT_LIT16 =
+      new Dop(Opcodes.REM_INT_LIT16, Opcodes.REM_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop ADD_INT_LIT8 =
-        new Dop(Opcodes.ADD_INT_LIT8, Opcodes.ADD_INT,
-            Opcodes.ADD_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop AND_INT_LIT16 =
+      new Dop(Opcodes.AND_INT_LIT16, Opcodes.AND_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop RSUB_INT_LIT8 =
-        new Dop(Opcodes.RSUB_INT_LIT8, Opcodes.RSUB_INT,
-            Opcodes.RSUB_INT, Form22b.THE_ONE, true);
+  public static final Dop OR_INT_LIT16 =
+      new Dop(Opcodes.OR_INT_LIT16, Opcodes.OR_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop MUL_INT_LIT8 =
-        new Dop(Opcodes.MUL_INT_LIT8, Opcodes.MUL_INT,
-            Opcodes.MUL_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop XOR_INT_LIT16 =
+      new Dop(Opcodes.XOR_INT_LIT16, Opcodes.XOR_INT, Opcodes.NO_NEXT, Form22s.THE_ONE, true);
 
-    public static final Dop DIV_INT_LIT8 =
-        new Dop(Opcodes.DIV_INT_LIT8, Opcodes.DIV_INT,
-            Opcodes.DIV_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop ADD_INT_LIT8 =
+      new Dop(Opcodes.ADD_INT_LIT8, Opcodes.ADD_INT, Opcodes.ADD_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop REM_INT_LIT8 =
-        new Dop(Opcodes.REM_INT_LIT8, Opcodes.REM_INT,
-            Opcodes.REM_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop RSUB_INT_LIT8 =
+      new Dop(Opcodes.RSUB_INT_LIT8, Opcodes.RSUB_INT, Opcodes.RSUB_INT, Form22b.THE_ONE, true);
 
-    public static final Dop AND_INT_LIT8 =
-        new Dop(Opcodes.AND_INT_LIT8, Opcodes.AND_INT,
-            Opcodes.AND_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop MUL_INT_LIT8 =
+      new Dop(Opcodes.MUL_INT_LIT8, Opcodes.MUL_INT, Opcodes.MUL_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop OR_INT_LIT8 =
-        new Dop(Opcodes.OR_INT_LIT8, Opcodes.OR_INT,
-            Opcodes.OR_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop DIV_INT_LIT8 =
+      new Dop(Opcodes.DIV_INT_LIT8, Opcodes.DIV_INT, Opcodes.DIV_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop XOR_INT_LIT8 =
-        new Dop(Opcodes.XOR_INT_LIT8, Opcodes.XOR_INT,
-            Opcodes.XOR_INT_LIT16, Form22b.THE_ONE, true);
+  public static final Dop REM_INT_LIT8 =
+      new Dop(Opcodes.REM_INT_LIT8, Opcodes.REM_INT, Opcodes.REM_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop SHL_INT_LIT8 =
-        new Dop(Opcodes.SHL_INT_LIT8, Opcodes.SHL_INT,
-            Opcodes.NO_NEXT, Form22b.THE_ONE, true);
+  public static final Dop AND_INT_LIT8 =
+      new Dop(Opcodes.AND_INT_LIT8, Opcodes.AND_INT, Opcodes.AND_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop SHR_INT_LIT8 =
-        new Dop(Opcodes.SHR_INT_LIT8, Opcodes.SHR_INT,
-            Opcodes.NO_NEXT, Form22b.THE_ONE, true);
+  public static final Dop OR_INT_LIT8 =
+      new Dop(Opcodes.OR_INT_LIT8, Opcodes.OR_INT, Opcodes.OR_INT_LIT16, Form22b.THE_ONE, true);
 
-    public static final Dop USHR_INT_LIT8 =
-        new Dop(Opcodes.USHR_INT_LIT8, Opcodes.USHR_INT,
-            Opcodes.NO_NEXT, Form22b.THE_ONE, true);
+  public static final Dop XOR_INT_LIT8 =
+      new Dop(Opcodes.XOR_INT_LIT8, Opcodes.XOR_INT, Opcodes.XOR_INT_LIT16, Form22b.THE_ONE, true);
 
-    // END(dops)
+  public static final Dop SHL_INT_LIT8 =
+      new Dop(Opcodes.SHL_INT_LIT8, Opcodes.SHL_INT, Opcodes.NO_NEXT, Form22b.THE_ONE, true);
 
-    // Static initialization.
-    static {
-        DOPS = new Dop[Opcodes.MAX_VALUE - Opcodes.MIN_VALUE + 1];
+  public static final Dop SHR_INT_LIT8 =
+      new Dop(Opcodes.SHR_INT_LIT8, Opcodes.SHR_INT, Opcodes.NO_NEXT, Form22b.THE_ONE, true);
 
-        set(SPECIAL_FORMAT);
+  public static final Dop USHR_INT_LIT8 =
+      new Dop(Opcodes.USHR_INT_LIT8, Opcodes.USHR_INT, Opcodes.NO_NEXT, Form22b.THE_ONE, true);
 
-        // BEGIN(dops-init); GENERATED AUTOMATICALLY BY opcode-gen
-        set(NOP);
-        set(MOVE);
-        set(MOVE_FROM16);
-        set(MOVE_16);
-        set(MOVE_WIDE);
-        set(MOVE_WIDE_FROM16);
-        set(MOVE_WIDE_16);
-        set(MOVE_OBJECT);
-        set(MOVE_OBJECT_FROM16);
-        set(MOVE_OBJECT_16);
-        set(MOVE_RESULT);
-        set(MOVE_RESULT_WIDE);
-        set(MOVE_RESULT_OBJECT);
-        set(MOVE_EXCEPTION);
-        set(RETURN_VOID);
-        set(RETURN);
-        set(RETURN_WIDE);
-        set(RETURN_OBJECT);
-        set(CONST_4);
-        set(CONST_16);
-        set(CONST);
-        set(CONST_HIGH16);
-        set(CONST_WIDE_16);
-        set(CONST_WIDE_32);
-        set(CONST_WIDE);
-        set(CONST_WIDE_HIGH16);
-        set(CONST_STRING);
-        set(CONST_STRING_JUMBO);
-        set(CONST_CLASS);
-        set(MONITOR_ENTER);
-        set(MONITOR_EXIT);
-        set(CHECK_CAST);
-        set(INSTANCE_OF);
-        set(ARRAY_LENGTH);
-        set(NEW_INSTANCE);
-        set(NEW_ARRAY);
-        set(FILLED_NEW_ARRAY);
-        set(FILLED_NEW_ARRAY_RANGE);
-        set(FILL_ARRAY_DATA);
-        set(THROW);
-        set(GOTO);
-        set(GOTO_16);
-        set(GOTO_32);
-        set(PACKED_SWITCH);
-        set(SPARSE_SWITCH);
-        set(CMPL_FLOAT);
-        set(CMPG_FLOAT);
-        set(CMPL_DOUBLE);
-        set(CMPG_DOUBLE);
-        set(CMP_LONG);
-        set(IF_EQ);
-        set(IF_NE);
-        set(IF_LT);
-        set(IF_GE);
-        set(IF_GT);
-        set(IF_LE);
-        set(IF_EQZ);
-        set(IF_NEZ);
-        set(IF_LTZ);
-        set(IF_GEZ);
-        set(IF_GTZ);
-        set(IF_LEZ);
-        set(AGET);
-        set(AGET_WIDE);
-        set(AGET_OBJECT);
-        set(AGET_BOOLEAN);
-        set(AGET_BYTE);
-        set(AGET_CHAR);
-        set(AGET_SHORT);
-        set(APUT);
-        set(APUT_WIDE);
-        set(APUT_OBJECT);
-        set(APUT_BOOLEAN);
-        set(APUT_BYTE);
-        set(APUT_CHAR);
-        set(APUT_SHORT);
-        set(IGET);
-        set(IGET_WIDE);
-        set(IGET_OBJECT);
-        set(IGET_BOOLEAN);
-        set(IGET_BYTE);
-        set(IGET_CHAR);
-        set(IGET_SHORT);
-        set(IPUT);
-        set(IPUT_WIDE);
-        set(IPUT_OBJECT);
-        set(IPUT_BOOLEAN);
-        set(IPUT_BYTE);
-        set(IPUT_CHAR);
-        set(IPUT_SHORT);
-        set(SGET);
-        set(SGET_WIDE);
-        set(SGET_OBJECT);
-        set(SGET_BOOLEAN);
-        set(SGET_BYTE);
-        set(SGET_CHAR);
-        set(SGET_SHORT);
-        set(SPUT);
-        set(SPUT_WIDE);
-        set(SPUT_OBJECT);
-        set(SPUT_BOOLEAN);
-        set(SPUT_BYTE);
-        set(SPUT_CHAR);
-        set(SPUT_SHORT);
-        set(INVOKE_VIRTUAL);
-        set(INVOKE_SUPER);
-        set(INVOKE_DIRECT);
-        set(INVOKE_STATIC);
-        set(INVOKE_INTERFACE);
-        set(INVOKE_VIRTUAL_RANGE);
-        set(INVOKE_SUPER_RANGE);
-        set(INVOKE_DIRECT_RANGE);
-        set(INVOKE_STATIC_RANGE);
-        set(INVOKE_INTERFACE_RANGE);
-        set(NEG_INT);
-        set(NOT_INT);
-        set(NEG_LONG);
-        set(NOT_LONG);
-        set(NEG_FLOAT);
-        set(NEG_DOUBLE);
-        set(INT_TO_LONG);
-        set(INT_TO_FLOAT);
-        set(INT_TO_DOUBLE);
-        set(LONG_TO_INT);
-        set(LONG_TO_FLOAT);
-        set(LONG_TO_DOUBLE);
-        set(FLOAT_TO_INT);
-        set(FLOAT_TO_LONG);
-        set(FLOAT_TO_DOUBLE);
-        set(DOUBLE_TO_INT);
-        set(DOUBLE_TO_LONG);
-        set(DOUBLE_TO_FLOAT);
-        set(INT_TO_BYTE);
-        set(INT_TO_CHAR);
-        set(INT_TO_SHORT);
-        set(ADD_INT);
-        set(SUB_INT);
-        set(MUL_INT);
-        set(DIV_INT);
-        set(REM_INT);
-        set(AND_INT);
-        set(OR_INT);
-        set(XOR_INT);
-        set(SHL_INT);
-        set(SHR_INT);
-        set(USHR_INT);
-        set(ADD_LONG);
-        set(SUB_LONG);
-        set(MUL_LONG);
-        set(DIV_LONG);
-        set(REM_LONG);
-        set(AND_LONG);
-        set(OR_LONG);
-        set(XOR_LONG);
-        set(SHL_LONG);
-        set(SHR_LONG);
-        set(USHR_LONG);
-        set(ADD_FLOAT);
-        set(SUB_FLOAT);
-        set(MUL_FLOAT);
-        set(DIV_FLOAT);
-        set(REM_FLOAT);
-        set(ADD_DOUBLE);
-        set(SUB_DOUBLE);
-        set(MUL_DOUBLE);
-        set(DIV_DOUBLE);
-        set(REM_DOUBLE);
-        set(ADD_INT_2ADDR);
-        set(SUB_INT_2ADDR);
-        set(MUL_INT_2ADDR);
-        set(DIV_INT_2ADDR);
-        set(REM_INT_2ADDR);
-        set(AND_INT_2ADDR);
-        set(OR_INT_2ADDR);
-        set(XOR_INT_2ADDR);
-        set(SHL_INT_2ADDR);
-        set(SHR_INT_2ADDR);
-        set(USHR_INT_2ADDR);
-        set(ADD_LONG_2ADDR);
-        set(SUB_LONG_2ADDR);
-        set(MUL_LONG_2ADDR);
-        set(DIV_LONG_2ADDR);
-        set(REM_LONG_2ADDR);
-        set(AND_LONG_2ADDR);
-        set(OR_LONG_2ADDR);
-        set(XOR_LONG_2ADDR);
-        set(SHL_LONG_2ADDR);
-        set(SHR_LONG_2ADDR);
-        set(USHR_LONG_2ADDR);
-        set(ADD_FLOAT_2ADDR);
-        set(SUB_FLOAT_2ADDR);
-        set(MUL_FLOAT_2ADDR);
-        set(DIV_FLOAT_2ADDR);
-        set(REM_FLOAT_2ADDR);
-        set(ADD_DOUBLE_2ADDR);
-        set(SUB_DOUBLE_2ADDR);
-        set(MUL_DOUBLE_2ADDR);
-        set(DIV_DOUBLE_2ADDR);
-        set(REM_DOUBLE_2ADDR);
-        set(ADD_INT_LIT16);
-        set(RSUB_INT);
-        set(MUL_INT_LIT16);
-        set(DIV_INT_LIT16);
-        set(REM_INT_LIT16);
-        set(AND_INT_LIT16);
-        set(OR_INT_LIT16);
-        set(XOR_INT_LIT16);
-        set(ADD_INT_LIT8);
-        set(RSUB_INT_LIT8);
-        set(MUL_INT_LIT8);
-        set(DIV_INT_LIT8);
-        set(REM_INT_LIT8);
-        set(AND_INT_LIT8);
-        set(OR_INT_LIT8);
-        set(XOR_INT_LIT8);
-        set(SHL_INT_LIT8);
-        set(SHR_INT_LIT8);
-        set(USHR_INT_LIT8);
-        // END(dops-init)
-    }
+  // END(dops)
 
-    /**
-     * This class is uninstantiable.
-     */
-    private Dops() {
-        // This space intentionally left blank.
-    }
+  // Static initialization.
+  static {
+    DOPS = new Dop[Opcodes.MAX_VALUE - Opcodes.MIN_VALUE + 1];
 
-    /**
-     * Gets the {@link Dop} for the given opcode value.
-     *
-     * @param opcode {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the
-     * opcode value
-     * @return {@code non-null;} the associated opcode instance
-     */
-    public static Dop get(int opcode) {
-        int idx = opcode - Opcodes.MIN_VALUE;
+    set(SPECIAL_FORMAT);
 
-        try {
-            Dop result = DOPS[idx];
-            if (result != null) {
-                return result;
-            }
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Fall through.
-        }
+    // BEGIN(dops-init); GENERATED AUTOMATICALLY BY opcode-gen
+    set(NOP);
+    set(MOVE);
+    set(MOVE_FROM16);
+    set(MOVE_16);
+    set(MOVE_WIDE);
+    set(MOVE_WIDE_FROM16);
+    set(MOVE_WIDE_16);
+    set(MOVE_OBJECT);
+    set(MOVE_OBJECT_FROM16);
+    set(MOVE_OBJECT_16);
+    set(MOVE_RESULT);
+    set(MOVE_RESULT_WIDE);
+    set(MOVE_RESULT_OBJECT);
+    set(MOVE_EXCEPTION);
+    set(RETURN_VOID);
+    set(RETURN);
+    set(RETURN_WIDE);
+    set(RETURN_OBJECT);
+    set(CONST_4);
+    set(CONST_16);
+    set(CONST);
+    set(CONST_HIGH16);
+    set(CONST_WIDE_16);
+    set(CONST_WIDE_32);
+    set(CONST_WIDE);
+    set(CONST_WIDE_HIGH16);
+    set(CONST_STRING);
+    set(CONST_STRING_JUMBO);
+    set(CONST_CLASS);
+    set(MONITOR_ENTER);
+    set(MONITOR_EXIT);
+    set(CHECK_CAST);
+    set(INSTANCE_OF);
+    set(ARRAY_LENGTH);
+    set(NEW_INSTANCE);
+    set(NEW_ARRAY);
+    set(FILLED_NEW_ARRAY);
+    set(FILLED_NEW_ARRAY_RANGE);
+    set(FILL_ARRAY_DATA);
+    set(THROW);
+    set(GOTO);
+    set(GOTO_16);
+    set(GOTO_32);
+    set(PACKED_SWITCH);
+    set(SPARSE_SWITCH);
+    set(CMPL_FLOAT);
+    set(CMPG_FLOAT);
+    set(CMPL_DOUBLE);
+    set(CMPG_DOUBLE);
+    set(CMP_LONG);
+    set(IF_EQ);
+    set(IF_NE);
+    set(IF_LT);
+    set(IF_GE);
+    set(IF_GT);
+    set(IF_LE);
+    set(IF_EQZ);
+    set(IF_NEZ);
+    set(IF_LTZ);
+    set(IF_GEZ);
+    set(IF_GTZ);
+    set(IF_LEZ);
+    set(AGET);
+    set(AGET_WIDE);
+    set(AGET_OBJECT);
+    set(AGET_BOOLEAN);
+    set(AGET_BYTE);
+    set(AGET_CHAR);
+    set(AGET_SHORT);
+    set(APUT);
+    set(APUT_WIDE);
+    set(APUT_OBJECT);
+    set(APUT_BOOLEAN);
+    set(APUT_BYTE);
+    set(APUT_CHAR);
+    set(APUT_SHORT);
+    set(IGET);
+    set(IGET_WIDE);
+    set(IGET_OBJECT);
+    set(IGET_BOOLEAN);
+    set(IGET_BYTE);
+    set(IGET_CHAR);
+    set(IGET_SHORT);
+    set(IPUT);
+    set(IPUT_WIDE);
+    set(IPUT_OBJECT);
+    set(IPUT_BOOLEAN);
+    set(IPUT_BYTE);
+    set(IPUT_CHAR);
+    set(IPUT_SHORT);
+    set(SGET);
+    set(SGET_WIDE);
+    set(SGET_OBJECT);
+    set(SGET_BOOLEAN);
+    set(SGET_BYTE);
+    set(SGET_CHAR);
+    set(SGET_SHORT);
+    set(SPUT);
+    set(SPUT_WIDE);
+    set(SPUT_OBJECT);
+    set(SPUT_BOOLEAN);
+    set(SPUT_BYTE);
+    set(SPUT_CHAR);
+    set(SPUT_SHORT);
+    set(INVOKE_VIRTUAL);
+    set(INVOKE_SUPER);
+    set(INVOKE_DIRECT);
+    set(INVOKE_STATIC);
+    set(INVOKE_INTERFACE);
+    set(INVOKE_VIRTUAL_RANGE);
+    set(INVOKE_SUPER_RANGE);
+    set(INVOKE_DIRECT_RANGE);
+    set(INVOKE_STATIC_RANGE);
+    set(INVOKE_INTERFACE_RANGE);
+    set(NEG_INT);
+    set(NOT_INT);
+    set(NEG_LONG);
+    set(NOT_LONG);
+    set(NEG_FLOAT);
+    set(NEG_DOUBLE);
+    set(INT_TO_LONG);
+    set(INT_TO_FLOAT);
+    set(INT_TO_DOUBLE);
+    set(LONG_TO_INT);
+    set(LONG_TO_FLOAT);
+    set(LONG_TO_DOUBLE);
+    set(FLOAT_TO_INT);
+    set(FLOAT_TO_LONG);
+    set(FLOAT_TO_DOUBLE);
+    set(DOUBLE_TO_INT);
+    set(DOUBLE_TO_LONG);
+    set(DOUBLE_TO_FLOAT);
+    set(INT_TO_BYTE);
+    set(INT_TO_CHAR);
+    set(INT_TO_SHORT);
+    set(ADD_INT);
+    set(SUB_INT);
+    set(MUL_INT);
+    set(DIV_INT);
+    set(REM_INT);
+    set(AND_INT);
+    set(OR_INT);
+    set(XOR_INT);
+    set(SHL_INT);
+    set(SHR_INT);
+    set(USHR_INT);
+    set(ADD_LONG);
+    set(SUB_LONG);
+    set(MUL_LONG);
+    set(DIV_LONG);
+    set(REM_LONG);
+    set(AND_LONG);
+    set(OR_LONG);
+    set(XOR_LONG);
+    set(SHL_LONG);
+    set(SHR_LONG);
+    set(USHR_LONG);
+    set(ADD_FLOAT);
+    set(SUB_FLOAT);
+    set(MUL_FLOAT);
+    set(DIV_FLOAT);
+    set(REM_FLOAT);
+    set(ADD_DOUBLE);
+    set(SUB_DOUBLE);
+    set(MUL_DOUBLE);
+    set(DIV_DOUBLE);
+    set(REM_DOUBLE);
+    set(ADD_INT_2ADDR);
+    set(SUB_INT_2ADDR);
+    set(MUL_INT_2ADDR);
+    set(DIV_INT_2ADDR);
+    set(REM_INT_2ADDR);
+    set(AND_INT_2ADDR);
+    set(OR_INT_2ADDR);
+    set(XOR_INT_2ADDR);
+    set(SHL_INT_2ADDR);
+    set(SHR_INT_2ADDR);
+    set(USHR_INT_2ADDR);
+    set(ADD_LONG_2ADDR);
+    set(SUB_LONG_2ADDR);
+    set(MUL_LONG_2ADDR);
+    set(DIV_LONG_2ADDR);
+    set(REM_LONG_2ADDR);
+    set(AND_LONG_2ADDR);
+    set(OR_LONG_2ADDR);
+    set(XOR_LONG_2ADDR);
+    set(SHL_LONG_2ADDR);
+    set(SHR_LONG_2ADDR);
+    set(USHR_LONG_2ADDR);
+    set(ADD_FLOAT_2ADDR);
+    set(SUB_FLOAT_2ADDR);
+    set(MUL_FLOAT_2ADDR);
+    set(DIV_FLOAT_2ADDR);
+    set(REM_FLOAT_2ADDR);
+    set(ADD_DOUBLE_2ADDR);
+    set(SUB_DOUBLE_2ADDR);
+    set(MUL_DOUBLE_2ADDR);
+    set(DIV_DOUBLE_2ADDR);
+    set(REM_DOUBLE_2ADDR);
+    set(ADD_INT_LIT16);
+    set(RSUB_INT);
+    set(MUL_INT_LIT16);
+    set(DIV_INT_LIT16);
+    set(REM_INT_LIT16);
+    set(AND_INT_LIT16);
+    set(OR_INT_LIT16);
+    set(XOR_INT_LIT16);
+    set(ADD_INT_LIT8);
+    set(RSUB_INT_LIT8);
+    set(MUL_INT_LIT8);
+    set(DIV_INT_LIT8);
+    set(REM_INT_LIT8);
+    set(AND_INT_LIT8);
+    set(OR_INT_LIT8);
+    set(XOR_INT_LIT8);
+    set(SHL_INT_LIT8);
+    set(SHR_INT_LIT8);
+    set(USHR_INT_LIT8);
+    // END(dops-init)
+  }
 
-        throw new IllegalArgumentException("bogus opcode");
-    }
+  /**
+   * This class is uninstantiable.
+   */
+  private Dops() {
+    // This space intentionally left blank.
+  }
 
-    /**
-     * Gets the next {@link Dop} in the instruction fitting chain after the
-     * given instance, if any.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param options {@code non-null;} options, used to determine
-     * which opcodes are potentially off-limits
-     * @return {@code null-ok;} the next opcode in the same family, in the
-     * chain of opcodes to try, or {@code null} if the given opcode is
-     * the last in its chain
-     */
-    public static Dop getNextOrNull(Dop opcode, DexOptions options) {
-      int nextOpcode = opcode.getNextOpcode();
+  /**
+   * Gets the {@link Dop} for the given opcode value.
+   *
+   * @param opcode {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the
+   * opcode value
+   * @return {@code non-null;} the associated opcode instance
+   */
+  public static Dop get(int opcode) {
+    int idx = opcode - Opcodes.MIN_VALUE;
 
-      if (nextOpcode == Opcodes.NO_NEXT) {
-        return null;
+    try {
+      Dop result = DOPS[idx];
+      if (result != null) {
+        return result;
       }
-
-      opcode = get(nextOpcode);
-
-      return opcode;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Fall through.
     }
 
-    /**
-     * Puts the given opcode into the table of all ops.
-     *
-     * @param opcode {@code non-null;} the opcode
-     */
-    private static void set(Dop opcode) {
-        int idx = opcode.getOpcode() - Opcodes.MIN_VALUE;
-        DOPS[idx] = opcode;
+    throw new IllegalArgumentException("bogus opcode");
+  }
+
+  /**
+   * Gets the next {@link Dop} in the instruction fitting chain after the
+   * given instance, if any.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param options {@code non-null;} options, used to determine
+   * which opcodes are potentially off-limits
+   * @return {@code null-ok;} the next opcode in the same family, in the
+   * chain of opcodes to try, or {@code null} if the given opcode is
+   * the last in its chain
+   */
+  public static Dop getNextOrNull(Dop opcode, DexOptions options) {
+    int nextOpcode = opcode.getNextOpcode();
+
+    if (nextOpcode == Opcodes.NO_NEXT) {
+      return null;
     }
+
+    opcode = get(nextOpcode);
+
+    return opcode;
+  }
+
+  /**
+   * Puts the given opcode into the table of all ops.
+   *
+   * @param opcode {@code non-null;} the opcode
+   */
+  private static void set(Dop opcode) {
+    int idx = opcode.getOpcode() - Opcodes.MIN_VALUE;
+    DOPS[idx] = opcode;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/FixedSizeInsn.java b/dx/src/com/android/jack/dx/dex/code/FixedSizeInsn.java
index d3ab83c..5718b61 100644
--- a/dx/src/com/android/jack/dx/dex/code/FixedSizeInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/FixedSizeInsn.java
@@ -26,48 +26,47 @@
  * includes most &mdash; but not all &mdash; instructions.
  */
 public abstract class FixedSizeInsn extends DalvInsn {
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * <p><b>Note:</b> In the unlikely event that an instruction takes
-     * absolutely no registers (e.g., a {@code nop} or a
-     * no-argument no-result * static method call), then the given
-     * register list may be passed as {@link
-     * RegisterSpecList#EMPTY}.</p>
-     *
-     * @param opcode the opcode; one of the constants from {@link Dops}
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} register list, including a
-     * result register if appropriate (that is, registers may be either
-     * ins or outs)
-     */
-    public FixedSizeInsn(Dop opcode, SourcePosition position,
-                         RegisterSpecList registers) {
-        super(opcode, position, registers);
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * <p><b>Note:</b> In the unlikely event that an instruction takes
+   * absolutely no registers (e.g., a {@code nop} or a
+   * no-argument no-result * static method call), then the given
+   * register list may be passed as {@link
+   * RegisterSpecList#EMPTY}.</p>
+   *
+   * @param opcode the opcode; one of the constants from {@link Dops}
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} register list, including a
+   * result register if appropriate (that is, registers may be either
+   * ins or outs)
+   */
+  public FixedSizeInsn(Dop opcode, SourcePosition position, RegisterSpecList registers) {
+    super(opcode, position, registers);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final int codeSize() {
-        return getOpcode().getFormat().codeSize();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final int codeSize() {
+    return getOpcode().getFormat().codeSize();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final void writeTo(AnnotatedOutput out) {
-        getOpcode().getFormat().writeTo(out, this);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final void writeTo(AnnotatedOutput out) {
+    getOpcode().getFormat().writeTo(out, this);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final DalvInsn withRegisterOffset(int delta) {
-        return withRegisters(getRegisters().withOffset(delta));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final DalvInsn withRegisterOffset(int delta) {
+    return withRegisters(getRegisters().withOffset(delta));
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected final String listingString0(boolean noteIndices) {
-        return getOpcode().getFormat().listingString(this, noteIndices);
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected final String listingString0(boolean noteIndices) {
+    return getOpcode().getFormat().listingString(this, noteIndices);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/HighRegisterPrefix.java b/dx/src/com/android/jack/dx/dex/code/HighRegisterPrefix.java
index 424db5e..8f9b185 100644
--- a/dx/src/com/android/jack/dx/dex/code/HighRegisterPrefix.java
+++ b/dx/src/com/android/jack/dx/dex/code/HighRegisterPrefix.java
@@ -19,7 +19,6 @@
 import com.android.jack.dx.rop.code.RegisterSpec;
 import com.android.jack.dx.rop.code.RegisterSpecList;
 import com.android.jack.dx.rop.code.SourcePosition;
-import com.android.jack.dx.rop.type.Type;
 import com.android.jack.dx.util.AnnotatedOutput;
 
 /**
@@ -30,118 +29,116 @@
  * be met using a straightforward choice of a single opcode.
  */
 public final class HighRegisterPrefix extends VariableSizeInsn {
-    /** {@code null-ok;} cached instructions, if constructed */
-    private SimpleInsn[] insns;
+  /** {@code null-ok;} cached instructions, if constructed */
+  private SimpleInsn[] insns;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} source registers
-     */
-    public HighRegisterPrefix(SourcePosition position,
-                              RegisterSpecList registers) {
-        super(position, registers);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} source registers
+   */
+  public HighRegisterPrefix(SourcePosition position, RegisterSpecList registers) {
+    super(position, registers);
 
-        if (registers.size() == 0) {
-            throw new IllegalArgumentException("registers.size() == 0");
-        }
-
-        insns = null;
+    if (registers.size() == 0) {
+      throw new IllegalArgumentException("registers.size() == 0");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        int result = 0;
+    insns = null;
+  }
 
-        calculateInsnsIfNecessary();
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    int result = 0;
 
-        for (SimpleInsn insn : insns) {
-            result += insn.codeSize();
-        }
+    calculateInsnsIfNecessary();
 
-        return result;
+    for (SimpleInsn insn : insns) {
+      result += insn.codeSize();
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out) {
-        calculateInsnsIfNecessary();
+    return result;
+  }
 
-        for (SimpleInsn insn : insns) {
-            insn.writeTo(out);
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out) {
+    calculateInsnsIfNecessary();
+
+    for (SimpleInsn insn : insns) {
+      insn.writeTo(out);
+    }
+  }
+
+  /**
+   * Helper for {@link #codeSize} and {@link #writeTo} which sets up
+   * {@link #insns} if not already done.
+   */
+  private void calculateInsnsIfNecessary() {
+    if (insns != null) {
+      return;
     }
 
-    /**
-     * Helper for {@link #codeSize} and {@link #writeTo} which sets up
-     * {@link #insns} if not already done.
-     */
-    private void calculateInsnsIfNecessary() {
-        if (insns != null) {
-            return;
-        }
+    RegisterSpecList registers = getRegisters();
+    int sz = registers.size();
 
-        RegisterSpecList registers = getRegisters();
-        int sz = registers.size();
+    insns = new SimpleInsn[sz];
 
-        insns = new SimpleInsn[sz];
+    for (int i = 0, outAt = 0; i < sz; i++) {
+      RegisterSpec src = registers.get(i);
+      insns[i] = moveInsnFor(src, outAt);
+      outAt += src.getCategory();
+    }
+  }
 
-        for (int i = 0, outAt = 0; i < sz; i++) {
-            RegisterSpec src = registers.get(i);
-            insns[i] = moveInsnFor(src, outAt);
-            outAt += src.getCategory();
-        }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new HighRegisterPrefix(getPosition(), registers);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    RegisterSpecList registers = getRegisters();
+    int sz = registers.size();
+    StringBuffer sb = new StringBuffer(100);
+
+    for (int i = 0, outAt = 0; i < sz; i++) {
+      RegisterSpec src = registers.get(i);
+      SimpleInsn insn = moveInsnFor(src, outAt);
+
+      if (i != 0) {
+        sb.append('\n');
+      }
+
+      sb.append(insn.listingString0(noteIndices));
+
+      outAt += src.getCategory();
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new HighRegisterPrefix(getPosition(), registers);
-    }
+    return sb.toString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return null;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        RegisterSpecList registers = getRegisters();
-        int sz = registers.size();
-        StringBuffer sb = new StringBuffer(100);
-
-        for (int i = 0, outAt = 0; i < sz; i++) {
-            RegisterSpec src = registers.get(i);
-            SimpleInsn insn = moveInsnFor(src, outAt);
-
-            if (i != 0) {
-                sb.append('\n');
-            }
-
-            sb.append(insn.listingString0(noteIndices));
-
-            outAt += src.getCategory();
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * Returns the proper move instruction for the given source spec
-     * and destination index.
-     *
-     * @param src {@code non-null;} the source register spec
-     * @param destIndex {@code >= 0;} the destination register index
-     * @return {@code non-null;} the appropriate move instruction
-     */
-    private static SimpleInsn moveInsnFor(RegisterSpec src, int destIndex) {
-        return DalvInsn.makeMove(SourcePosition.NO_INFO,
-                RegisterSpec.make(destIndex, src.getType()),
-                src);
-    }
+  /**
+   * Returns the proper move instruction for the given source spec
+   * and destination index.
+   *
+   * @param src {@code non-null;} the source register spec
+   * @param destIndex {@code >= 0;} the destination register index
+   * @return {@code non-null;} the appropriate move instruction
+   */
+  private static SimpleInsn moveInsnFor(RegisterSpec src, int destIndex) {
+    return DalvInsn.makeMove(SourcePosition.NO_INFO, RegisterSpec.make(destIndex, src.getType()),
+        src);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/InsnFormat.java b/dx/src/com/android/jack/dx/dex/code/InsnFormat.java
index ab09b69..276d573 100644
--- a/dx/src/com/android/jack/dx/dex/code/InsnFormat.java
+++ b/dx/src/com/android/jack/dx/dex/code/InsnFormat.java
@@ -36,679 +36,691 @@
  * representing such translations.
  */
 public abstract class InsnFormat {
-    /**
-     * flag to enable/disable the new extended opcode formats; meant as a
-     * temporary measure until VM support for the salient opcodes is
-     * added. TODO: Remove this declaration when the VM can deal.
-     */
-    public static boolean ALLOW_EXTENDED_OPCODES = true;
+  /**
+   * flag to enable/disable the new extended opcode formats; meant as a
+   * temporary measure until VM support for the salient opcodes is
+   * added. TODO(dx team): Remove this declaration when the VM can deal.
+   */
+  public static final boolean ALLOW_EXTENDED_OPCODES = true;
 
-    /**
-     * Returns the string form, suitable for inclusion in a listing
-     * dump, of the given instruction. The instruction must be of this
-     * instance's format for proper operation.
-     *
-     * @param insn {@code non-null;} the instruction
-     * @param noteIndices whether to include an explicit notation of
-     * constant pool indices
-     * @return {@code non-null;} the string form
-     */
-    public final String listingString(DalvInsn insn, boolean noteIndices) {
-        String op = insn.getOpcode().getName();
-        String arg = insnArgString(insn);
-        String comment = insnCommentString(insn, noteIndices);
-        StringBuilder sb = new StringBuilder(100);
+  /**
+   * Returns the string form, suitable for inclusion in a listing
+   * dump, of the given instruction. The instruction must be of this
+   * instance's format for proper operation.
+   *
+   * @param insn {@code non-null;} the instruction
+   * @param noteIndices whether to include an explicit notation of
+   * constant pool indices
+   * @return {@code non-null;} the string form
+   */
+  public final String listingString(DalvInsn insn, boolean noteIndices) {
+    String op = insn.getOpcode().getName();
+    String arg = insnArgString(insn);
+    String comment = insnCommentString(insn, noteIndices);
+    StringBuilder sb = new StringBuilder(100);
 
-        sb.append(op);
+    sb.append(op);
 
-        if (arg.length() != 0) {
-            sb.append(' ');
-            sb.append(arg);
-        }
-
-        if (comment.length() != 0) {
-            sb.append(" // ");
-            sb.append(comment);
-        }
-
-        return sb.toString();
+    if (arg.length() != 0) {
+      sb.append(' ');
+      sb.append(arg);
     }
 
-    /**
-     * Returns the string form of the arguments to the given instruction.
-     * The instruction must be of this instance's format. If the instruction
-     * has no arguments, then the result should be {@code ""}, not
-     * {@code null}.
-     *
-     * <p>Subclasses must override this method.</p>
-     *
-     * @param insn {@code non-null;} the instruction
-     * @return {@code non-null;} the string form
-     */
-    public abstract String insnArgString(DalvInsn insn);
-
-    /**
-     * Returns the associated comment for the given instruction, if any.
-     * The instruction must be of this instance's format. If the instruction
-     * has no comment, then the result should be {@code ""}, not
-     * {@code null}.
-     *
-     * <p>Subclasses must override this method.</p>
-     *
-     * @param insn {@code non-null;} the instruction
-     * @param noteIndices whether to include an explicit notation of
-     * constant pool indices
-     * @return {@code non-null;} the string form
-     */
-    public abstract String insnCommentString(DalvInsn insn,
-            boolean noteIndices);
-
-    /**
-     * Gets the code size of instructions that use this format. The
-     * size is a number of 16-bit code units, not bytes. This should
-     * throw an exception if this format is of variable size.
-     *
-     * @return {@code >= 0;} the instruction length in 16-bit code units
-     */
-    public abstract int codeSize();
-
-    /**
-     * Returns whether or not the given instruction's arguments will
-     * fit in this instance's format. This includes such things as
-     * counting register arguments, checking register ranges, and
-     * making sure that additional arguments are of appropriate types
-     * and are in-range. If this format has a branch target but the
-     * instruction's branch offset is unknown, this method will simply
-     * not check the offset.
-     *
-     * <p>Subclasses must override this method.</p>
-     *
-     * @param insn {@code non-null;} the instruction to check
-     * @return {@code true} iff the instruction's arguments are
-     * appropriate for this instance, or {@code false} if not
-     */
-    public abstract boolean isCompatible(DalvInsn insn);
-
-    /**
-     * Returns which of a given instruction's registers will fit in
-     * this instance's format.
-     *
-     * <p>The default implementation of this method always returns
-     * an empty BitSet. Subclasses must override this method if they
-     * have registers.</p>
-     *
-     * @param insn {@code non-null;} the instruction to check
-     * @return {@code non-null;} a BitSet flagging registers in the
-     * register list that are compatible to this format
-     */
-    public BitSet compatibleRegs(DalvInsn insn) {
-        return new BitSet();
+    if (comment.length() != 0) {
+      sb.append(" // ");
+      sb.append(comment);
     }
 
-    /**
-     * Returns whether or not the given instruction's branch offset will
-     * fit in this instance's format. This always returns {@code false}
-     * for formats that don't include a branch offset.
-     *
-     * <p>The default implementation of this method always returns
-     * {@code false}. Subclasses must override this method if they
-     * include branch offsets.</p>
-     *
-     * @param insn {@code non-null;} the instruction to check
-     * @return {@code true} iff the instruction's branch offset is
-     * appropriate for this instance, or {@code false} if not
-     */
-    public boolean branchFits(TargetInsn insn) {
+    return sb.toString();
+  }
+
+  /**
+   * Returns the string form of the arguments to the given instruction.
+   * The instruction must be of this instance's format. If the instruction
+   * has no arguments, then the result should be {@code ""}, not
+   * {@code null}.
+   *
+   * <p>Subclasses must override this method.</p>
+   *
+   * @param insn {@code non-null;} the instruction
+   * @return {@code non-null;} the string form
+   */
+  public abstract String insnArgString(DalvInsn insn);
+
+  /**
+   * Returns the associated comment for the given instruction, if any.
+   * The instruction must be of this instance's format. If the instruction
+   * has no comment, then the result should be {@code ""}, not
+   * {@code null}.
+   *
+   * <p>Subclasses must override this method.</p>
+   *
+   * @param insn {@code non-null;} the instruction
+   * @param noteIndices whether to include an explicit notation of
+   * constant pool indices
+   * @return {@code non-null;} the string form
+   */
+  public abstract String insnCommentString(DalvInsn insn, boolean noteIndices);
+
+  /**
+   * Gets the code size of instructions that use this format. The
+   * size is a number of 16-bit code units, not bytes. This should
+   * throw an exception if this format is of variable size.
+   *
+   * @return {@code >= 0;} the instruction length in 16-bit code units
+   */
+  public abstract int codeSize();
+
+  /**
+   * Returns whether or not the given instruction's arguments will
+   * fit in this instance's format. This includes such things as
+   * counting register arguments, checking register ranges, and
+   * making sure that additional arguments are of appropriate types
+   * and are in-range. If this format has a branch target but the
+   * instruction's branch offset is unknown, this method will simply
+   * not check the offset.
+   *
+   * <p>Subclasses must override this method.</p>
+   *
+   * @param insn {@code non-null;} the instruction to check
+   * @return {@code true} iff the instruction's arguments are
+   * appropriate for this instance, or {@code false} if not
+   */
+  public abstract boolean isCompatible(DalvInsn insn);
+
+  /**
+   * Returns which of a given instruction's registers will fit in
+   * this instance's format.
+   *
+   * <p>The default implementation of this method always returns
+   * an empty BitSet. Subclasses must override this method if they
+   * have registers.</p>
+   *
+   * @param insn {@code non-null;} the instruction to check
+   * @return {@code non-null;} a BitSet flagging registers in the
+   * register list that are compatible to this format
+   */
+  public BitSet compatibleRegs(DalvInsn insn) {
+    return new BitSet();
+  }
+
+  /**
+   * Returns whether or not the given instruction's branch offset will
+   * fit in this instance's format. This always returns {@code false}
+   * for formats that don't include a branch offset.
+   *
+   * <p>The default implementation of this method always returns
+   * {@code false}. Subclasses must override this method if they
+   * include branch offsets.</p>
+   *
+   * @param insn {@code non-null;} the instruction to check
+   * @return {@code true} iff the instruction's branch offset is
+   * appropriate for this instance, or {@code false} if not
+   */
+  public boolean branchFits(TargetInsn insn) {
+    return false;
+  }
+
+  /**
+   * Writes the code units for the given instruction to the given
+   * output destination. The instruction must be of this instance's format.
+   *
+   * <p>Subclasses must override this method.</p>
+   *
+   * @param out {@code non-null;} the output destination to write to
+   * @param insn {@code non-null;} the instruction to write
+   */
+  public abstract void writeTo(AnnotatedOutput out, DalvInsn insn);
+
+  /**
+   * Helper method to return a register list string.
+   *
+   * @param list {@code non-null;} the list of registers
+   * @return {@code non-null;} the string form
+   */
+  protected static String regListString(RegisterSpecList list) {
+    int sz = list.size();
+    StringBuffer sb = new StringBuffer(sz * 5 + 2);
+
+    sb.append('{');
+
+    for (int i = 0; i < sz; i++) {
+      if (i != 0) {
+        sb.append(", ");
+      }
+      sb.append(list.get(i).regString());
+    }
+
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper method to return a register range string.
+   *
+   * @param list {@code non-null;} the list of registers (which must be
+   * sequential)
+   * @return {@code non-null;} the string form
+   */
+  protected static String regRangeString(RegisterSpecList list) {
+    int size = list.size();
+    StringBuilder sb = new StringBuilder(30);
+
+    sb.append("{");
+
+    switch (size) {
+      case 0: {
+        // Nothing to do.
+        break;
+      }
+      case 1: {
+        sb.append(list.get(0).regString());
+        break;
+      }
+      default: {
+        RegisterSpec lastReg = list.get(size - 1);
+        if (lastReg.getCategory() == 2) {
+          /*
+           * Add one to properly represent a list-final
+           * category-2 register.
+           */
+          lastReg = lastReg.withOffset(1);
+        }
+
+        sb.append(list.get(0).regString());
+        sb.append("..");
+        sb.append(lastReg.regString());
+      }
+    }
+
+    sb.append("}");
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper method to return a literal bits argument string.
+   *
+   * @param value the value
+   * @return {@code non-null;} the string form
+   */
+  protected static String literalBitsString(CstLiteralBits value) {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append('#');
+
+    if (value instanceof CstKnownNull) {
+      sb.append("null");
+    } else {
+      sb.append(value.typeName());
+      sb.append(' ');
+      sb.append(value.toHuman());
+    }
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper method to return a literal bits comment string.
+   *
+   * @param value the value
+   * @param width the width of the constant, in bits (used for displaying
+   * the uninterpreted bits; one of: {@code 4 8 16 32 64}
+   * @return {@code non-null;} the comment
+   */
+  protected static String literalBitsComment(CstLiteralBits value, int width) {
+    StringBuffer sb = new StringBuffer(20);
+
+    sb.append("#");
+
+    long bits;
+
+    if (value instanceof CstLiteral64) {
+      bits = ((CstLiteral64) value).getLongBits();
+    } else {
+      bits = value.getIntBits();
+    }
+
+    switch (width) {
+      case 4:
+        sb.append(Hex.uNibble((int) bits));
+        break;
+      case 8:
+        sb.append(Hex.u1((int) bits));
+        break;
+      case 16:
+        sb.append(Hex.u2((int) bits));
+        break;
+      case 32:
+        sb.append(Hex.u4((int) bits));
+        break;
+      case 64:
+        sb.append(Hex.u8(bits));
+        break;
+      default: {
+        throw new RuntimeException("shouldn't happen");
+      }
+    }
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper method to return a branch address string.
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @return {@code non-null;} the string form of the instruction's
+   * branch target
+   */
+  protected static String branchString(DalvInsn insn) {
+    TargetInsn ti = (TargetInsn) insn;
+    int address = ti.getTargetAddress();
+
+    return (address == (char) address) ? Hex.u2(address) : Hex.u4(address);
+  }
+
+  /**
+   * Helper method to return the comment for a branch.
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @return {@code non-null;} the comment
+   */
+  protected static String branchComment(DalvInsn insn) {
+    TargetInsn ti = (TargetInsn) insn;
+    int offset = ti.getTargetOffset();
+
+    return (offset == (short) offset) ? Hex.s2(offset) : Hex.s4(offset);
+  }
+
+  /**
+   * Helper method to return the constant string for a {@link CstInsn}
+   * in human form.
+   *
+   * @param insn {@code non-null;} a constant-bearing instruction
+   * @return {@code non-null;} the human string form of the contained
+   * constant
+   */
+  protected static String cstString(DalvInsn insn) {
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
+
+    return cst instanceof CstString ? ((CstString) cst).toQuoted() : cst.toHuman();
+  }
+
+  /**
+   * Helper method to return an instruction comment for a constant.
+   *
+   * @param insn {@code non-null;} a constant-bearing instruction
+   * @return {@code non-null;} comment string representing the constant
+   */
+  protected static String cstComment(DalvInsn insn) {
+    CstInsn ci = (CstInsn) insn;
+
+    if (!ci.hasIndex()) {
+      return "";
+    }
+
+    StringBuilder sb = new StringBuilder(20);
+    int index = ci.getIndex();
+
+    sb.append(ci.getConstant().typeName());
+    sb.append('@');
+
+    if (index < 65536) {
+      sb.append(Hex.u2(index));
+    } else {
+      sb.append(Hex.u4(index));
+    }
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper method to determine if a signed int value fits in a nibble.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range -8..+7
+   */
+  protected static boolean signedFitsInNibble(int value) {
+    return (value >= -8) && (value <= 7);
+  }
+
+  /**
+   * Helper method to determine if an unsigned int value fits in a nibble.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range 0..0xf
+   */
+  protected static boolean unsignedFitsInNibble(int value) {
+    return value == (value & 0xf);
+  }
+
+  /**
+   * Helper method to determine if a signed int value fits in a byte.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range -0x80..+0x7f
+   */
+  protected static boolean signedFitsInByte(int value) {
+    return (byte) value == value;
+  }
+
+  /**
+   * Helper method to determine if an unsigned int value fits in a byte.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range 0..0xff
+   */
+  protected static boolean unsignedFitsInByte(int value) {
+    return value == (value & 0xff);
+  }
+
+  /**
+   * Helper method to determine if a signed int value fits in a short.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range -0x8000..+0x7fff
+   */
+  protected static boolean signedFitsInShort(int value) {
+    return (short) value == value;
+  }
+
+  /**
+   * Helper method to determine if an unsigned int value fits in a short.
+   *
+   * @param value the value in question
+   * @return {@code true} iff it's in the range 0..0xffff
+   */
+  protected static boolean unsignedFitsInShort(int value) {
+    return value == (value & 0xffff);
+  }
+
+  /**
+   * Helper method to determine if a list of registers are sequential,
+   * including degenerate cases for empty or single-element lists.
+   *
+   * @param list {@code non-null;} the list of registers
+   * @return {@code true} iff the list is sequentially ordered
+   */
+  protected static boolean isRegListSequential(RegisterSpecList list) {
+    int sz = list.size();
+
+    if (sz < 2) {
+      return true;
+    }
+
+    int first = list.get(0).getReg();
+    int next = first;
+
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec one = list.get(i);
+      if (one.getReg() != next) {
         return false;
+      }
+      next += one.getCategory();
     }
 
-    /**
-     * Writes the code units for the given instruction to the given
-     * output destination. The instruction must be of this instance's format.
-     *
-     * <p>Subclasses must override this method.</p>
-     *
-     * @param out {@code non-null;} the output destination to write to
-     * @param insn {@code non-null;} the instruction to write
-     */
-    public abstract void writeTo(AnnotatedOutput out, DalvInsn insn);
+    return true;
+  }
 
-    /**
-     * Helper method to return a register list string.
-     *
-     * @param list {@code non-null;} the list of registers
-     * @return {@code non-null;} the string form
-     */
-    protected static String regListString(RegisterSpecList list) {
-        int sz = list.size();
-        StringBuffer sb = new StringBuffer(sz * 5 + 2);
+  /**
+   * Helper method to extract the callout-argument index from an
+   * appropriate instruction.
+   *
+   * @param insn {@code non-null;} the instruction
+   * @return {@code >= 0;} the callout argument index
+   */
+  protected static int argIndex(DalvInsn insn) {
+    int arg = ((CstInteger) ((CstInsn) insn).getConstant()).getValue();
 
-        sb.append('{');
-
-        for (int i = 0; i < sz; i++) {
-            if (i != 0) {
-                sb.append(", ");
-            }
-            sb.append(list.get(i).regString());
-        }
-
-        sb.append('}');
-
-        return sb.toString();
+    if (arg < 0) {
+      throw new IllegalArgumentException("bogus insn");
     }
 
-    /**
-     * Helper method to return a register range string.
-     *
-     * @param list {@code non-null;} the list of registers (which must be
-     * sequential)
-     * @return {@code non-null;} the string form
-     */
-    protected static String regRangeString(RegisterSpecList list) {
-        int size = list.size();
-        StringBuilder sb = new StringBuilder(30);
+    return arg;
+  }
 
-        sb.append("{");
-
-        switch (size) {
-            case 0: {
-                // Nothing to do.
-                break;
-            }
-            case 1: {
-                sb.append(list.get(0).regString());
-                break;
-            }
-            default: {
-                RegisterSpec lastReg = list.get(size - 1);
-                if (lastReg.getCategory() == 2) {
-                    /*
-                     * Add one to properly represent a list-final
-                     * category-2 register.
-                     */
-                    lastReg = lastReg.withOffset(1);
-                }
-
-                sb.append(list.get(0).regString());
-                sb.append("..");
-                sb.append(lastReg.regString());
-            }
-        }
-
-        sb.append("}");
-
-        return sb.toString();
+  /**
+   * Helper method to combine an opcode and a second byte of data into
+   * the appropriate form for emitting into a code buffer.
+   *
+   * @param insn {@code non-null;} the instruction containing the opcode
+   * @param arg {@code 0..255;} arbitrary other byte value
+   * @return combined value
+   */
+  protected static short opcodeUnit(DalvInsn insn, int arg) {
+    if ((arg & 0xff) != arg) {
+      throw new IllegalArgumentException("arg out of range 0..255");
     }
 
-    /**
-     * Helper method to return a literal bits argument string.
-     *
-     * @param value the value
-     * @return {@code non-null;} the string form
-     */
-    protected static String literalBitsString(CstLiteralBits value) {
-        StringBuffer sb = new StringBuffer(100);
+    int opcode = insn.getOpcode().getOpcode();
 
-        sb.append('#');
-
-        if (value instanceof CstKnownNull) {
-            sb.append("null");
-        } else {
-            sb.append(value.typeName());
-            sb.append(' ');
-            sb.append(value.toHuman());
-        }
-
-        return sb.toString();
+    if ((opcode & 0xff) != opcode) {
+      throw new IllegalArgumentException("opcode out of range 0..255");
     }
 
-    /**
-     * Helper method to return a literal bits comment string.
-     *
-     * @param value the value
-     * @param width the width of the constant, in bits (used for displaying
-     * the uninterpreted bits; one of: {@code 4 8 16 32 64}
-     * @return {@code non-null;} the comment
-     */
-    protected static String literalBitsComment(CstLiteralBits value,
-            int width) {
-        StringBuffer sb = new StringBuffer(20);
+    return (short) (opcode | (arg << 8));
+  }
 
-        sb.append("#");
+  /**
+   * Helper method to get an extended (16-bit) opcode out of an
+   * instruction, returning it as a code unit. The opcode
+   * <i>must</i> be an extended opcode.
+   *
+   * @param insn {@code non-null;} the instruction containing the
+   * extended opcode
+   * @return the opcode as a code unit
+   */
+  protected static short opcodeUnit(DalvInsn insn) {
+    int opcode = insn.getOpcode().getOpcode();
 
-        long bits;
-
-        if (value instanceof CstLiteral64) {
-            bits = ((CstLiteral64) value).getLongBits();
-        } else {
-            bits = value.getIntBits();
-        }
-
-        switch (width) {
-            case 4:  sb.append(Hex.uNibble((int) bits)); break;
-            case 8:  sb.append(Hex.u1((int) bits));      break;
-            case 16: sb.append(Hex.u2((int) bits));      break;
-            case 32: sb.append(Hex.u4((int) bits));      break;
-            case 64: sb.append(Hex.u8(bits));            break;
-            default: {
-                throw new RuntimeException("shouldn't happen");
-            }
-        }
-
-        return sb.toString();
+    if ((opcode < 0x100) || (opcode > 0xffff)) {
+      throw new IllegalArgumentException("opcode out of range 0..65535");
     }
 
-    /**
-     * Helper method to return a branch address string.
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @return {@code non-null;} the string form of the instruction's
-     * branch target
-     */
-    protected static String branchString(DalvInsn insn) {
-        TargetInsn ti = (TargetInsn) insn;
-        int address = ti.getTargetAddress();
+    return (short) opcode;
+  }
 
-        return (address == (char) address) ? Hex.u2(address) : Hex.u4(address);
+  /**
+   * Helper method to combine two bytes into a code unit.
+   *
+   * @param low {@code 0..255;} low byte
+   * @param high {@code 0..255;} high byte
+   * @return combined value
+   */
+  protected static short codeUnit(int low, int high) {
+    if ((low & 0xff) != low) {
+      throw new IllegalArgumentException("low out of range 0..255");
     }
 
-    /**
-     * Helper method to return the comment for a branch.
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @return {@code non-null;} the comment
-     */
-    protected static String branchComment(DalvInsn insn) {
-        TargetInsn ti = (TargetInsn) insn;
-        int offset = ti.getTargetOffset();
-
-        return (offset == (short) offset) ? Hex.s2(offset) : Hex.s4(offset);
+    if ((high & 0xff) != high) {
+      throw new IllegalArgumentException("high out of range 0..255");
     }
 
-    /**
-     * Helper method to return the constant string for a {@link CstInsn}
-     * in human form.
-     *
-     * @param insn {@code non-null;} a constant-bearing instruction
-     * @return {@code non-null;} the human string form of the contained
-     * constant
-     */
-    protected static String cstString(DalvInsn insn) {
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+    return (short) (low | (high << 8));
+  }
 
-        return cst instanceof CstString ? ((CstString) cst).toQuoted() : cst.toHuman();
+  /**
+   * Helper method to combine four nibbles into a code unit.
+   *
+   * @param n0 {@code 0..15;} low nibble
+   * @param n1 {@code 0..15;} medium-low nibble
+   * @param n2 {@code 0..15;} medium-high nibble
+   * @param n3 {@code 0..15;} high nibble
+   * @return combined value
+   */
+  protected static short codeUnit(int n0, int n1, int n2, int n3) {
+    if ((n0 & 0xf) != n0) {
+      throw new IllegalArgumentException("n0 out of range 0..15");
     }
 
-    /**
-     * Helper method to return an instruction comment for a constant.
-     *
-     * @param insn {@code non-null;} a constant-bearing instruction
-     * @return {@code non-null;} comment string representing the constant
-     */
-    protected static String cstComment(DalvInsn insn) {
-        CstInsn ci = (CstInsn) insn;
-
-        if (! ci.hasIndex()) {
-            return "";
-        }
-
-        StringBuilder sb = new StringBuilder(20);
-        int index = ci.getIndex();
-
-        sb.append(ci.getConstant().typeName());
-        sb.append('@');
-
-        if (index < 65536) {
-            sb.append(Hex.u2(index));
-        } else {
-            sb.append(Hex.u4(index));
-        }
-
-        return sb.toString();
+    if ((n1 & 0xf) != n1) {
+      throw new IllegalArgumentException("n1 out of range 0..15");
     }
 
-    /**
-     * Helper method to determine if a signed int value fits in a nibble.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range -8..+7
-     */
-    protected static boolean signedFitsInNibble(int value) {
-        return (value >= -8) && (value <= 7);
+    if ((n2 & 0xf) != n2) {
+      throw new IllegalArgumentException("n2 out of range 0..15");
     }
 
-    /**
-     * Helper method to determine if an unsigned int value fits in a nibble.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range 0..0xf
-     */
-    protected static boolean unsignedFitsInNibble(int value) {
-        return value == (value & 0xf);
+    if ((n3 & 0xf) != n3) {
+      throw new IllegalArgumentException("n3 out of range 0..15");
     }
 
-    /**
-     * Helper method to determine if a signed int value fits in a byte.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range -0x80..+0x7f
-     */
-    protected static boolean signedFitsInByte(int value) {
-        return (byte) value == value;
+    return (short) (n0 | (n1 << 4) | (n2 << 8) | (n3 << 12));
+  }
+
+  /**
+   * Helper method to combine two nibbles into a byte.
+   *
+   * @param low {@code 0..15;} low nibble
+   * @param high {@code 0..15;} high nibble
+   * @return {@code 0..255;} combined value
+   */
+  protected static int makeByte(int low, int high) {
+    if ((low & 0xf) != low) {
+      throw new IllegalArgumentException("low out of range 0..15");
     }
 
-    /**
-     * Helper method to determine if an unsigned int value fits in a byte.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range 0..0xff
-     */
-    protected static boolean unsignedFitsInByte(int value) {
-        return value == (value & 0xff);
+    if ((high & 0xf) != high) {
+      throw new IllegalArgumentException("high out of range 0..15");
     }
 
-    /**
-     * Helper method to determine if a signed int value fits in a short.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range -0x8000..+0x7fff
-     */
-    protected static boolean signedFitsInShort(int value) {
-        return (short) value == value;
-    }
+    return low | (high << 4);
+  }
 
-    /**
-     * Helper method to determine if an unsigned int value fits in a short.
-     *
-     * @param value the value in question
-     * @return {@code true} iff it's in the range 0..0xffff
-     */
-    protected static boolean unsignedFitsInShort(int value) {
-        return value == (value & 0xffff);
-    }
+  /**
+   * Writes one code unit to the given output destination.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0) {
+    out.writeShort(c0);
+  }
 
-    /**
-     * Helper method to determine if a list of registers are sequential,
-     * including degenerate cases for empty or single-element lists.
-     *
-     * @param list {@code non-null;} the list of registers
-     * @return {@code true} iff the list is sequentially ordered
-     */
-    protected static boolean isRegListSequential(RegisterSpecList list) {
-        int sz = list.size();
+  /**
+   * Writes two code units to the given output destination.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, short c1) {
+    out.writeShort(c0);
+    out.writeShort(c1);
+  }
 
-        if (sz < 2) {
-            return true;
-        }
+  /**
+   * Writes three code units to the given output destination.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1 code unit to write
+   * @param c2 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, short c1, short c2) {
+    out.writeShort(c0);
+    out.writeShort(c1);
+    out.writeShort(c2);
+  }
 
-        int first = list.get(0).getReg();
-        int next = first;
+  /**
+   * Writes four code units to the given output destination.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1 code unit to write
+   * @param c2 code unit to write
+   * @param c3 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, short c1, short c2, short c3) {
+    out.writeShort(c0);
+    out.writeShort(c1);
+    out.writeShort(c2);
+    out.writeShort(c3);
+  }
 
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec one = list.get(i);
-            if (one.getReg() != next) {
-                return false;
-            }
-            next += one.getCategory();
-        }
+  /**
+   * Writes five code units to the given output destination.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1 code unit to write
+   * @param c2 code unit to write
+   * @param c3 code unit to write
+   * @param c4 code unit to write
+   */
+  protected static void write(AnnotatedOutput out,
+      short c0,
+      short c1,
+      short c2,
+      short c3,
+      short c4) {
+    out.writeShort(c0);
+    out.writeShort(c1);
+    out.writeShort(c2);
+    out.writeShort(c3);
+    out.writeShort(c4);
+  }
 
-        return true;
-    }
+  /**
+   * Writes three code units to the given output destination, where the
+   * second and third are represented as single <code>int</code> and emitted
+   * in little-endian order.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1c2 code unit pair to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, int c1c2) {
+    write(out, c0, (short) c1c2, (short) (c1c2 >> 16));
+  }
 
-    /**
-     * Helper method to extract the callout-argument index from an
-     * appropriate instruction.
-     *
-     * @param insn {@code non-null;} the instruction
-     * @return {@code >= 0;} the callout argument index
-     */
-    protected static int argIndex(DalvInsn insn) {
-        int arg = ((CstInteger) ((CstInsn) insn).getConstant()).getValue();
+  /**
+   * Writes four code units to the given output destination, where the
+   * second and third are represented as single <code>int</code> and emitted
+   * in little-endian order.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1c2 code unit pair to write
+   * @param c3 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, int c1c2, short c3) {
+    write(out, c0, (short) c1c2, (short) (c1c2 >> 16), c3);
+  }
 
-        if (arg < 0) {
-            throw new IllegalArgumentException("bogus insn");
-        }
+  /**
+   * Writes five code units to the given output destination, where the
+   * second and third are represented as single <code>int</code> and emitted
+   * in little-endian order.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1c2 code unit pair to write
+   * @param c3 code unit to write
+   * @param c4 code unit to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, int c1c2, short c3, short c4) {
+    write(out, c0, (short) c1c2, (short) (c1c2 >> 16), c3, c4);
+  }
 
-        return arg;
-    }
-
-    /**
-     * Helper method to combine an opcode and a second byte of data into
-     * the appropriate form for emitting into a code buffer.
-     *
-     * @param insn {@code non-null;} the instruction containing the opcode
-     * @param arg {@code 0..255;} arbitrary other byte value
-     * @return combined value
-     */
-    protected static short opcodeUnit(DalvInsn insn, int arg) {
-        if ((arg & 0xff) != arg) {
-            throw new IllegalArgumentException("arg out of range 0..255");
-        }
-
-        int opcode = insn.getOpcode().getOpcode();
-
-        if ((opcode & 0xff) != opcode) {
-            throw new IllegalArgumentException("opcode out of range 0..255");
-        }
-
-        return (short) (opcode | (arg << 8));
-    }
-
-    /**
-     * Helper method to get an extended (16-bit) opcode out of an
-     * instruction, returning it as a code unit. The opcode
-     * <i>must</i> be an extended opcode.
-     *
-     * @param insn {@code non-null;} the instruction containing the
-     * extended opcode
-     * @return the opcode as a code unit
-     */
-    protected static short opcodeUnit(DalvInsn insn) {
-        int opcode = insn.getOpcode().getOpcode();
-
-        if ((opcode < 0x100) || (opcode > 0xffff)) {
-            throw new IllegalArgumentException("opcode out of range 0..65535");
-        }
-
-        return (short) opcode;
-    }
-
-    /**
-     * Helper method to combine two bytes into a code unit.
-     *
-     * @param low {@code 0..255;} low byte
-     * @param high {@code 0..255;} high byte
-     * @return combined value
-     */
-    protected static short codeUnit(int low, int high) {
-        if ((low & 0xff) != low) {
-            throw new IllegalArgumentException("low out of range 0..255");
-        }
-
-        if ((high & 0xff) != high) {
-            throw new IllegalArgumentException("high out of range 0..255");
-        }
-
-        return (short) (low | (high << 8));
-    }
-
-    /**
-     * Helper method to combine four nibbles into a code unit.
-     *
-     * @param n0 {@code 0..15;} low nibble
-     * @param n1 {@code 0..15;} medium-low nibble
-     * @param n2 {@code 0..15;} medium-high nibble
-     * @param n3 {@code 0..15;} high nibble
-     * @return combined value
-     */
-    protected static short codeUnit(int n0, int n1, int n2, int n3) {
-        if ((n0 & 0xf) != n0) {
-            throw new IllegalArgumentException("n0 out of range 0..15");
-        }
-
-        if ((n1 & 0xf) != n1) {
-            throw new IllegalArgumentException("n1 out of range 0..15");
-        }
-
-        if ((n2 & 0xf) != n2) {
-            throw new IllegalArgumentException("n2 out of range 0..15");
-        }
-
-        if ((n3 & 0xf) != n3) {
-            throw new IllegalArgumentException("n3 out of range 0..15");
-        }
-
-        return (short) (n0 | (n1 << 4) | (n2 << 8) | (n3 << 12));
-    }
-
-    /**
-     * Helper method to combine two nibbles into a byte.
-     *
-     * @param low {@code 0..15;} low nibble
-     * @param high {@code 0..15;} high nibble
-     * @return {@code 0..255;} combined value
-     */
-    protected static int makeByte(int low, int high) {
-        if ((low & 0xf) != low) {
-            throw new IllegalArgumentException("low out of range 0..15");
-        }
-
-        if ((high & 0xf) != high) {
-            throw new IllegalArgumentException("high out of range 0..15");
-        }
-
-        return low | (high << 4);
-    }
-
-    /**
-     * Writes one code unit to the given output destination.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0) {
-        out.writeShort(c0);
-    }
-
-    /**
-     * Writes two code units to the given output destination.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, short c1) {
-        out.writeShort(c0);
-        out.writeShort(c1);
-    }
-
-    /**
-     * Writes three code units to the given output destination.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1 code unit to write
-     * @param c2 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, short c1,
-            short c2) {
-        out.writeShort(c0);
-        out.writeShort(c1);
-        out.writeShort(c2);
-    }
-
-    /**
-     * Writes four code units to the given output destination.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1 code unit to write
-     * @param c2 code unit to write
-     * @param c3 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, short c1,
-            short c2, short c3) {
-        out.writeShort(c0);
-        out.writeShort(c1);
-        out.writeShort(c2);
-        out.writeShort(c3);
-    }
-
-    /**
-     * Writes five code units to the given output destination.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1 code unit to write
-     * @param c2 code unit to write
-     * @param c3 code unit to write
-     * @param c4 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, short c1,
-            short c2, short c3, short c4) {
-        out.writeShort(c0);
-        out.writeShort(c1);
-        out.writeShort(c2);
-        out.writeShort(c3);
-        out.writeShort(c4);
-    }
-
-    /**
-     * Writes three code units to the given output destination, where the
-     * second and third are represented as single <code>int</code> and emitted
-     * in little-endian order.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1c2 code unit pair to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, int c1c2) {
-        write(out, c0, (short) c1c2, (short) (c1c2 >> 16));
-    }
-
-    /**
-     * Writes four code units to the given output destination, where the
-     * second and third are represented as single <code>int</code> and emitted
-     * in little-endian order.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1c2 code unit pair to write
-     * @param c3 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, int c1c2,
-            short c3) {
-        write(out, c0, (short) c1c2, (short) (c1c2 >> 16), c3);
-    }
-
-    /**
-     * Writes five code units to the given output destination, where the
-     * second and third are represented as single <code>int</code> and emitted
-     * in little-endian order.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1c2 code unit pair to write
-     * @param c3 code unit to write
-     * @param c4 code unit to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, int c1c2,
-            short c3, short c4) {
-        write(out, c0, (short) c1c2, (short) (c1c2 >> 16), c3, c4);
-    }
-
-    /**
-     * Writes five code units to the given output destination, where the
-     * second through fifth are represented as single <code>long</code>
-     * and emitted in little-endian order.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param c0 code unit to write
-     * @param c1c2c3c4 code unit quad to write
-     */
-    protected static void write(AnnotatedOutput out, short c0, long c1c2c3c4) {
-        write(out, c0, (short) c1c2c3c4, (short) (c1c2c3c4 >> 16),
-                (short) (c1c2c3c4 >> 32), (short) (c1c2c3c4 >> 48));
-    }
+  /**
+   * Writes five code units to the given output destination, where the
+   * second through fifth are represented as single <code>long</code>
+   * and emitted in little-endian order.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param c0 code unit to write
+   * @param c1c2c3c4 code unit quad to write
+   */
+  protected static void write(AnnotatedOutput out, short c0, long c1c2c3c4) {
+    write(out,
+        c0,
+        (short) c1c2c3c4,
+        (short) (c1c2c3c4 >> 16),
+        (short) (c1c2c3c4 >> 32),
+        (short) (c1c2c3c4 >> 48));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/LocalEnd.java b/dx/src/com/android/jack/dx/dex/code/LocalEnd.java
index a72044a..897ef7c 100644
--- a/dx/src/com/android/jack/dx/dex/code/LocalEnd.java
+++ b/dx/src/com/android/jack/dx/dex/code/LocalEnd.java
@@ -27,64 +27,64 @@
  * subsequent instruction, the indicated variable is no longer valid.
  */
 public final class LocalEnd extends ZeroSizeInsn {
-    /**
-     * {@code non-null;} register spec representing the local variable ended
-     * by this instance. <b>Note:</b> Technically, only the register
-     * number needs to be recorded here as the rest of the information
-     * is implicit in the ambient local variable state, but other code
-     * will check the other info for consistency.
-     */
-    private final RegisterSpec local;
+  /**
+   * {@code non-null;} register spec representing the local variable ended
+   * by this instance. <b>Note:</b> Technically, only the register
+   * number needs to be recorded here as the rest of the information
+   * is implicit in the ambient local variable state, but other code
+   * will check the other info for consistency.
+   */
+  private final RegisterSpec local;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param local {@code non-null;} register spec representing the local
-     * variable introduced by this instance
-     */
-    public LocalEnd(SourcePosition position, RegisterSpec local) {
-        super(position);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param local {@code non-null;} register spec representing the local
+   * variable introduced by this instance
+   */
+  public LocalEnd(SourcePosition position, RegisterSpec local) {
+    super(position);
 
-        if (local == null) {
-            throw new NullPointerException("local == null");
-        }
-
-        this.local = local;
+    if (local == null) {
+      throw new NullPointerException("local == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisterOffset(int delta) {
-        return new LocalEnd(getPosition(), local.withOffset(delta));
-    }
+    this.local = local;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new LocalEnd(getPosition(), local);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisterOffset(int delta) {
+    return new LocalEnd(getPosition(), local.withOffset(delta));
+  }
 
-    /**
-     * Gets the register spec representing the local variable ended
-     * by this instance.
-     *
-     * @return {@code non-null;} the register spec
-     */
-    public RegisterSpec getLocal() {
-        return local;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new LocalEnd(getPosition(), local);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return local.toString();
-    }
+  /**
+   * Gets the register spec representing the local variable ended
+   * by this instance.
+   *
+   * @return {@code non-null;} the register spec
+   */
+  public RegisterSpec getLocal() {
+    return local;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        return "local-end " + LocalStart.localString(local);
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return local.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    return "local-end " + LocalStart.localString(local);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/LocalList.java b/dx/src/com/android/jack/dx/dex/code/LocalList.java
index 0a07a60..8f1c713 100644
--- a/dx/src/com/android/jack/dx/dex/code/LocalList.java
+++ b/dx/src/com/android/jack/dx/dex/code/LocalList.java
@@ -33,916 +33,895 @@
  * and a type.
  */
 public final class LocalList extends FixedSizeList {
-    /** {@code non-null;} empty instance */
-    public static final LocalList EMPTY = new LocalList(0);
+  /** {@code non-null;} empty instance */
+  public static final LocalList EMPTY = new LocalList(0);
 
-    /** whether to run the self-check code */
-    private static final boolean DEBUG = false;
+  /** whether to run the self-check code */
+  private static final boolean DEBUG = false;
+
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size {@code >= 0;} the size of the list
+   */
+  public LocalList(int size) {
+    super(size);
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Entry get(int n) {
+    return (Entry) get0(n);
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param entry {@code non-null;} the entry to set at {@code n}
+   */
+  public void set(int n, Entry entry) {
+    set0(n, entry);
+  }
+
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} prefix to attach to each line of output
+   */
+  public void debugPrint(PrintStream out, String prefix) {
+    int sz = size();
+
+    for (int i = 0; i < sz; i++) {
+      out.print(prefix);
+      out.println(get(i));
+    }
+  }
+
+  /**
+   * Disposition of a local entry.
+   */
+  public static enum Disposition {
+    /** local started (introduced) */
+    START,
+
+    /** local ended without being replaced */
+    END_SIMPLY,
+
+    /** local ended because it was directly replaced */
+    END_REPLACED,
+
+    /** local ended because it was moved to a different register */
+    END_MOVED,
 
     /**
-     * Constructs an instance. All indices initially contain {@code null}.
+     * local ended because the previous local clobbered this one
+     * (because it is category-2)
+     */
+    END_CLOBBERED_BY_PREV,
+
+    /**
+     * local ended because the next local clobbered this one
+     * (because this one is a category-2)
+     */
+    END_CLOBBERED_BY_NEXT;
+  }
+
+  /**
+   * Entry in a local list.
+   */
+  public static class Entry implements Comparable<Entry> {
+    /** {@code >= 0;} address */
+    private final int address;
+
+    /** {@code non-null;} disposition of the local */
+    private final Disposition disposition;
+
+    /** {@code non-null;} register spec representing the variable */
+    private final RegisterSpec spec;
+
+    /** {@code non-null;} variable type (derived from {@code spec}) */
+    private final CstType type;
+
+    /**
+     * Constructs an instance.
      *
-     * @param size {@code >= 0;} the size of the list
+     * @param address {@code >= 0;} address
+     * @param disposition {@code non-null;} disposition of the local
+     * @param spec {@code non-null;} register spec representing
+     * the variable
      */
-    public LocalList(int size) {
-        super(size);
+    public Entry(int address, Disposition disposition, RegisterSpec spec) {
+      if (address < 0) {
+        throw new IllegalArgumentException("address < 0");
+      }
+
+      if (disposition == null) {
+        throw new NullPointerException("disposition == null");
+      }
+
+      try {
+        if (spec.getLocalItem() == null) {
+          throw new NullPointerException("spec.getLocalItem() == null");
+        }
+      } catch (NullPointerException ex) {
+        // Elucidate the exception.
+        throw new NullPointerException("spec == null");
+      }
+
+      this.address = address;
+      this.disposition = disposition;
+      this.spec = spec;
+      this.type = spec.getLocalItem().getType();
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public String toString() {
+      return Integer.toHexString(address) + " " + disposition + " " + spec;
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public boolean equals(Object other) {
+      if (!(other instanceof Entry)) {
+        return false;
+      }
+
+      return (compareTo((Entry) other) == 0);
     }
 
     /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
+     * Compares by (in priority order) address, end then start
+     * disposition (variants of end are all consistered
+     * equivalent), and spec.
      *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
+     * @param other {@code non-null;} entry to compare to
+     * @return {@code -1..1;} standard result of comparison
      */
-    public Entry get(int n) {
-        return (Entry) get0(n);
+    @Override
+    public int compareTo(Entry other) {
+      if (address < other.address) {
+        return -1;
+      } else if (address > other.address) {
+        return 1;
+      }
+
+      boolean thisIsStart = isStart();
+      boolean otherIsStart = other.isStart();
+
+      if (thisIsStart != otherIsStart) {
+        return thisIsStart ? 1 : -1;
+      }
+
+      return spec.compareTo(other.spec);
     }
 
     /**
-     * Sets the entry at the given index.
+     * Gets the address.
      *
-     * @param n {@code >= 0, < size();} which index
-     * @param entry {@code non-null;} the entry to set at {@code n}
+     * @return {@code >= 0;} the address
      */
-    public void set(int n, Entry entry) {
-        set0(n, entry);
+    public int getAddress() {
+      return address;
     }
 
     /**
-     * Does a human-friendly dump of this instance.
+     * Gets the disposition.
      *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} prefix to attach to each line of output
+     * @return {@code non-null;} the disposition
      */
-    public void debugPrint(PrintStream out, String prefix) {
-        int sz = size();
-
-        for (int i = 0; i < sz; i++) {
-            out.print(prefix);
-            out.println(get(i));
-        }
+    public Disposition getDisposition() {
+      return disposition;
     }
 
     /**
-     * Disposition of a local entry.
-     */
-    public static enum Disposition {
-        /** local started (introduced) */
-        START,
-
-        /** local ended without being replaced */
-        END_SIMPLY,
-
-        /** local ended because it was directly replaced */
-        END_REPLACED,
-
-        /** local ended because it was moved to a different register */
-        END_MOVED,
-
-        /**
-         * local ended because the previous local clobbered this one
-         * (because it is category-2)
-         */
-        END_CLOBBERED_BY_PREV,
-
-        /**
-         * local ended because the next local clobbered this one
-         * (because this one is a category-2)
-         */
-        END_CLOBBERED_BY_NEXT;
-    }
-
-    /**
-     * Entry in a local list.
-     */
-    public static class Entry implements Comparable<Entry> {
-        /** {@code >= 0;} address */
-        private final int address;
-
-        /** {@code non-null;} disposition of the local */
-        private final Disposition disposition;
-
-        /** {@code non-null;} register spec representing the variable */
-        private final RegisterSpec spec;
-
-        /** {@code non-null;} variable type (derived from {@code spec}) */
-        private final CstType type;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param address {@code >= 0;} address
-         * @param disposition {@code non-null;} disposition of the local
-         * @param spec {@code non-null;} register spec representing
-         * the variable
-         */
-        public Entry(int address, Disposition disposition, RegisterSpec spec) {
-            if (address < 0) {
-                throw new IllegalArgumentException("address < 0");
-            }
-
-            if (disposition == null) {
-                throw new NullPointerException("disposition == null");
-            }
-
-            try {
-                if (spec.getLocalItem() == null) {
-                    throw new NullPointerException(
-                            "spec.getLocalItem() == null");
-                }
-            } catch (NullPointerException ex) {
-                // Elucidate the exception.
-                throw new NullPointerException("spec == null");
-            }
-
-            this.address = address;
-            this.disposition = disposition;
-            this.spec = spec;
-            this.type = spec.getLocalItem().getType();
-        }
-
-        /** {@inheritDoc} */
-        public String toString() {
-            return Integer.toHexString(address) + " " + disposition + " " +
-                spec;
-        }
-
-        /** {@inheritDoc} */
-        public boolean equals(Object other) {
-            if (!(other instanceof Entry)) {
-                return false;
-            }
-
-            return (compareTo((Entry) other) == 0);
-        }
-
-        /**
-         * Compares by (in priority order) address, end then start
-         * disposition (variants of end are all consistered
-         * equivalent), and spec.
-         *
-         * @param other {@code non-null;} entry to compare to
-         * @return {@code -1..1;} standard result of comparison
-         */
-        public int compareTo(Entry other) {
-            if (address < other.address) {
-                return -1;
-            } else if (address > other.address) {
-                return 1;
-            }
-
-            boolean thisIsStart = isStart();
-            boolean otherIsStart = other.isStart();
-
-            if (thisIsStart != otherIsStart) {
-                return thisIsStart ? 1 : -1;
-            }
-
-            return spec.compareTo(other.spec);
-        }
-
-        /**
-         * Gets the address.
-         *
-         * @return {@code >= 0;} the address
-         */
-        public int getAddress() {
-            return address;
-        }
-
-        /**
-         * Gets the disposition.
-         *
-         * @return {@code non-null;} the disposition
-         */
-        public Disposition getDisposition() {
-            return disposition;
-        }
-
-        /**
-         * Gets whether this is a local start. This is just shorthand for
-         * {@code getDisposition() == Disposition.START}.
-         *
-         * @return {@code true} iff this is a start
-         */
-        public boolean isStart() {
-            return disposition == Disposition.START;
-        }
-
-        /**
-         * Gets the variable name.
-         *
-         * @return {@code null-ok;} the variable name
-         */
-        public CstString getName() {
-            return spec.getLocalItem().getName();
-        }
-
-        /**
-         * Gets the variable signature.
-         *
-         * @return {@code null-ok;} the variable signature
-         */
-        public CstString getSignature() {
-            return spec.getLocalItem().getSignature();
-        }
-
-        /**
-         * Gets the variable's type.
-         *
-         * @return {@code non-null;} the type
-         */
-        public CstType getType() {
-            return type;
-        }
-
-        /**
-         * Gets the number of the register holding the variable.
-         *
-         * @return {@code >= 0;} the number of the register holding
-         * the variable
-         */
-        public int getRegister() {
-            return spec.getReg();
-        }
-
-        /**
-         * Gets the RegisterSpec of the register holding the variable.
-         *
-         * @return {@code non-null;} RegisterSpec of the holding register.
-         */
-        public RegisterSpec getRegisterSpec() {
-            return spec;
-        }
-
-        /**
-         * Returns whether or not this instance matches the given spec.
-         *
-         * @param otherSpec {@code non-null;} the spec in question
-         * @return {@code true} iff this instance matches
-         * {@code spec}
-         */
-        public boolean matches(RegisterSpec otherSpec) {
-            return spec.equalsUsingSimpleType(otherSpec);
-        }
-
-        /**
-         * Returns whether or not this instance matches the spec in
-         * the given instance.
-         *
-         * @param other {@code non-null;} another entry
-         * @return {@code true} iff this instance's spec matches
-         * {@code other}
-         */
-        public boolean matches(Entry other) {
-            return matches(other.spec);
-        }
-
-        /**
-         * Returns an instance just like this one but with the disposition
-         * set as given.
-         *
-         * @param disposition {@code non-null;} the new disposition
-         * @return {@code non-null;} an appropriately-constructed instance
-         */
-        public Entry withDisposition(Disposition disposition) {
-            if (disposition == this.disposition) {
-                return this;
-            }
-
-            return new Entry(address, disposition, spec);
-        }
-    }
-
-    /**
-     * Constructs an instance for the given method, based on the given
-     * block order and intermediate local information.
+     * Gets whether this is a local start. This is just shorthand for
+     * {@code getDisposition() == Disposition.START}.
      *
-     * @param insns {@code non-null;} instructions to convert
-     * @return {@code non-null;} the constructed list
+     * @return {@code true} iff this is a start
      */
-    public static LocalList make(DalvInsnList insns) {
-        int sz = insns.size();
+    public boolean isStart() {
+      return disposition == Disposition.START;
+    }
 
+    /**
+     * Gets the variable name.
+     *
+     * @return {@code null-ok;} the variable name
+     */
+    public CstString getName() {
+      return spec.getLocalItem().getName();
+    }
+
+    /**
+     * Gets the variable signature.
+     *
+     * @return {@code null-ok;} the variable signature
+     */
+    public CstString getSignature() {
+      return spec.getLocalItem().getSignature();
+    }
+
+    /**
+     * Gets the variable's type.
+     *
+     * @return {@code non-null;} the type
+     */
+    public CstType getType() {
+      return type;
+    }
+
+    /**
+     * Gets the number of the register holding the variable.
+     *
+     * @return {@code >= 0;} the number of the register holding
+     * the variable
+     */
+    public int getRegister() {
+      return spec.getReg();
+    }
+
+    /**
+     * Gets the RegisterSpec of the register holding the variable.
+     *
+     * @return {@code non-null;} RegisterSpec of the holding register.
+     */
+    public RegisterSpec getRegisterSpec() {
+      return spec;
+    }
+
+    /**
+     * Returns whether or not this instance matches the given spec.
+     *
+     * @param otherSpec {@code non-null;} the spec in question
+     * @return {@code true} iff this instance matches
+     * {@code spec}
+     */
+    public boolean matches(RegisterSpec otherSpec) {
+      return spec.equalsUsingSimpleType(otherSpec);
+    }
+
+    /**
+     * Returns whether or not this instance matches the spec in
+     * the given instance.
+     *
+     * @param other {@code non-null;} another entry
+     * @return {@code true} iff this instance's spec matches
+     * {@code other}
+     */
+    public boolean matches(Entry other) {
+      return matches(other.spec);
+    }
+
+    /**
+     * Returns an instance just like this one but with the disposition
+     * set as given.
+     *
+     * @param disposition {@code non-null;} the new disposition
+     * @return {@code non-null;} an appropriately-constructed instance
+     */
+    public Entry withDisposition(Disposition disposition) {
+      if (disposition == this.disposition) {
+        return this;
+      }
+
+      return new Entry(address, disposition, spec);
+    }
+  }
+
+  /**
+   * Constructs an instance for the given method, based on the given
+   * block order and intermediate local information.
+   *
+   * @param insns {@code non-null;} instructions to convert
+   * @return {@code non-null;} the constructed list
+   */
+  public static LocalList make(DalvInsnList insns) {
+    int sz = insns.size();
+
+    /*
+     * Go through the insn list, looking for all the local
+     * variable pseudoinstructions, splitting out LocalSnapshots
+     * into separate per-variable starts, adding explicit ends
+     * wherever a variable is replaced or moved, and collecting
+     * these and all the other local variable "activity"
+     * together into an output list (without the other insns).
+     *
+     * Note: As of this writing, this method won't be handed any
+     * insn lists that contain local ends, but I (danfuzz) expect
+     * that to change at some point, when we start feeding that
+     * info explicitly into the rop layer rather than only trying
+     * to infer it. So, given that expectation, this code is
+     * written to deal with them.
+     */
+
+MakeState state = new MakeState(sz);
+
+    for (int i = 0; i < sz; i++) {
+      DalvInsn insn = insns.get(i);
+
+      if (insn instanceof LocalSnapshot) {
+        RegisterSpecSet snapshot = ((LocalSnapshot) insn).getLocals();
+        state.snapshot(insn.getAddress(), snapshot);
+      } else if (insn instanceof LocalStart) {
+        RegisterSpec local = ((LocalStart) insn).getLocal();
+        state.startLocal(insn.getAddress(), local);
+      } else if (insn instanceof LocalEnd) {
+        RegisterSpec local = ((LocalEnd) insn).getLocal();
+        state.endLocal(insn.getAddress(), local);
+      }
+    }
+
+    LocalList result = state.finish();
+
+    if (DEBUG) {
+      debugVerify(result);
+    }
+
+    return result;
+  }
+
+  /**
+   * Debugging helper that verifies the constraint that a list doesn't
+   * contain any redundant local starts and that local ends that are
+   * due to replacements are properly annotated.
+   */
+  private static void debugVerify(LocalList locals) {
+    try {
+      debugVerify0(locals);
+    } catch (RuntimeException ex) {
+      int sz = locals.size();
+      for (int i = 0; i < sz; i++) {
+        System.err.println(locals.get(i));
+      }
+      throw ex;
+    }
+
+  }
+
+  /**
+   * Helper for {@link #debugVerify} which does most of the work.
+   */
+  private static void debugVerify0(LocalList locals) {
+    int sz = locals.size();
+    Entry[] active = new Entry[65536];
+
+    for (int i = 0; i < sz; i++) {
+      Entry e = locals.get(i);
+      int reg = e.getRegister();
+
+      if (e.isStart()) {
+        Entry already = active[reg];
+
+        if ((already != null) && e.matches(already)) {
+          throw new RuntimeException("redundant start at " + Integer.toHexString(e.getAddress())
+              + ": got " + e + "; had " + already);
+        }
+
+        active[reg] = e;
+      } else {
+        if (active[reg] == null) {
+          throw new RuntimeException("redundant end at " + Integer.toHexString(e.getAddress()));
+        }
+
+        int addr = e.getAddress();
+        boolean foundStart = false;
+
+        for (int j = i + 1; j < sz; j++) {
+          Entry test = locals.get(j);
+          if (test.getAddress() != addr) {
+            break;
+          }
+          if (test.getRegisterSpec().getReg() == reg) {
+            if (test.isStart()) {
+              if (e.getDisposition() != Disposition.END_REPLACED) {
+                throw new RuntimeException("improperly marked end at " + Integer.toHexString(addr));
+              }
+              foundStart = true;
+            } else {
+              throw new RuntimeException("redundant end at " + Integer.toHexString(addr));
+            }
+          }
+        }
+
+        if (!foundStart && (e.getDisposition() == Disposition.END_REPLACED)) {
+          throw new RuntimeException(
+              "improper end replacement claim at " + Integer.toHexString(addr));
+        }
+
+        active[reg] = null;
+      }
+    }
+  }
+
+  /**
+   * Intermediate state when constructing a local list.
+   */
+  public static class MakeState {
+    /** {@code non-null;} result being collected */
+    private final ArrayList<Entry> result;
+
+    /**
+     * {@code >= 0;} running count of nulled result entries, to help with
+     * sizing the final list
+     */
+    private int nullResultCount;
+
+    /** {@code null-ok;} current register mappings */
+    private RegisterSpecSet regs;
+
+    /** {@code null-ok;} result indices where local ends are stored */
+    private int[] endIndices;
+
+    /** {@code >= 0;} last address seen */
+    private int lastAddress;
+
+    /**
+     * Constructs an instance.
+     */
+    public MakeState(int initialSize) {
+      result = new ArrayList<Entry>(initialSize);
+      nullResultCount = 0;
+      regs = null;
+      endIndices = null;
+      lastAddress = 0;
+    }
+
+    /**
+     * Checks the address and other vitals as a prerequisite to
+     * further processing.
+     *
+     * @param address {@code >= 0;} address about to be processed
+     * @param reg {@code >= 0;} register number about to be processed
+     */
+    private void aboutToProcess(int address, int reg) {
+      boolean first = (endIndices == null);
+
+      if ((address == lastAddress) && !first) {
+        return;
+      }
+
+      if (address < lastAddress) {
+        throw new RuntimeException("shouldn't happen");
+      }
+
+      if (first || (reg >= endIndices.length)) {
         /*
-         * Go through the insn list, looking for all the local
-         * variable pseudoinstructions, splitting out LocalSnapshots
-         * into separate per-variable starts, adding explicit ends
-         * wherever a variable is replaced or moved, and collecting
-         * these and all the other local variable "activity"
-         * together into an output list (without the other insns).
-         *
-         * Note: As of this writing, this method won't be handed any
-         * insn lists that contain local ends, but I (danfuzz) expect
-         * that to change at some point, when we start feeding that
-         * info explicitly into the rop layer rather than only trying
-         * to infer it. So, given that expectation, this code is
-         * written to deal with them.
+         * This is the first allocation of the state set and
+         * index array, or we need to grow. (The latter doesn't
+         * happen much; in fact, we have only ever observed
+         * it happening in test cases, never in "real" code.)
          */
+        int newSz = reg + 1;
+        RegisterSpecSet newRegs = new RegisterSpecSet(newSz);
+        int[] newEnds = new int[newSz];
+        Arrays.fill(newEnds, -1);
 
-        MakeState state = new MakeState(sz);
-
-        for (int i = 0; i < sz; i++) {
-            DalvInsn insn = insns.get(i);
-
-            if (insn instanceof LocalSnapshot) {
-                RegisterSpecSet snapshot =
-                    ((LocalSnapshot) insn).getLocals();
-                state.snapshot(insn.getAddress(), snapshot);
-            } else if (insn instanceof LocalStart) {
-                RegisterSpec local = ((LocalStart) insn).getLocal();
-                state.startLocal(insn.getAddress(), local);
-            } else if (insn instanceof LocalEnd) {
-                RegisterSpec local = ((LocalEnd) insn).getLocal();
-                state.endLocal(insn.getAddress(), local);
-            }
+        if (!first) {
+          newRegs.putAll(regs);
+          System.arraycopy(endIndices, 0, newEnds, 0, endIndices.length);
         }
 
-        LocalList result = state.finish();
-
-        if (DEBUG) {
-            debugVerify(result);
-        }
-
-        return result;
+        regs = newRegs;
+        endIndices = newEnds;
+      }
     }
 
     /**
-     * Debugging helper that verifies the constraint that a list doesn't
-     * contain any redundant local starts and that local ends that are
-     * due to replacements are properly annotated.
+     * Sets the local state at the given address to the given snapshot.
+     * The first call on this instance must be to this method, so that
+     * the register state can be properly sized.
+     *
+     * @param address {@code >= 0;} the address
+     * @param specs {@code non-null;} spec set representing the locals
      */
-    private static void debugVerify(LocalList locals) {
-        try {
-            debugVerify0(locals);
-        } catch (RuntimeException ex) {
-            int sz = locals.size();
-            for (int i = 0; i < sz; i++) {
-                System.err.println(locals.get(i));
-            }
-            throw ex;
-        }
+    public void snapshot(int address, RegisterSpecSet specs) {
+      if (DEBUG) {
+        System.err.printf("%04x snapshot %s\n", address, specs);
+      }
 
+      int sz = specs.getMaxSize();
+      aboutToProcess(address, sz - 1);
+
+      for (int i = 0; i < sz; i++) {
+        RegisterSpec oldSpec = regs.get(i);
+        RegisterSpec newSpec = filterSpec(specs.get(i));
+
+        if (oldSpec == null) {
+          if (newSpec != null) {
+            startLocal(address, newSpec);
+          }
+        } else if (newSpec == null) {
+          endLocal(address, oldSpec);
+        } else if (!newSpec.equalsUsingSimpleType(oldSpec)) {
+          endLocal(address, oldSpec);
+          startLocal(address, newSpec);
+        }
+      }
+
+      if (DEBUG) {
+        System.err.printf("%04x snapshot done\n", address);
+      }
     }
 
     /**
-     * Helper for {@link #debugVerify} which does most of the work.
+     * Starts a local at the given address.
+     *
+     * @param address {@code >= 0;} the address
+     * @param startedLocal {@code non-null;} spec representing the
+     * started local
      */
-    private static void debugVerify0(LocalList locals) {
-        int sz = locals.size();
-        Entry[] active = new Entry[65536];
+    public void startLocal(int address, RegisterSpec startedLocal) {
+      if (DEBUG) {
+        System.err.printf("%04x start %s\n", address, startedLocal);
+      }
 
-        for (int i = 0; i < sz; i++) {
-            Entry e = locals.get(i);
-            int reg = e.getRegister();
+      int regNum = startedLocal.getReg();
 
-            if (e.isStart()) {
-                Entry already = active[reg];
+      startedLocal = filterSpec(startedLocal);
+      aboutToProcess(address, regNum);
 
-                if ((already != null) && e.matches(already)) {
-                    throw new RuntimeException("redundant start at " +
-                            Integer.toHexString(e.getAddress()) + ": got " +
-                            e + "; had " + already);
-                }
+      RegisterSpec existingLocal = regs.get(regNum);
 
-                active[reg] = e;
-            } else {
-                if (active[reg] == null) {
-                    throw new RuntimeException("redundant end at " +
-                            Integer.toHexString(e.getAddress()));
-                }
+      if (startedLocal.equalsUsingSimpleType(existingLocal)) {
+        // Silently ignore a redundant start.
+        return;
+      }
 
-                int addr = e.getAddress();
-                boolean foundStart = false;
-
-                for (int j = i + 1; j < sz; j++) {
-                    Entry test = locals.get(j);
-                    if (test.getAddress() != addr) {
-                        break;
-                    }
-                    if (test.getRegisterSpec().getReg() == reg) {
-                        if (test.isStart()) {
-                            if (e.getDisposition()
-                                    != Disposition.END_REPLACED) {
-                                throw new RuntimeException(
-                                        "improperly marked end at " +
-                                        Integer.toHexString(addr));
-                            }
-                            foundStart = true;
-                        } else {
-                            throw new RuntimeException(
-                                    "redundant end at " +
-                                    Integer.toHexString(addr));
-                        }
-                    }
-                }
-
-                if (!foundStart &&
-                        (e.getDisposition() == Disposition.END_REPLACED)) {
-                    throw new RuntimeException(
-                            "improper end replacement claim at " +
-                            Integer.toHexString(addr));
-                }
-
-                active[reg] = null;
-            }
-        }
-    }
-
-    /**
-     * Intermediate state when constructing a local list.
-     */
-    public static class MakeState {
-        /** {@code non-null;} result being collected */
-        private final ArrayList<Entry> result;
-
-        /**
-         * {@code >= 0;} running count of nulled result entries, to help with
-         * sizing the final list
+      RegisterSpec movedLocal = regs.findMatchingLocal(startedLocal);
+      if (movedLocal != null) {
+        /*
+         * The same variable was moved from one register to another.
+         * So add an end for its old location.
          */
-        private int nullResultCount;
+        addOrUpdateEnd(address, Disposition.END_MOVED, movedLocal);
+      }
 
-        /** {@code null-ok;} current register mappings */
-        private RegisterSpecSet regs;
+      int endAt = endIndices[regNum];
 
-        /** {@code null-ok;} result indices where local ends are stored */
-        private int[] endIndices;
-
-        /** {@code >= 0;} last address seen */
-        private int lastAddress;
-
-        /**
-         * Constructs an instance.
+      if (existingLocal != null) {
+        /*
+         * There is an existing (but non-matching) local.
+         * Add an explicit end for it.
          */
-        public MakeState(int initialSize) {
-            result = new ArrayList<Entry>(initialSize);
-            nullResultCount = 0;
-            regs = null;
-            endIndices = null;
-            lastAddress = 0;
-        }
-
-        /**
-         * Checks the address and other vitals as a prerequisite to
-         * further processing.
-         *
-         * @param address {@code >= 0;} address about to be processed
-         * @param reg {@code >= 0;} register number about to be processed
+        add(address, Disposition.END_REPLACED, existingLocal);
+      } else if (endAt >= 0) {
+        /*
+         * Look for an end local for the same register at the
+         * same address. If found, then update it or delete
+         * it, depending on whether or not it represents the
+         * same variable as the one being started.
          */
-        private void aboutToProcess(int address, int reg) {
-            boolean first = (endIndices == null);
-
-            if ((address == lastAddress) && !first) {
-                return;
-            }
-
-            if (address < lastAddress) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            if (first || (reg >= endIndices.length)) {
-                /*
-                 * This is the first allocation of the state set and
-                 * index array, or we need to grow. (The latter doesn't
-                 * happen much; in fact, we have only ever observed
-                 * it happening in test cases, never in "real" code.)
-                 */
-                int newSz = reg + 1;
-                RegisterSpecSet newRegs = new RegisterSpecSet(newSz);
-                int[] newEnds = new int[newSz];
-                Arrays.fill(newEnds, -1);
-
-                if (!first) {
-                    newRegs.putAll(regs);
-                    System.arraycopy(endIndices, 0, newEnds, 0,
-                            endIndices.length);
-                }
-
-                regs = newRegs;
-                endIndices = newEnds;
-            }
-        }
-
-        /**
-         * Sets the local state at the given address to the given snapshot.
-         * The first call on this instance must be to this method, so that
-         * the register state can be properly sized.
-         *
-         * @param address {@code >= 0;} the address
-         * @param specs {@code non-null;} spec set representing the locals
-         */
-        public void snapshot(int address, RegisterSpecSet specs) {
-            if (DEBUG) {
-                System.err.printf("%04x snapshot %s\n", address, specs);
-            }
-
-            int sz = specs.getMaxSize();
-            aboutToProcess(address, sz - 1);
-
-            for (int i = 0; i < sz; i++) {
-                RegisterSpec oldSpec = regs.get(i);
-                RegisterSpec newSpec = filterSpec(specs.get(i));
-
-                if (oldSpec == null) {
-                    if (newSpec != null) {
-                        startLocal(address, newSpec);
-                    }
-                } else if (newSpec == null) {
-                    endLocal(address, oldSpec);
-                } else if (! newSpec.equalsUsingSimpleType(oldSpec)) {
-                    endLocal(address, oldSpec);
-                    startLocal(address, newSpec);
-                }
-            }
-
-            if (DEBUG) {
-                System.err.printf("%04x snapshot done\n", address);
-            }
-        }
-
-        /**
-         * Starts a local at the given address.
-         *
-         * @param address {@code >= 0;} the address
-         * @param startedLocal {@code non-null;} spec representing the
-         * started local
-         */
-        public void startLocal(int address, RegisterSpec startedLocal) {
-            if (DEBUG) {
-                System.err.printf("%04x start %s\n", address, startedLocal);
-            }
-
-            int regNum = startedLocal.getReg();
-
-            startedLocal = filterSpec(startedLocal);
-            aboutToProcess(address, regNum);
-
-            RegisterSpec existingLocal = regs.get(regNum);
-
-            if (startedLocal.equalsUsingSimpleType(existingLocal)) {
-                // Silently ignore a redundant start.
-                return;
-            }
-
-            RegisterSpec movedLocal = regs.findMatchingLocal(startedLocal);
-            if (movedLocal != null) {
-                /*
-                 * The same variable was moved from one register to another.
-                 * So add an end for its old location.
-                 */
-                addOrUpdateEnd(address, Disposition.END_MOVED, movedLocal);
-            }
-
-            int endAt = endIndices[regNum];
-
-            if (existingLocal != null) {
-                /*
-                 * There is an existing (but non-matching) local.
-                 * Add an explicit end for it.
-                 */
-                add(address, Disposition.END_REPLACED, existingLocal);
-            } else if (endAt >= 0) {
-                /*
-                 * Look for an end local for the same register at the
-                 * same address. If found, then update it or delete
-                 * it, depending on whether or not it represents the
-                 * same variable as the one being started.
-                 */
-                Entry endEntry = result.get(endAt);
-                if (endEntry.getAddress() == address) {
-                    if (endEntry.matches(startedLocal)) {
-                        /*
-                         * There was already an end local for the same
-                         * variable at the same address. This turns
-                         * out to be superfluous, as we are starting
-                         * up the exact same local. This situation can
-                         * happen when a single local variable got
-                         * somehow "split up" during intermediate
-                         * processing. In any case, rather than represent
-                         * the end-then-start, just remove the old end.
-                         */
-                        result.set(endAt, null);
-                        nullResultCount++;
-                        regs.put(startedLocal);
-                        endIndices[regNum] = -1;
-                        return;
-                    } else {
-                        /*
-                         * There was a different variable ended at the
-                         * same address. Update it to indicate that
-                         * it was ended due to a replacement (rather than
-                         * ending for no particular reason).
-                         */
-                        endEntry = endEntry.withDisposition(
-                                Disposition.END_REPLACED);
-                        result.set(endAt, endEntry);
-                    }
-                }
-            }
-
+        Entry endEntry = result.get(endAt);
+        if (endEntry.getAddress() == address) {
+          if (endEntry.matches(startedLocal)) {
             /*
-             * The code above didn't find and remove an unnecessary
-             * local end, so we now have to add one or more entries to
-             * the output to capture the transition.
+             * There was already an end local for the same
+             * variable at the same address. This turns
+             * out to be superfluous, as we are starting
+             * up the exact same local. This situation can
+             * happen when a single local variable got
+             * somehow "split up" during intermediate
+             * processing. In any case, rather than represent
+             * the end-then-start, just remove the old end.
              */
-
-            /*
-             * If the local just below (in the register set at reg-1)
-             * is of category-2, then it is ended by this new start.
-             */
-            if (regNum > 0) {
-                RegisterSpec justBelow = regs.get(regNum - 1);
-                if ((justBelow != null) && justBelow.isCategory2()) {
-                    addOrUpdateEnd(address,
-                            Disposition.END_CLOBBERED_BY_NEXT,
-                            justBelow);
-                }
-            }
-
-            /*
-             * Similarly, if this local is category-2, then the local
-             * just above (if any) is ended by the start now being
-             * emitted.
-             */
-            if (startedLocal.isCategory2()) {
-                RegisterSpec justAbove = regs.get(regNum + 1);
-                if (justAbove != null) {
-                    addOrUpdateEnd(address,
-                            Disposition.END_CLOBBERED_BY_PREV,
-                            justAbove);
-                }
-            }
-
-            /*
-             * TODO: Add an end for the same local in a different reg,
-             * if any (that is, if the local migrates from vX to vY,
-             * we should note that as a local end in vX).
-             */
-
-            add(address, Disposition.START, startedLocal);
-        }
-
-        /**
-         * Ends a local at the given address, using the disposition
-         * {@code END_SIMPLY}.
-         *
-         * @param address {@code >= 0;} the address
-         * @param endedLocal {@code non-null;} spec representing the
-         * local being ended
-         */
-        public void endLocal(int address, RegisterSpec endedLocal) {
-            endLocal(address, endedLocal, Disposition.END_SIMPLY);
-        }
-
-        /**
-         * Ends a local at the given address.
-         *
-         * @param address {@code >= 0;} the address
-         * @param endedLocal {@code non-null;} spec representing the
-         * local being ended
-         * @param disposition reason for the end
-         */
-        public void endLocal(int address, RegisterSpec endedLocal,
-                Disposition disposition) {
-            if (DEBUG) {
-                System.err.printf("%04x end %s\n", address, endedLocal);
-            }
-
-            int regNum = endedLocal.getReg();
-
-            endedLocal = filterSpec(endedLocal);
-            aboutToProcess(address, regNum);
-
-            int endAt = endIndices[regNum];
-
-            if (endAt >= 0) {
-                /*
-                 * The local in the given register is already ended.
-                 * Silently return without adding anything to the result.
-                 */
-                return;
-            }
-
-            // Check for start and end at the same address.
-            if (checkForEmptyRange(address, endedLocal)) {
-                return;
-            }
-
-            add(address, disposition, endedLocal);
-        }
-
-        /**
-         * Helper for {@link #endLocal}, which handles the cases where
-         * and end local is issued at the same address as a start local
-         * for the same register. If this case is found, then this
-         * method will remove the start (as the local was never actually
-         * active), update the {@link #endIndices} to be accurate, and
-         * if needed update the newly-active end to reflect an altered
-         * disposition.
-         *
-         * @param address {@code >= 0;} the address
-         * @param endedLocal {@code non-null;} spec representing the
-         * local being ended
-         * @return {@code true} iff this method found the case in question
-         * and adjusted things accordingly
-         */
-        private boolean checkForEmptyRange(int address,
-                RegisterSpec endedLocal) {
-            int at = result.size() - 1;
-            Entry entry;
-
-            // Look for a previous entry at the same address.
-            for (/*at*/; at >= 0; at--) {
-                entry = result.get(at);
-
-                if (entry == null) {
-                    continue;
-                }
-
-                if (entry.getAddress() != address) {
-                    // We didn't find any match at the same address.
-                    return false;
-                }
-
-                if (entry.matches(endedLocal)) {
-                    break;
-                }
-            }
-
-            /*
-             * In fact, we found that the endedLocal had started at the
-             * same address, so do all the requisite cleanup.
-             */
-
-            regs.remove(endedLocal);
-            result.set(at, null);
+            result.set(endAt, null);
             nullResultCount++;
-
-            int regNum = endedLocal.getReg();
-            boolean found = false;
-            entry = null;
-
-            // Now look back further to update where the register ended.
-            for (at--; at >= 0; at--) {
-                entry = result.get(at);
-
-                if (entry == null) {
-                    continue;
-                }
-
-                if (entry.getRegisterSpec().getReg() == regNum) {
-                    found = true;
-                    break;
-                }
-            }
-
-            if (found) {
-                // We found an end for the same register.
-                endIndices[regNum] = at;
-
-                if (entry.getAddress() == address) {
-                    /*
-                     * It's still the same address, so update the
-                     * disposition.
-                     */
-                    result.set(at,
-                            entry.withDisposition(Disposition.END_SIMPLY));
-                }
-            }
-
-            return true;
-        }
-
-        /**
-         * Converts a given spec into the form acceptable for use in a
-         * local list. This, in particular, transforms the "known
-         * null" type into simply {@code Object}. This method needs to
-         * be called for any spec that is on its way into a locals
-         * list.
-         *
-         * <p>This isn't necessarily the cleanest way to achieve the
-         * goal of not representing known nulls in a locals list, but
-         * it gets the job done.</p>
-         *
-         * @param orig {@code null-ok;} the original spec
-         * @return {@code null-ok;} an appropriately modified spec, or the
-         * original if nothing needs to be done
-         */
-        private static RegisterSpec filterSpec(RegisterSpec orig) {
-            if ((orig != null) && (orig.getType() == Type.KNOWN_NULL)) {
-                return orig.withType(Type.OBJECT);
-            }
-
-            return orig;
-        }
-
-        /**
-         * Adds an entry to the result, updating the adjunct tables
-         * accordingly.
-         *
-         * @param address {@code >= 0;} the address
-         * @param disposition {@code non-null;} the disposition
-         * @param spec {@code non-null;} spec representing the local
-         */
-        private void add(int address, Disposition disposition,
-                RegisterSpec spec) {
-            int regNum = spec.getReg();
-
-            result.add(new Entry(address, disposition, spec));
-
-            if (disposition == Disposition.START) {
-                regs.put(spec);
-                endIndices[regNum] = -1;
-            } else {
-                regs.remove(spec);
-                endIndices[regNum] = result.size() - 1;
-            }
-        }
-
-        /**
-         * Adds or updates an end local (changing its disposition). If
-         * this would cause an empty range for a local, this instead
-         * removes the local entirely.
-         *
-         * @param address {@code >= 0;} the address
-         * @param disposition {@code non-null;} the disposition
-         * @param spec {@code non-null;} spec representing the local
-         */
-        private void addOrUpdateEnd(int address, Disposition disposition,
-                RegisterSpec spec) {
-            if (disposition == Disposition.START) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            int regNum = spec.getReg();
-            int endAt = endIndices[regNum];
-
-            if (endAt >= 0) {
-                // There is a previous end.
-                Entry endEntry = result.get(endAt);
-                if ((endEntry.getAddress() == address) &&
-                        endEntry.getRegisterSpec().equals(spec)) {
-                    /*
-                     * The end is for the right address and variable, so
-                     * update it.
-                     */
-                    result.set(endAt, endEntry.withDisposition(disposition));
-                    regs.remove(spec); // TODO: Is this line superfluous?
-                    return;
-                }
-            }
-
-            endLocal(address, spec, disposition);
-        }
-
-        /**
-         * Finishes processing altogether and gets the result.
-         *
-         * @return {@code non-null;} the result list
-         */
-        public LocalList finish() {
-            aboutToProcess(Integer.MAX_VALUE, 0);
-
-            int resultSz = result.size();
-            int finalSz = resultSz - nullResultCount;
-
-            if (finalSz == 0) {
-                return EMPTY;
-            }
-
+            regs.put(startedLocal);
+            endIndices[regNum] = -1;
+            return;
+          } else {
             /*
-             * Collect an array of only the non-null entries, and then
-             * sort it to get a consistent order for everything: Local
-             * ends and starts for a given address could come in any
-             * order, but we want ends before starts as well as
-             * registers in order (within ends or starts).
+             * There was a different variable ended at the
+             * same address. Update it to indicate that
+             * it was ended due to a replacement (rather than
+             * ending for no particular reason).
              */
-
-            Entry[] resultArr = new Entry[finalSz];
-
-            if (resultSz == finalSz) {
-                result.toArray(resultArr);
-            } else {
-                int at = 0;
-                for (Entry e : result) {
-                    if (e != null) {
-                        resultArr[at++] = e;
-                    }
-                }
-            }
-
-            Arrays.sort(resultArr);
-
-            LocalList resultList = new LocalList(finalSz);
-
-            for (int i = 0; i < finalSz; i++) {
-                resultList.set(i, resultArr[i]);
-            }
-
-            resultList.setImmutable();
-            return resultList;
+            endEntry = endEntry.withDisposition(Disposition.END_REPLACED);
+            result.set(endAt, endEntry);
+          }
         }
+      }
+
+      /*
+       * The code above didn't find and remove an unnecessary
+       * local end, so we now have to add one or more entries to
+       * the output to capture the transition.
+       */
+
+/*
+         * If the local just below (in the register set at reg-1)
+         * is of category-2, then it is ended by this new start.
+         */
+      if (regNum > 0) {
+        RegisterSpec justBelow = regs.get(regNum - 1);
+        if ((justBelow != null) && justBelow.isCategory2()) {
+          addOrUpdateEnd(address, Disposition.END_CLOBBERED_BY_NEXT, justBelow);
+        }
+      }
+
+      /*
+       * Similarly, if this local is category-2, then the local
+       * just above (if any) is ended by the start now being
+       * emitted.
+       */
+      if (startedLocal.isCategory2()) {
+        RegisterSpec justAbove = regs.get(regNum + 1);
+        if (justAbove != null) {
+          addOrUpdateEnd(address, Disposition.END_CLOBBERED_BY_PREV, justAbove);
+        }
+      }
+
+      /*
+       * TODO(dx team): Add an end for the same local in a different reg,
+       * if any (that is, if the local migrates from vX to vY,
+       * we should note that as a local end in vX).
+       */
+
+add(address, Disposition.START, startedLocal);
     }
+
+    /**
+     * Ends a local at the given address, using the disposition
+     * {@code END_SIMPLY}.
+     *
+     * @param address {@code >= 0;} the address
+     * @param endedLocal {@code non-null;} spec representing the
+     * local being ended
+     */
+    public void endLocal(int address, RegisterSpec endedLocal) {
+      endLocal(address, endedLocal, Disposition.END_SIMPLY);
+    }
+
+    /**
+     * Ends a local at the given address.
+     *
+     * @param address {@code >= 0;} the address
+     * @param endedLocal {@code non-null;} spec representing the
+     * local being ended
+     * @param disposition reason for the end
+     */
+    public void endLocal(int address, RegisterSpec endedLocal, Disposition disposition) {
+      if (DEBUG) {
+        System.err.printf("%04x end %s\n", address, endedLocal);
+      }
+
+      int regNum = endedLocal.getReg();
+
+      endedLocal = filterSpec(endedLocal);
+      aboutToProcess(address, regNum);
+
+      int endAt = endIndices[regNum];
+
+      if (endAt >= 0) {
+        /*
+         * The local in the given register is already ended.
+         * Silently return without adding anything to the result.
+         */
+        return;
+      }
+
+      // Check for start and end at the same address.
+      if (checkForEmptyRange(address, endedLocal)) {
+        return;
+      }
+
+      add(address, disposition, endedLocal);
+    }
+
+    /**
+     * Helper for {@link #endLocal}, which handles the cases where
+     * and end local is issued at the same address as a start local
+     * for the same register. If this case is found, then this
+     * method will remove the start (as the local was never actually
+     * active), update the {@link #endIndices} to be accurate, and
+     * if needed update the newly-active end to reflect an altered
+     * disposition.
+     *
+     * @param address {@code >= 0;} the address
+     * @param endedLocal {@code non-null;} spec representing the
+     * local being ended
+     * @return {@code true} iff this method found the case in question
+     * and adjusted things accordingly
+     */
+    private boolean checkForEmptyRange(int address, RegisterSpec endedLocal) {
+      int at = result.size() - 1;
+      Entry entry;
+
+      // Look for a previous entry at the same address.
+      for (/*at*/; at >= 0; at--) {
+        entry = result.get(at);
+
+        if (entry == null) {
+          continue;
+        }
+
+        if (entry.getAddress() != address) {
+          // We didn't find any match at the same address.
+          return false;
+        }
+
+        if (entry.matches(endedLocal)) {
+          break;
+        }
+      }
+
+      /*
+       * In fact, we found that the endedLocal had started at the
+       * same address, so do all the requisite cleanup.
+       */
+
+regs.remove(endedLocal);
+      result.set(at, null);
+      nullResultCount++;
+
+      int regNum = endedLocal.getReg();
+      boolean found = false;
+      entry = null;
+
+      // Now look back further to update where the register ended.
+      for (at--; at >= 0; at--) {
+        entry = result.get(at);
+
+        if (entry == null) {
+          continue;
+        }
+
+        if (entry.getRegisterSpec().getReg() == regNum) {
+          found = true;
+          break;
+        }
+      }
+
+      if (found) {
+        // We found an end for the same register.
+        endIndices[regNum] = at;
+
+        if (entry.getAddress() == address) {
+          /*
+           * It's still the same address, so update the
+           * disposition.
+           */
+          result.set(at, entry.withDisposition(Disposition.END_SIMPLY));
+        }
+      }
+
+      return true;
+    }
+
+    /**
+     * Converts a given spec into the form acceptable for use in a
+     * local list. This, in particular, transforms the "known
+     * null" type into simply {@code Object}. This method needs to
+     * be called for any spec that is on its way into a locals
+     * list.
+     *
+     * <p>This isn't necessarily the cleanest way to achieve the
+     * goal of not representing known nulls in a locals list, but
+     * it gets the job done.</p>
+     *
+     * @param orig {@code null-ok;} the original spec
+     * @return {@code null-ok;} an appropriately modified spec, or the
+     * original if nothing needs to be done
+     */
+    private static RegisterSpec filterSpec(RegisterSpec orig) {
+      if ((orig != null) && (orig.getType() == Type.KNOWN_NULL)) {
+        return orig.withType(Type.OBJECT);
+      }
+
+      return orig;
+    }
+
+    /**
+     * Adds an entry to the result, updating the adjunct tables
+     * accordingly.
+     *
+     * @param address {@code >= 0;} the address
+     * @param disposition {@code non-null;} the disposition
+     * @param spec {@code non-null;} spec representing the local
+     */
+    private void add(int address, Disposition disposition, RegisterSpec spec) {
+      int regNum = spec.getReg();
+
+      result.add(new Entry(address, disposition, spec));
+
+      if (disposition == Disposition.START) {
+        regs.put(spec);
+        endIndices[regNum] = -1;
+      } else {
+        regs.remove(spec);
+        endIndices[regNum] = result.size() - 1;
+      }
+    }
+
+    /**
+     * Adds or updates an end local (changing its disposition). If
+     * this would cause an empty range for a local, this instead
+     * removes the local entirely.
+     *
+     * @param address {@code >= 0;} the address
+     * @param disposition {@code non-null;} the disposition
+     * @param spec {@code non-null;} spec representing the local
+     */
+    private void addOrUpdateEnd(int address, Disposition disposition, RegisterSpec spec) {
+      if (disposition == Disposition.START) {
+        throw new RuntimeException("shouldn't happen");
+      }
+
+      int regNum = spec.getReg();
+      int endAt = endIndices[regNum];
+
+      if (endAt >= 0) {
+        // There is a previous end.
+        Entry endEntry = result.get(endAt);
+        if ((endEntry.getAddress() == address) && endEntry.getRegisterSpec().equals(spec)) {
+          /*
+           * The end is for the right address and variable, so
+           * update it.
+           */
+          result.set(endAt, endEntry.withDisposition(disposition));
+          regs.remove(spec); // TODO(dx team): Is this line superfluous?
+          return;
+        }
+      }
+
+      endLocal(address, spec, disposition);
+    }
+
+    /**
+     * Finishes processing altogether and gets the result.
+     *
+     * @return {@code non-null;} the result list
+     */
+    public LocalList finish() {
+      aboutToProcess(Integer.MAX_VALUE, 0);
+
+      int resultSz = result.size();
+      int finalSz = resultSz - nullResultCount;
+
+      if (finalSz == 0) {
+        return EMPTY;
+      }
+
+      /*
+       * Collect an array of only the non-null entries, and then
+       * sort it to get a consistent order for everything: Local
+       * ends and starts for a given address could come in any
+       * order, but we want ends before starts as well as
+       * registers in order (within ends or starts).
+       */
+
+Entry[] resultArr = new Entry[finalSz];
+
+      if (resultSz == finalSz) {
+        result.toArray(resultArr);
+      } else {
+        int at = 0;
+        for (Entry e : result) {
+          if (e != null) {
+            resultArr[at++] = e;
+          }
+        }
+      }
+
+      Arrays.sort(resultArr);
+
+      LocalList resultList = new LocalList(finalSz);
+
+      for (int i = 0; i < finalSz; i++) {
+        resultList.set(i, resultArr[i]);
+      }
+
+      resultList.setImmutable();
+      return resultList;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/LocalSnapshot.java b/dx/src/com/android/jack/dx/dex/code/LocalSnapshot.java
index 01f3943..d14a9a2 100644
--- a/dx/src/com/android/jack/dx/dex/code/LocalSnapshot.java
+++ b/dx/src/com/android/jack/dx/dex/code/LocalSnapshot.java
@@ -27,70 +27,70 @@
  * the instance in an instruction array.
  */
 public final class LocalSnapshot extends ZeroSizeInsn {
-    /** {@code non-null;} local state associated with this instance */
-    private final RegisterSpecSet locals;
+  /** {@code non-null;} local state associated with this instance */
+  private final RegisterSpecSet locals;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param locals {@code non-null;} associated local variable state
-     */
-    public LocalSnapshot(SourcePosition position, RegisterSpecSet locals) {
-        super(position);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param locals {@code non-null;} associated local variable state
+   */
+  public LocalSnapshot(SourcePosition position, RegisterSpecSet locals) {
+    super(position);
 
-        if (locals == null) {
-            throw new NullPointerException("locals == null");
-        }
-
-        this.locals = locals;
+    if (locals == null) {
+      throw new NullPointerException("locals == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisterOffset(int delta) {
-        return new LocalSnapshot(getPosition(), locals.withOffset(delta));
+    this.locals = locals;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisterOffset(int delta) {
+    return new LocalSnapshot(getPosition(), locals.withOffset(delta));
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new LocalSnapshot(getPosition(), locals);
+  }
+
+  /**
+   * Gets the local state associated with this instance.
+   *
+   * @return {@code non-null;} the state
+   */
+  public RegisterSpecSet getLocals() {
+    return locals;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return locals.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    int sz = locals.size();
+    int max = locals.getMaxSize();
+    StringBuffer sb = new StringBuffer(100 + sz * 40);
+
+    sb.append("local-snapshot");
+
+    for (int i = 0; i < max; i++) {
+      RegisterSpec spec = locals.get(i);
+      if (spec != null) {
+        sb.append("\n  ");
+        sb.append(LocalStart.localString(spec));
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new LocalSnapshot(getPosition(), locals);
-    }
-
-    /**
-     * Gets the local state associated with this instance.
-     *
-     * @return {@code non-null;} the state
-     */
-    public RegisterSpecSet getLocals() {
-        return locals;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return locals.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        int sz = locals.size();
-        int max = locals.getMaxSize();
-        StringBuffer sb = new StringBuffer(100 + sz * 40);
-
-        sb.append("local-snapshot");
-
-        for (int i = 0; i < max; i++) {
-            RegisterSpec spec = locals.get(i);
-            if (spec != null) {
-                sb.append("\n  ");
-                sb.append(LocalStart.localString(spec));
-            }
-        }
-
-        return sb.toString();
-    }
+    return sb.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/LocalStart.java b/dx/src/com/android/jack/dx/dex/code/LocalStart.java
index 9b8a400..5d5f6ab 100644
--- a/dx/src/com/android/jack/dx/dex/code/LocalStart.java
+++ b/dx/src/com/android/jack/dx/dex/code/LocalStart.java
@@ -27,72 +27,72 @@
  * is bound.
  */
 public final class LocalStart extends ZeroSizeInsn {
-    /**
-     * {@code non-null;} register spec representing the local variable introduced
-     * by this instance
-     */
-    private final RegisterSpec local;
+  /**
+   * {@code non-null;} register spec representing the local variable introduced
+   * by this instance
+   */
+  private final RegisterSpec local;
 
-    /**
-     * Returns the local variable listing string for a single register spec.
-     *
-     * @param spec {@code non-null;} the spec to convert
-     * @return {@code non-null;} the string form
-     */
-    public static String localString(RegisterSpec spec) {
-        return spec.regString() + ' ' + spec.getLocalItem().toString() + ": " +
-            spec.getTypeBearer().toHuman();
+  /**
+   * Returns the local variable listing string for a single register spec.
+   *
+   * @param spec {@code non-null;} the spec to convert
+   * @return {@code non-null;} the string form
+   */
+  public static String localString(RegisterSpec spec) {
+    return spec.regString() + ' ' + spec.getLocalItem().toString() + ": "
+        + spec.getTypeBearer().toHuman();
+  }
+
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param local {@code non-null;} register spec representing the local
+   * variable introduced by this instance
+   */
+  public LocalStart(SourcePosition position, RegisterSpec local) {
+    super(position);
+
+    if (local == null) {
+      throw new NullPointerException("local == null");
     }
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param local {@code non-null;} register spec representing the local
-     * variable introduced by this instance
-     */
-    public LocalStart(SourcePosition position, RegisterSpec local) {
-        super(position);
+    this.local = local;
+  }
 
-        if (local == null) {
-            throw new NullPointerException("local == null");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisterOffset(int delta) {
+    return new LocalStart(getPosition(), local.withOffset(delta));
+  }
 
-        this.local = local;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new LocalStart(getPosition(), local);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisterOffset(int delta) {
-        return new LocalStart(getPosition(), local.withOffset(delta));
-    }
+  /**
+   * Gets the register spec representing the local variable introduced
+   * by this instance.
+   *
+   * @return {@code non-null;} the register spec
+   */
+  public RegisterSpec getLocal() {
+    return local;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new LocalStart(getPosition(), local);
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return local.toString();
+  }
 
-    /**
-     * Gets the register spec representing the local variable introduced
-     * by this instance.
-     *
-     * @return {@code non-null;} the register spec
-     */
-    public RegisterSpec getLocal() {
-        return local;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return local.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        return "local-start " + localString(local);
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    return "local-start " + localString(local);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/OddSpacer.java b/dx/src/com/android/jack/dx/dex/code/OddSpacer.java
index c9166f5..8924659 100644
--- a/dx/src/com/android/jack/dx/dex/code/OddSpacer.java
+++ b/dx/src/com/android/jack/dx/dex/code/OddSpacer.java
@@ -28,49 +28,49 @@
  * require it.
  */
 public final class OddSpacer extends VariableSizeInsn {
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     */
-    public OddSpacer(SourcePosition position) {
-        super(position, RegisterSpecList.EMPTY);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   */
+  public OddSpacer(SourcePosition position) {
+    super(position, RegisterSpecList.EMPTY);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return (getAddress() & 1);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out) {
+    if (codeSize() != 0) {
+      out.writeShort(InsnFormat.codeUnit(Opcodes.NOP, 0));
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new OddSpacer(getPosition());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    if (codeSize() == 0) {
+      return null;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return (getAddress() & 1);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out) {
-        if (codeSize() != 0) {
-            out.writeShort(InsnFormat.codeUnit(Opcodes.NOP, 0));
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new OddSpacer(getPosition());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return null;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        if (codeSize() == 0) {
-            return null;
-        }
-
-        return "nop // spacer";
-    }
+    return "nop // spacer";
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/OutputCollector.java b/dx/src/com/android/jack/dx/dex/code/OutputCollector.java
index 3225b24..6c12f4c 100644
--- a/dx/src/com/android/jack/dx/dex/code/OutputCollector.java
+++ b/dx/src/com/android/jack/dx/dex/code/OutputCollector.java
@@ -29,93 +29,93 @@
  * instance.
  */
 public final class OutputCollector {
-    /**
-     * {@code non-null;} the associated finisher (which holds the instruction
-     * list in-progress)
-     */
-    private final OutputFinisher finisher;
+  /**
+   * {@code non-null;} the associated finisher (which holds the instruction
+   * list in-progress)
+   */
+  private final OutputFinisher finisher;
 
-    /**
-     * {@code null-ok;} suffix for the output, or {@code null} if the suffix
-     * has been appended to the main output (by {@link #appendSuffixToOutput})
-     */
-    private ArrayList<DalvInsn> suffix;
+  /**
+   * {@code null-ok;} suffix for the output, or {@code null} if the suffix
+   * has been appended to the main output (by {@link #appendSuffixToOutput})
+   */
+  private ArrayList<DalvInsn> suffix;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param dexOptions {@code non-null;} options for dex output
-     * @param initialCapacity {@code >= 0;} initial capacity of the output list
-     * @param suffixInitialCapacity {@code >= 0;} initial capacity of the output
-     * suffix
-     * @param regCount {@code >= 0;} register count for the method
-     */
-    public OutputCollector(DexOptions dexOptions, int initialCapacity, int suffixInitialCapacity,
-            int regCount) {
-        this.finisher = new OutputFinisher(dexOptions, initialCapacity, regCount);
-        this.suffix = new ArrayList<DalvInsn>(suffixInitialCapacity);
+  /**
+   * Constructs an instance.
+   *
+   * @param dexOptions {@code non-null;} options for dex output
+   * @param initialCapacity {@code >= 0;} initial capacity of the output list
+   * @param suffixInitialCapacity {@code >= 0;} initial capacity of the output
+   * suffix
+   * @param regCount {@code >= 0;} register count for the method
+   */
+  public OutputCollector(DexOptions dexOptions, int initialCapacity, int suffixInitialCapacity,
+      int regCount) {
+    this.finisher = new OutputFinisher(dexOptions, initialCapacity, regCount);
+    this.suffix = new ArrayList<DalvInsn>(suffixInitialCapacity);
+  }
+
+  /**
+   * Adds an instruction to the output.
+   *
+   * @param insn {@code non-null;} the instruction to add
+   */
+  public void add(DalvInsn insn) {
+    finisher.add(insn);
+  }
+
+  /**
+   * Reverses a branch which is buried a given number of instructions
+   * backward in the output. It is illegal to call this unless the
+   * indicated instruction really is a reversible branch.
+   *
+   * @param which how many instructions back to find the branch;
+   * {@code 0} is the most recently added instruction,
+   * {@code 1} is the instruction before that, etc.
+   * @param newTarget {@code non-null;} the new target for the reversed branch
+   */
+  public void reverseBranch(int which, CodeAddress newTarget) {
+    finisher.reverseBranch(which, newTarget);
+  }
+
+  /**
+   * Adds an instruction to the output suffix.
+   *
+   * @param insn {@code non-null;} the instruction to add
+   */
+  public void addSuffix(DalvInsn insn) {
+    suffix.add(insn);
+  }
+
+  /**
+   * Gets the results of all the calls on this instance, in the form of
+   * an {@link OutputFinisher}.
+   *
+   * @return {@code non-null;} the output finisher
+   * @throws UnsupportedOperationException if this method has
+   * already been called
+   */
+  public OutputFinisher getFinisher() {
+    if (suffix == null) {
+      throw new UnsupportedOperationException("already processed");
     }
 
-    /**
-     * Adds an instruction to the output.
-     *
-     * @param insn {@code non-null;} the instruction to add
-     */
-    public void add(DalvInsn insn) {
-        finisher.add(insn);
+    appendSuffixToOutput();
+    return finisher;
+  }
+
+  /**
+   * Helper for {@link #getFinisher}, which appends the suffix to
+   * the primary output.
+   */
+  private void appendSuffixToOutput() {
+    int size = suffix.size();
+
+    for (int i = 0; i < size; i++) {
+      finisher.add(suffix.get(i));
     }
 
-    /**
-     * Reverses a branch which is buried a given number of instructions
-     * backward in the output. It is illegal to call this unless the
-     * indicated instruction really is a reversible branch.
-     *
-     * @param which how many instructions back to find the branch;
-     * {@code 0} is the most recently added instruction,
-     * {@code 1} is the instruction before that, etc.
-     * @param newTarget {@code non-null;} the new target for the reversed branch
-     */
-    public void reverseBranch(int which, CodeAddress newTarget) {
-        finisher.reverseBranch(which, newTarget);
-    }
-
-    /**
-     * Adds an instruction to the output suffix.
-     *
-     * @param insn {@code non-null;} the instruction to add
-     */
-    public void addSuffix(DalvInsn insn) {
-        suffix.add(insn);
-    }
-
-    /**
-     * Gets the results of all the calls on this instance, in the form of
-     * an {@link OutputFinisher}.
-     *
-     * @return {@code non-null;} the output finisher
-     * @throws UnsupportedOperationException if this method has
-     * already been called
-     */
-    public OutputFinisher getFinisher() {
-        if (suffix == null) {
-            throw new UnsupportedOperationException("already processed");
-        }
-
-        appendSuffixToOutput();
-        return finisher;
-    }
-
-    /**
-     * Helper for {@link #getFinisher}, which appends the suffix to
-     * the primary output.
-     */
-    private void appendSuffixToOutput() {
-        int size = suffix.size();
-
-        for (int i = 0; i < size; i++) {
-            finisher.add(suffix.get(i));
-        }
-
-        suffix = null;
-    }
+    suffix = null;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/OutputFinisher.java b/dx/src/com/android/jack/dx/dex/code/OutputFinisher.java
index f004b02..ac3923d 100644
--- a/dx/src/com/android/jack/dx/dex/code/OutputFinisher.java
+++ b/dx/src/com/android/jack/dx/dex/code/OutputFinisher.java
@@ -41,744 +41,735 @@
  * form of a {@link DalvInsnList} instance.
  */
 public final class OutputFinisher {
-    /** {@code non-null;} options for dex output */
-    private final DexOptions dexOptions;
+  /** {@code non-null;} options for dex output */
+  private final DexOptions dexOptions;
 
-    /**
-     * {@code >= 0;} register count for the method, not including any extra
-     * "reserved" registers needed to translate "difficult" instructions
-     */
-    private final int unreservedRegCount;
+  /**
+   * {@code >= 0;} register count for the method, not including any extra
+   * "reserved" registers needed to translate "difficult" instructions
+   */
+  private final int unreservedRegCount;
 
-    /** {@code non-null;} the list of instructions, per se */
-    private ArrayList<DalvInsn> insns;
+  /** {@code non-null;} the list of instructions, per se */
+  private ArrayList<DalvInsn> insns;
 
-    /** whether any instruction has position info */
-    private boolean hasAnyPositionInfo;
+  /** whether any instruction has position info */
+  private boolean hasAnyPositionInfo;
 
-    /** whether any instruction has local variable info */
-    private boolean hasAnyLocalInfo;
+  /** whether any instruction has local variable info */
+  private boolean hasAnyLocalInfo;
 
-    /**
-     * {@code >= 0;} the count of reserved registers (low-numbered
-     * registers used when expanding instructions that can't be
-     * represented simply); becomes valid after a call to {@link
-     * #massageInstructions}
-     */
-    private int reservedCount;
+  /**
+   * {@code >= 0;} the count of reserved registers (low-numbered
+   * registers used when expanding instructions that can't be
+   * represented simply); becomes valid after a call to {@link
+   * #massageInstructions}
+   */
+  private int reservedCount;
 
-    /**
-     * Constructs an instance. It initially contains no instructions.
-     *
-     * @param dexOptions {@code non-null;} options for dex output
-     * @param regCount {@code >= 0;} register count for the method
-     * @param initialCapacity {@code >= 0;} initial capacity of the
-     * instructions list
-     */
-    public OutputFinisher(DexOptions dexOptions, int initialCapacity, int regCount) {
-        this.dexOptions = dexOptions;
-        this.unreservedRegCount = regCount;
-        this.insns = new ArrayList<DalvInsn>(initialCapacity);
-        this.reservedCount = -1;
-        this.hasAnyPositionInfo = false;
-        this.hasAnyLocalInfo = false;
-    }
+  /**
+   * Constructs an instance. It initially contains no instructions.
+   *
+   * @param dexOptions {@code non-null;} options for dex output
+   * @param regCount {@code >= 0;} register count for the method
+   * @param initialCapacity {@code >= 0;} initial capacity of the
+   * instructions list
+   */
+  public OutputFinisher(DexOptions dexOptions, int initialCapacity, int regCount) {
+    this.dexOptions = dexOptions;
+    this.unreservedRegCount = regCount;
+    this.insns = new ArrayList<DalvInsn>(initialCapacity);
+    this.reservedCount = -1;
+    this.hasAnyPositionInfo = false;
+    this.hasAnyLocalInfo = false;
+  }
 
-    /**
-     * Returns whether any of the instructions added to this instance
-     * come with position info.
-     *
-     * @return whether any of the instructions added to this instance
-     * come with position info
-     */
-    public boolean hasAnyPositionInfo() {
-        return hasAnyPositionInfo;
-    }
+  /**
+   * Returns whether any of the instructions added to this instance
+   * come with position info.
+   *
+   * @return whether any of the instructions added to this instance
+   * come with position info
+   */
+  public boolean hasAnyPositionInfo() {
+    return hasAnyPositionInfo;
+  }
 
-    /**
-     * Returns whether this instance has any local variable information.
-     *
-     * @return whether this instance has any local variable information
-     */
-    public boolean hasAnyLocalInfo() {
-        return hasAnyLocalInfo;
-    }
+  /**
+   * Returns whether this instance has any local variable information.
+   *
+   * @return whether this instance has any local variable information
+   */
+  public boolean hasAnyLocalInfo() {
+    return hasAnyLocalInfo;
+  }
 
-    /**
-     * Helper for {@link #add} which scrutinizes a single
-     * instruction for local variable information.
-     *
-     * @param insn {@code non-null;} instruction to scrutinize
-     * @return {@code true} iff the instruction refers to any
-     * named locals
-     */
-    private static boolean hasLocalInfo(DalvInsn insn) {
-        if (insn instanceof LocalSnapshot) {
-            RegisterSpecSet specs = ((LocalSnapshot) insn).getLocals();
-            int size = specs.size();
-            for (int i = 0; i < size; i++) {
-                if (hasLocalInfo(specs.get(i))) {
-                    return true;
-                }
-            }
-        } else if (insn instanceof LocalStart) {
-            RegisterSpec spec = ((LocalStart) insn).getLocal();
-            if (hasLocalInfo(spec)) {
-                return true;
-            }
+  /**
+   * Helper for {@link #add} which scrutinizes a single
+   * instruction for local variable information.
+   *
+   * @param insn {@code non-null;} instruction to scrutinize
+   * @return {@code true} iff the instruction refers to any
+   * named locals
+   */
+  private static boolean hasLocalInfo(DalvInsn insn) {
+    if (insn instanceof LocalSnapshot) {
+      RegisterSpecSet specs = ((LocalSnapshot) insn).getLocals();
+      int size = specs.size();
+      for (int i = 0; i < size; i++) {
+        if (hasLocalInfo(specs.get(i))) {
+          return true;
         }
-
-        return false;
+      }
+    } else if (insn instanceof LocalStart) {
+      RegisterSpec spec = ((LocalStart) insn).getLocal();
+      if (hasLocalInfo(spec)) {
+        return true;
+      }
     }
 
-    /**
-     * Helper for {@link #hasAnyLocalInfo} which scrutinizes a single
-     * register spec.
-     *
-     * @param spec {@code non-null;} spec to scrutinize
-     * @return {@code true} iff the spec refers to any
-     * named locals
-     */
-    private static boolean hasLocalInfo(RegisterSpec spec) {
-        return (spec != null)
-            && (spec.getLocalItem().getName() != null);
+    return false;
+  }
+
+  /**
+   * Helper for {@link #hasAnyLocalInfo} which scrutinizes a single
+   * register spec.
+   *
+   * @param spec {@code non-null;} spec to scrutinize
+   * @return {@code true} iff the spec refers to any
+   * named locals
+   */
+  private static boolean hasLocalInfo(RegisterSpec spec) {
+    return (spec != null) && (spec.getLocalItem().getName() != null);
+  }
+
+  /**
+   * Returns the set of all constants referred to by instructions added
+   * to this instance.
+   *
+   * @return {@code non-null;} the set of constants
+   */
+  public HashSet<Constant> getAllConstants() {
+    HashSet<Constant> result = new HashSet<Constant>(20);
+
+    for (DalvInsn insn : insns) {
+      addConstants(result, insn);
     }
 
-    /**
-     * Returns the set of all constants referred to by instructions added
-     * to this instance.
-     *
-     * @return {@code non-null;} the set of constants
-     */
-    public HashSet<Constant> getAllConstants() {
-        HashSet<Constant> result = new HashSet<Constant>(20);
+    return result;
+  }
 
-        for (DalvInsn insn : insns) {
-            addConstants(result, insn);
-        }
+  /**
+   * Helper for {@link #getAllConstants} which adds all the info for
+   * a single instruction.
+   *
+   * @param result {@code non-null;} result set to add to
+   * @param insn {@code non-null;} instruction to scrutinize
+   */
+  private static void addConstants(HashSet<Constant> result, DalvInsn insn) {
+    if (insn instanceof CstInsn) {
+      Constant cst = ((CstInsn) insn).getConstant();
+      result.add(cst);
+    } else if (insn instanceof LocalSnapshot) {
+      RegisterSpecSet specs = ((LocalSnapshot) insn).getLocals();
+      int size = specs.size();
+      for (int i = 0; i < size; i++) {
+        addConstants(result, specs.get(i));
+      }
+    } else if (insn instanceof LocalStart) {
+      RegisterSpec spec = ((LocalStart) insn).getLocal();
+      addConstants(result, spec);
+    }
+  }
 
-        return result;
+  /**
+   * Helper for {@link #getAllConstants} which adds all the info for
+   * a single {@code RegisterSpec}.
+   *
+   * @param result {@code non-null;} result set to add to
+   * @param spec {@code null-ok;} register spec to add
+   */
+  private static void addConstants(HashSet<Constant> result, RegisterSpec spec) {
+    if (spec == null) {
+      return;
     }
 
-    /**
-     * Helper for {@link #getAllConstants} which adds all the info for
-     * a single instruction.
-     *
-     * @param result {@code non-null;} result set to add to
-     * @param insn {@code non-null;} instruction to scrutinize
-     */
-    private static void addConstants(HashSet<Constant> result,
-            DalvInsn insn) {
-        if (insn instanceof CstInsn) {
-            Constant cst = ((CstInsn) insn).getConstant();
-            result.add(cst);
-        } else if (insn instanceof LocalSnapshot) {
-            RegisterSpecSet specs = ((LocalSnapshot) insn).getLocals();
-            int size = specs.size();
-            for (int i = 0; i < size; i++) {
-                addConstants(result, specs.get(i));
-            }
-        } else if (insn instanceof LocalStart) {
-            RegisterSpec spec = ((LocalStart) insn).getLocal();
-            addConstants(result, spec);
-        }
+    LocalItem local = spec.getLocalItem();
+    CstString name = local.getName();
+    CstString signature = local.getSignature();
+    Type type = spec.getType();
+    CstType localType = local.getType();
+
+    if (type != Type.KNOWN_NULL) {
+      result.add(CstType.intern(type));
     }
 
-    /**
-     * Helper for {@link #getAllConstants} which adds all the info for
-     * a single {@code RegisterSpec}.
-     *
-     * @param result {@code non-null;} result set to add to
-     * @param spec {@code null-ok;} register spec to add
-     */
-    private static void addConstants(HashSet<Constant> result,
-            RegisterSpec spec) {
-        if (spec == null) {
-            return;
-        }
-
-        LocalItem local = spec.getLocalItem();
-        CstString name = local.getName();
-        CstString signature = local.getSignature();
-        Type type = spec.getType();
-        CstType localType = local.getType();
-
-        if (type != Type.KNOWN_NULL) {
-            result.add(CstType.intern(type));
-        }
-
-        if (localType != null) {
-            result.add(localType);
-        }
-
-        if (name != null) {
-            result.add(name);
-        }
-
-        if (signature != null) {
-            result.add(signature);
-        }
+    if (localType != null) {
+      result.add(localType);
     }
 
-    /**
-     * Adds an instruction to the output.
-     *
-     * @param insn {@code non-null;} the instruction to add
-     */
-    public void add(DalvInsn insn) {
-        insns.add(insn);
-        updateInfo(insn);
+    if (name != null) {
+      result.add(name);
     }
 
-    /**
-     * Inserts an instruction in the output at the given offset.
-     *
-     * @param at {@code >= 0;} what index to insert at
-     * @param insn {@code non-null;} the instruction to insert
-     */
-    public void insert(int at, DalvInsn insn) {
-        insns.add(at, insn);
-        updateInfo(insn);
+    if (signature != null) {
+      result.add(signature);
+    }
+  }
+
+  /**
+   * Adds an instruction to the output.
+   *
+   * @param insn {@code non-null;} the instruction to add
+   */
+  public void add(DalvInsn insn) {
+    insns.add(insn);
+    updateInfo(insn);
+  }
+
+  /**
+   * Inserts an instruction in the output at the given offset.
+   *
+   * @param at {@code >= 0;} what index to insert at
+   * @param insn {@code non-null;} the instruction to insert
+   */
+  public void insert(int at, DalvInsn insn) {
+    insns.add(at, insn);
+    updateInfo(insn);
+  }
+
+  /**
+   * Helper for {@link #add} and {@link #insert},
+   * which updates the position and local info flags.
+   *
+   * @param insn {@code non-null;} an instruction that was just introduced
+   */
+  private void updateInfo(DalvInsn insn) {
+    if (!hasAnyPositionInfo) {
+      SourcePosition pos = insn.getPosition();
+      if (pos.getLine() >= 0) {
+        hasAnyPositionInfo = true;
+      }
     }
 
-    /**
-     * Helper for {@link #add} and {@link #insert},
-     * which updates the position and local info flags.
-     *
-     * @param insn {@code non-null;} an instruction that was just introduced
+    if (!hasAnyLocalInfo) {
+      if (hasLocalInfo(insn)) {
+        hasAnyLocalInfo = true;
+      }
+    }
+  }
+
+  /**
+   * Reverses a branch which is buried a given number of instructions
+   * backward in the output. It is illegal to call this unless the
+   * indicated instruction really is a reversible branch.
+   *
+   * @param which how many instructions back to find the branch;
+   * {@code 0} is the most recently added instruction,
+   * {@code 1} is the instruction before that, etc.
+   * @param newTarget {@code non-null;} the new target for the
+   * reversed branch
+   */
+  public void reverseBranch(int which, CodeAddress newTarget) {
+    int size = insns.size();
+    int index = size - which - 1;
+    TargetInsn targetInsn;
+
+    try {
+      targetInsn = (TargetInsn) insns.get(index);
+    } catch (IndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("too few instructions");
+    } catch (ClassCastException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("non-reversible instruction");
+    }
+
+    /*
+     * No need to call this.set(), since the format and other info
+     * are the same.
      */
-    private void updateInfo(DalvInsn insn) {
-        if (! hasAnyPositionInfo) {
-            SourcePosition pos = insn.getPosition();
-            if (pos.getLine() >= 0) {
-                hasAnyPositionInfo = true;
-            }
+    insns.set(index, targetInsn.withNewTargetAndReversed(newTarget));
+  }
+
+  /**
+   * Assigns indices in all instructions that need them, using the
+   * given callback to perform lookups. This should be called before
+   * calling {@link #finishProcessingAndGetList}.
+   *
+   * @param callback {@code non-null;} callback object
+   */
+  public void assignIndices(DalvCode.AssignIndicesCallback callback) {
+    for (DalvInsn insn : insns) {
+      if (insn instanceof CstInsn) {
+        assignIndices((CstInsn) insn, callback);
+      }
+    }
+  }
+
+  /**
+   * Helper for {@link #assignIndices} which does assignment for one
+   * instruction.
+   *
+   * @param insn {@code non-null;} the instruction
+   * @param callback {@code non-null;} the callback
+   */
+  private static void assignIndices(CstInsn insn, DalvCode.AssignIndicesCallback callback) {
+    Constant cst = insn.getConstant();
+    int index = callback.getIndex(cst);
+
+    if (index >= 0) {
+      insn.setIndex(index);
+    }
+
+    if (cst instanceof CstMemberRef) {
+      CstMemberRef member = (CstMemberRef) cst;
+      CstType definer = member.getDefiningClass();
+      index = callback.getIndex(definer);
+      if (index >= 0) {
+        insn.setClassIndex(index);
+      }
+    }
+  }
+
+  /**
+   * Does final processing on this instance and gets the output as
+   * a {@link DalvInsnList}. Final processing consists of:
+   *
+   * <ul>
+   *   <li>optionally renumbering registers (to make room as needed for
+   *   expanded instructions)</li>
+   *   <li>picking a final opcode for each instruction</li>
+   *   <li>rewriting instructions, because of register number,
+   *   constant pool index, or branch target size issues</li>
+   *   <li>assigning final addresses</li>
+   * </ul>
+   *
+   * <p><b>Note:</b> This method may only be called once per instance
+   * of this class.</p>
+   *
+   * @return {@code non-null;} the output list
+   * @throws UnsupportedOperationException if this method has
+   * already been called
+   */
+  public DalvInsnList finishProcessingAndGetList() {
+    if (reservedCount >= 0) {
+      throw new UnsupportedOperationException("already processed");
+    }
+
+    Dop[] opcodes = makeOpcodesArray();
+    reserveRegisters(opcodes);
+    massageInstructions(opcodes);
+    assignAddressesAndFixBranches();
+
+    return DalvInsnList.makeImmutable(insns, reservedCount + unreservedRegCount);
+  }
+
+  /**
+   * Helper for {@link #finishProcessingAndGetList}, which extracts
+   * the opcode out of each instruction into a separate array, to be
+   * further manipulated as things progress.
+   *
+   * @return {@code non-null;} the array of opcodes
+   */
+  private Dop[] makeOpcodesArray() {
+    int size = insns.size();
+    Dop[] result = new Dop[size];
+
+    for (int i = 0; i < size; i++) {
+      result[i] = insns.get(i).getOpcode();
+    }
+
+    return result;
+  }
+
+  /**
+   * Helper for {@link #finishProcessingAndGetList}, which figures
+   * out how many reserved registers are required and then reserving
+   * them. It also updates the given {@code opcodes} array so
+   * as to avoid extra work when constructing the massaged
+   * instruction list.
+   *
+   * @param opcodes {@code non-null;} array of per-instruction
+   * opcode selections
+   */
+  private void reserveRegisters(Dop[] opcodes) {
+    int oldReservedCount = (reservedCount < 0) ? 0 : reservedCount;
+
+    /*
+     * Call calculateReservedCount() and then perform register
+     * reservation, repeatedly until no new reservations happen.
+     */
+    for (;;) {
+      int newReservedCount = calculateReservedCount(opcodes);
+      if (oldReservedCount >= newReservedCount) {
+        break;
+      }
+
+      int reservedDifference = newReservedCount - oldReservedCount;
+      int size = insns.size();
+
+      for (int i = 0; i < size; i++) {
+        /*
+         * CodeAddress instance identity is used to link
+         * TargetInsns to their targets, so it is
+         * inappropriate to make replacements, and they don't
+         * have registers in any case. Hence, the instanceof
+         * test below.
+         */
+        DalvInsn insn = insns.get(i);
+        if (!(insn instanceof CodeAddress)) {
+          /*
+           * No need to call this.set() since the format and
+           * other info are the same.
+           */
+          insns.set(i, insn.withRegisterOffset(reservedDifference));
         }
+      }
 
-        if (! hasAnyLocalInfo) {
-            if (hasLocalInfo(insn)) {
-                hasAnyLocalInfo = true;
-            }
-        }
+      oldReservedCount = newReservedCount;
     }
 
-    /**
-     * Reverses a branch which is buried a given number of instructions
-     * backward in the output. It is illegal to call this unless the
-     * indicated instruction really is a reversible branch.
-     *
-     * @param which how many instructions back to find the branch;
-     * {@code 0} is the most recently added instruction,
-     * {@code 1} is the instruction before that, etc.
-     * @param newTarget {@code non-null;} the new target for the
-     * reversed branch
-     */
-    public void reverseBranch(int which, CodeAddress newTarget) {
-        int size = insns.size();
-        int index = size - which - 1;
-        TargetInsn targetInsn;
+    reservedCount = oldReservedCount;
+  }
 
+  /**
+   * Helper for {@link #reserveRegisters}, which does one
+   * pass over the instructions, calculating the number of
+   * registers that need to be reserved. It also updates the
+   * {@code opcodes} list to help avoid extra work in future
+   * register reservation passes.
+   *
+   * @param opcodes {@code non-null;} array of per-instruction
+   * opcode selections
+   * @return {@code >= 0;} the count of reserved registers
+   */
+  private int calculateReservedCount(Dop[] opcodes) {
+    int size = insns.size();
+
+    /*
+     * Potential new value of reservedCount, which gets updated in the
+     * following loop. It starts out with the existing reservedCount
+     * and gets increased if it turns out that additional registers
+     * need to be reserved.
+     */
+    int newReservedCount = reservedCount;
+
+    for (int i = 0; i < size; i++) {
+      DalvInsn insn = insns.get(i);
+      Dop originalOpcode = opcodes[i];
+      Dop newOpcode = findOpcodeForInsn(insn, originalOpcode);
+
+      if (newOpcode == null) {
+        /*
+         * The instruction will need to be expanded, so find the
+         * expanded opcode and reserve registers for it.
+         */
+        Dop expandedOp = findExpandedOpcodeForInsn(insn);
+        BitSet compatRegs = expandedOp.getFormat().compatibleRegs(insn);
+        int reserve = insn.getMinimumRegisterRequirement(compatRegs);
+        if (reserve > newReservedCount) {
+          newReservedCount = reserve;
+        }
+      } else if (originalOpcode == newOpcode) {
+        continue;
+      }
+
+      opcodes[i] = newOpcode;
+    }
+
+    return newReservedCount;
+  }
+
+  /**
+   * Attempts to fit the given instruction into a specific opcode,
+   * returning the opcode whose format that the instruction fits
+   * into or {@code null} to indicate that the instruction will need
+   * to be expanded. This fitting process starts with the given
+   * opcode as a first "best guess" and then pessimizes from there
+   * if necessary.
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @param guess {@code null-ok;} the current guess as to the best
+   * opcode; {@code null} means that no simple opcode fits
+   * @return {@code null-ok;} a possibly-different opcode; either a
+   * {@code non-null} good fit or {@code null} to indicate that no
+   * simple opcode fits
+   */
+  private Dop findOpcodeForInsn(DalvInsn insn, Dop guess) {
+    /*
+     * Note: The initial guess might be null, meaning that an
+     * earlier call to this method already determined that there
+     * was no possible simple opcode fit.
+     */
+
+while (guess != null) {
+      if (guess.getFormat().isCompatible(insn)) {
+        /*
+         * Don't break out for const_string to generate jumbo version
+         * when option is enabled.
+         */
+        if (!dexOptions.forceJumbo || guess.getOpcode() != Opcodes.CONST_STRING) {
+          break;
+        }
+      }
+
+      guess = Dops.getNextOrNull(guess, dexOptions);
+    }
+
+    return guess;
+  }
+
+  /**
+   * Finds the proper opcode for the given instruction, ignoring
+   * register constraints.
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @return {@code non-null;} the opcode that fits
+   */
+  private Dop findExpandedOpcodeForInsn(DalvInsn insn) {
+    Dop result = findOpcodeForInsn(insn.getLowRegVersion(), insn.getOpcode());
+    if (result == null) {
+      throw new DexException("No expanded opcode for " + insn);
+    }
+    return result;
+  }
+
+  /**
+   * Helper for {@link #finishProcessingAndGetList}, which goes
+   * through each instruction in the output, making sure its opcode
+   * can accomodate its arguments. In cases where the opcode is
+   * unable to do so, this replaces the instruction with a larger
+   * instruction with identical semantics that <i>will</i> work.
+   *
+   * <p>This method may also reserve a number of low-numbered
+   * registers, renumbering the instructions' original registers, in
+   * order to have register space available in which to move
+   * very-high registers when expanding instructions into
+   * multi-instruction sequences. This expansion is done when no
+   * simple instruction format can be found for a given instruction that
+   * is able to accomodate that instruction's registers.</p>
+   *
+   * <p>This method ignores issues of branch target size, since
+   * final addresses aren't known at the point that this method is
+   * called.</p>
+   *
+   * @param opcodes {@code non-null;} array of per-instruction
+   * opcode selections
+   */
+  private void massageInstructions(Dop[] opcodes) {
+    if (reservedCount == 0) {
+      /*
+       * The easy common case: No registers were reserved, so we
+       * merely need to replace any instructions whose format
+       * (and hence whose opcode) changed during the reservation
+       * pass, but all instructions will stay at their original
+       * indices, and the instruction list doesn't grow.
+       */
+      int size = insns.size();
+
+      for (int i = 0; i < size; i++) {
+        DalvInsn insn = insns.get(i);
+        Dop originalOpcode = insn.getOpcode();
+        Dop currentOpcode = opcodes[i];
+
+        if (originalOpcode != currentOpcode) {
+          insns.set(i, insn.withOpcode(currentOpcode));
+        }
+      }
+    } else {
+      /*
+       * The difficult uncommon case: Some instructions have to be
+       * expanded to deal with high registers.
+       */
+      insns = performExpansion(opcodes);
+    }
+  }
+
+  /**
+   * Helper for {@link #massageInstructions}, which constructs a
+   * replacement list, where each {link DalvInsn} instance that
+   * couldn't be represented simply (due to register representation
+   * problems) is expanded into a series of instances that together
+   * perform the proper function.
+   *
+   * @param opcodes {@code non-null;} array of per-instruction
+   * opcode selections
+   * @return {@code non-null;} the replacement list
+   */
+  private ArrayList<DalvInsn> performExpansion(Dop[] opcodes) {
+    int size = insns.size();
+    ArrayList<DalvInsn> result = new ArrayList<DalvInsn>(size * 2);
+
+    ArrayList<CodeAddress> closelyBoundAddresses = new ArrayList<CodeAddress>();
+
+    for (int i = 0; i < size; i++) {
+      DalvInsn insn = insns.get(i);
+      Dop originalOpcode = insn.getOpcode();
+      Dop currentOpcode = opcodes[i];
+      DalvInsn prefix;
+      DalvInsn suffix;
+
+      if (currentOpcode != null) {
+        // No expansion is necessary.
+        prefix = null;
+        suffix = null;
+      } else {
+        // Expansion is required.
+        currentOpcode = findExpandedOpcodeForInsn(insn);
+        BitSet compatRegs = currentOpcode.getFormat().compatibleRegs(insn);
+        prefix = insn.expandedPrefix(compatRegs);
+        suffix = insn.expandedSuffix(compatRegs);
+
+        // Expand necessary registers to fit the new format
+        insn = insn.expandedVersion(compatRegs);
+      }
+
+      if (insn instanceof CodeAddress) {
+        // If we have a closely bound address, don't add it yet,
+        // because we need to add it after the prefix for the
+        // instruction it is bound to.
+        if (((CodeAddress) insn).getBindsClosely()) {
+          closelyBoundAddresses.add((CodeAddress) insn);
+          continue;
+        }
+      }
+
+      if (prefix != null) {
+        result.add(prefix);
+      }
+
+      // Add any pending closely bound addresses
+      if (!(insn instanceof ZeroSizeInsn) && closelyBoundAddresses.size() > 0) {
+        for (CodeAddress codeAddress : closelyBoundAddresses) {
+          result.add(codeAddress);
+        }
+        closelyBoundAddresses.clear();
+      }
+
+      if (currentOpcode != originalOpcode) {
+        insn = insn.withOpcode(currentOpcode);
+      }
+      result.add(insn);
+
+      if (suffix != null) {
+        result.add(suffix);
+      }
+    }
+
+    return result;
+  }
+
+  /**
+   * Helper for {@link #finishProcessingAndGetList}, which assigns
+   * addresses to each instruction, possibly rewriting branches to
+   * fix ones that wouldn't otherwise be able to reach their
+   * targets.
+   */
+  private void assignAddressesAndFixBranches() {
+    for (;;) {
+      assignAddresses();
+      if (!fixBranches()) {
+        break;
+      }
+    }
+  }
+
+  /**
+   * Helper for {@link #assignAddressesAndFixBranches}, which
+   * assigns an address to each instruction, in order.
+   */
+  private void assignAddresses() {
+    int address = 0;
+    int size = insns.size();
+
+    for (int i = 0; i < size; i++) {
+      DalvInsn insn = insns.get(i);
+      insn.setAddress(address);
+      address += insn.codeSize();
+    }
+  }
+
+  /**
+   * Helper for {@link #assignAddressesAndFixBranches}, which checks
+   * the branch target size requirement of each branch instruction
+   * to make sure it fits. For instructions that don't fit, this
+   * rewrites them to use a {@code goto} of some sort. In the
+   * case of a conditional branch that doesn't fit, the sense of the
+   * test is reversed in order to branch around a {@code goto}
+   * to the original target.
+   *
+   * @return whether any branches had to be fixed
+   */
+  private boolean fixBranches() {
+    int size = insns.size();
+    boolean anyFixed = false;
+
+    for (int i = 0; i < size; i++) {
+      DalvInsn insn = insns.get(i);
+      if (!(insn instanceof TargetInsn)) {
+        // This loop only needs to inspect TargetInsns.
+        continue;
+      }
+
+      Dop opcode = insn.getOpcode();
+      TargetInsn target = (TargetInsn) insn;
+
+      if (opcode.getFormat().branchFits(target)) {
+        continue;
+      }
+
+      if (opcode.getFamily() == Opcodes.GOTO) {
+        // It is a goto; widen it if possible.
+        opcode = findOpcodeForInsn(insn, opcode);
+        if (opcode == null) {
+          /*
+           * The branch is already maximally large. This should
+           * only be possible if a method somehow manages to have
+           * more than 2^31 code units.
+           */
+          throw new UnsupportedOperationException("method too long");
+        }
+        insns.set(i, insn.withOpcode(opcode));
+      } else {
+        /*
+         * It is a conditional: Reverse its sense, and arrange for
+         * it to branch around an absolute goto to the original
+         * branch target.
+         *
+         * Note: An invariant of the list being processed is
+         * that every TargetInsn is followed by a CodeAddress.
+         * Hence, it is always safe to get the next element
+         * after a TargetInsn and cast it to CodeAddress, as
+         * is happening a few lines down.
+         *
+         * Also note: Size gets incremented by one here, as we
+         * have -- in the net -- added one additional element
+         * to the list, so we increment i to match. The added
+         * and changed elements will be inspected by a repeat
+         * call to this method after this invocation returns.
+         */
+        CodeAddress newTarget;
         try {
-            targetInsn = (TargetInsn) insns.get(index);
+          newTarget = (CodeAddress) insns.get(i + 1);
         } catch (IndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("too few instructions");
+          // The TargetInsn / CodeAddress invariant was violated.
+          throw new IllegalStateException("unpaired TargetInsn (dangling)");
         } catch (ClassCastException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("non-reversible instruction");
+          // The TargetInsn / CodeAddress invariant was violated.
+          throw new IllegalStateException("unpaired TargetInsn");
         }
+        TargetInsn gotoInsn = new TargetInsn(Dops.GOTO, target.getPosition(),
+            RegisterSpecList.EMPTY, target.getTarget());
+        insns.set(i, gotoInsn);
+        insns.add(i, target.withNewTargetAndReversed(newTarget));
+        size++;
+        i++;
+      }
 
-        /*
-         * No need to call this.set(), since the format and other info
-         * are the same.
-         */
-        insns.set(index, targetInsn.withNewTargetAndReversed(newTarget));
+      anyFixed = true;
     }
 
-    /**
-     * Assigns indices in all instructions that need them, using the
-     * given callback to perform lookups. This should be called before
-     * calling {@link #finishProcessingAndGetList}.
-     *
-     * @param callback {@code non-null;} callback object
-     */
-    public void assignIndices(DalvCode.AssignIndicesCallback callback) {
-        for (DalvInsn insn : insns) {
-            if (insn instanceof CstInsn) {
-                assignIndices((CstInsn) insn, callback);
-            }
-        }
-    }
-
-    /**
-     * Helper for {@link #assignIndices} which does assignment for one
-     * instruction.
-     *
-     * @param insn {@code non-null;} the instruction
-     * @param callback {@code non-null;} the callback
-     */
-    private static void assignIndices(CstInsn insn,
-            DalvCode.AssignIndicesCallback callback) {
-        Constant cst = insn.getConstant();
-        int index = callback.getIndex(cst);
-
-        if (index >= 0) {
-            insn.setIndex(index);
-        }
-
-        if (cst instanceof CstMemberRef) {
-            CstMemberRef member = (CstMemberRef) cst;
-            CstType definer = member.getDefiningClass();
-            index = callback.getIndex(definer);
-            if (index >= 0) {
-                insn.setClassIndex(index);
-            }
-        }
-    }
-
-    /**
-     * Does final processing on this instance and gets the output as
-     * a {@link DalvInsnList}. Final processing consists of:
-     *
-     * <ul>
-     *   <li>optionally renumbering registers (to make room as needed for
-     *   expanded instructions)</li>
-     *   <li>picking a final opcode for each instruction</li>
-     *   <li>rewriting instructions, because of register number,
-     *   constant pool index, or branch target size issues</li>
-     *   <li>assigning final addresses</li>
-     * </ul>
-     *
-     * <p><b>Note:</b> This method may only be called once per instance
-     * of this class.</p>
-     *
-     * @return {@code non-null;} the output list
-     * @throws UnsupportedOperationException if this method has
-     * already been called
-     */
-    public DalvInsnList finishProcessingAndGetList() {
-        if (reservedCount >= 0) {
-            throw new UnsupportedOperationException("already processed");
-        }
-
-        Dop[] opcodes = makeOpcodesArray();
-        reserveRegisters(opcodes);
-        massageInstructions(opcodes);
-        assignAddressesAndFixBranches();
-
-        return DalvInsnList.makeImmutable(insns,
-                reservedCount + unreservedRegCount);
-    }
-
-    /**
-     * Helper for {@link #finishProcessingAndGetList}, which extracts
-     * the opcode out of each instruction into a separate array, to be
-     * further manipulated as things progress.
-     *
-     * @return {@code non-null;} the array of opcodes
-     */
-    private Dop[] makeOpcodesArray() {
-        int size = insns.size();
-        Dop[] result = new Dop[size];
-
-        for (int i = 0; i < size; i++) {
-            result[i] = insns.get(i).getOpcode();
-        }
-
-        return result;
-    }
-
-    /**
-     * Helper for {@link #finishProcessingAndGetList}, which figures
-     * out how many reserved registers are required and then reserving
-     * them. It also updates the given {@code opcodes} array so
-     * as to avoid extra work when constructing the massaged
-     * instruction list.
-     *
-     * @param opcodes {@code non-null;} array of per-instruction
-     * opcode selections
-     */
-    private void reserveRegisters(Dop[] opcodes) {
-        int oldReservedCount = (reservedCount < 0) ? 0 : reservedCount;
-
-        /*
-         * Call calculateReservedCount() and then perform register
-         * reservation, repeatedly until no new reservations happen.
-         */
-        for (;;) {
-            int newReservedCount = calculateReservedCount(opcodes);
-            if (oldReservedCount >= newReservedCount) {
-                break;
-            }
-
-            int reservedDifference = newReservedCount - oldReservedCount;
-            int size = insns.size();
-
-            for (int i = 0; i < size; i++) {
-                /*
-                 * CodeAddress instance identity is used to link
-                 * TargetInsns to their targets, so it is
-                 * inappropriate to make replacements, and they don't
-                 * have registers in any case. Hence, the instanceof
-                 * test below.
-                 */
-                DalvInsn insn = insns.get(i);
-                if (!(insn instanceof CodeAddress)) {
-                    /*
-                     * No need to call this.set() since the format and
-                     * other info are the same.
-                     */
-                    insns.set(i, insn.withRegisterOffset(reservedDifference));
-                }
-            }
-
-            oldReservedCount = newReservedCount;
-        }
-
-        reservedCount = oldReservedCount;
-    }
-
-    /**
-     * Helper for {@link #reserveRegisters}, which does one
-     * pass over the instructions, calculating the number of
-     * registers that need to be reserved. It also updates the
-     * {@code opcodes} list to help avoid extra work in future
-     * register reservation passes.
-     *
-     * @param opcodes {@code non-null;} array of per-instruction
-     * opcode selections
-     * @return {@code >= 0;} the count of reserved registers
-     */
-    private int calculateReservedCount(Dop[] opcodes) {
-        int size = insns.size();
-
-        /*
-         * Potential new value of reservedCount, which gets updated in the
-         * following loop. It starts out with the existing reservedCount
-         * and gets increased if it turns out that additional registers
-         * need to be reserved.
-         */
-        int newReservedCount = reservedCount;
-
-        for (int i = 0; i < size; i++) {
-            DalvInsn insn = insns.get(i);
-            Dop originalOpcode = opcodes[i];
-            Dop newOpcode = findOpcodeForInsn(insn, originalOpcode);
-
-            if (newOpcode == null) {
-                /*
-                 * The instruction will need to be expanded, so find the
-                 * expanded opcode and reserve registers for it.
-                 */
-                Dop expandedOp = findExpandedOpcodeForInsn(insn);
-                BitSet compatRegs = expandedOp.getFormat().compatibleRegs(insn);
-                int reserve = insn.getMinimumRegisterRequirement(compatRegs);
-                if (reserve > newReservedCount) {
-                    newReservedCount = reserve;
-                }
-            } else if (originalOpcode == newOpcode) {
-                continue;
-            }
-
-            opcodes[i] = newOpcode;
-        }
-
-        return newReservedCount;
-    }
-
-    /**
-     * Attempts to fit the given instruction into a specific opcode,
-     * returning the opcode whose format that the instruction fits
-     * into or {@code null} to indicate that the instruction will need
-     * to be expanded. This fitting process starts with the given
-     * opcode as a first "best guess" and then pessimizes from there
-     * if necessary.
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @param guess {@code null-ok;} the current guess as to the best
-     * opcode; {@code null} means that no simple opcode fits
-     * @return {@code null-ok;} a possibly-different opcode; either a
-     * {@code non-null} good fit or {@code null} to indicate that no
-     * simple opcode fits
-     */
-    private Dop findOpcodeForInsn(DalvInsn insn, Dop guess) {
-        /*
-         * Note: The initial guess might be null, meaning that an
-         * earlier call to this method already determined that there
-         * was no possible simple opcode fit.
-         */
-
-        while (guess != null) {
-            if (guess.getFormat().isCompatible(insn)) {
-                /*
-                 * Don't break out for const_string to generate jumbo version
-                 * when option is enabled.
-                 */
-                if (!dexOptions.forceJumbo ||
-                    guess.getOpcode() != Opcodes.CONST_STRING) {
-                    break;
-                }
-            }
-
-            guess = Dops.getNextOrNull(guess, dexOptions);
-        }
-
-        return guess;
-    }
-
-    /**
-     * Finds the proper opcode for the given instruction, ignoring
-     * register constraints.
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @return {@code non-null;} the opcode that fits
-     */
-    private Dop findExpandedOpcodeForInsn(DalvInsn insn) {
-        Dop result = findOpcodeForInsn(insn.getLowRegVersion(), insn.getOpcode());
-        if (result == null) {
-            throw new DexException("No expanded opcode for " + insn);
-        }
-        return result;
-    }
-
-    /**
-     * Helper for {@link #finishProcessingAndGetList}, which goes
-     * through each instruction in the output, making sure its opcode
-     * can accomodate its arguments. In cases where the opcode is
-     * unable to do so, this replaces the instruction with a larger
-     * instruction with identical semantics that <i>will</i> work.
-     *
-     * <p>This method may also reserve a number of low-numbered
-     * registers, renumbering the instructions' original registers, in
-     * order to have register space available in which to move
-     * very-high registers when expanding instructions into
-     * multi-instruction sequences. This expansion is done when no
-     * simple instruction format can be found for a given instruction that
-     * is able to accomodate that instruction's registers.</p>
-     *
-     * <p>This method ignores issues of branch target size, since
-     * final addresses aren't known at the point that this method is
-     * called.</p>
-     *
-     * @param opcodes {@code non-null;} array of per-instruction
-     * opcode selections
-     */
-    private void massageInstructions(Dop[] opcodes) {
-        if (reservedCount == 0) {
-            /*
-             * The easy common case: No registers were reserved, so we
-             * merely need to replace any instructions whose format
-             * (and hence whose opcode) changed during the reservation
-             * pass, but all instructions will stay at their original
-             * indices, and the instruction list doesn't grow.
-             */
-            int size = insns.size();
-
-            for (int i = 0; i < size; i++) {
-                DalvInsn insn = insns.get(i);
-                Dop originalOpcode = insn.getOpcode();
-                Dop currentOpcode = opcodes[i];
-
-                if (originalOpcode != currentOpcode) {
-                    insns.set(i, insn.withOpcode(currentOpcode));
-                }
-            }
-        } else {
-            /*
-             * The difficult uncommon case: Some instructions have to be
-             * expanded to deal with high registers.
-             */
-            insns = performExpansion(opcodes);
-        }
-    }
-
-    /**
-     * Helper for {@link #massageInstructions}, which constructs a
-     * replacement list, where each {link DalvInsn} instance that
-     * couldn't be represented simply (due to register representation
-     * problems) is expanded into a series of instances that together
-     * perform the proper function.
-     *
-     * @param opcodes {@code non-null;} array of per-instruction
-     * opcode selections
-     * @return {@code non-null;} the replacement list
-     */
-    private ArrayList<DalvInsn> performExpansion(Dop[] opcodes) {
-        int size = insns.size();
-        ArrayList<DalvInsn> result = new ArrayList<DalvInsn>(size * 2);
-
-        ArrayList<CodeAddress> closelyBoundAddresses = new ArrayList<CodeAddress>();
-
-        for (int i = 0; i < size; i++) {
-            DalvInsn insn = insns.get(i);
-            Dop originalOpcode = insn.getOpcode();
-            Dop currentOpcode = opcodes[i];
-            DalvInsn prefix;
-            DalvInsn suffix;
-
-            if (currentOpcode != null) {
-                // No expansion is necessary.
-                prefix = null;
-                suffix = null;
-            } else {
-                // Expansion is required.
-                currentOpcode = findExpandedOpcodeForInsn(insn);
-                BitSet compatRegs =
-                    currentOpcode.getFormat().compatibleRegs(insn);
-                prefix = insn.expandedPrefix(compatRegs);
-                suffix = insn.expandedSuffix(compatRegs);
-
-                // Expand necessary registers to fit the new format
-                insn = insn.expandedVersion(compatRegs);
-            }
-
-            if (insn instanceof CodeAddress) {
-                // If we have a closely bound address, don't add it yet,
-                // because we need to add it after the prefix for the
-                // instruction it is bound to.
-                if (((CodeAddress) insn).getBindsClosely()) {
-                    closelyBoundAddresses.add((CodeAddress)insn);
-                    continue;
-                }
-            }
-
-            if (prefix != null) {
-                result.add(prefix);
-            }
-
-            // Add any pending closely bound addresses
-            if (!(insn instanceof ZeroSizeInsn) && closelyBoundAddresses.size() > 0) {
-                for (CodeAddress codeAddress: closelyBoundAddresses) {
-                    result.add(codeAddress);
-                }
-                closelyBoundAddresses.clear();
-            }
-
-            if (currentOpcode != originalOpcode) {
-                insn = insn.withOpcode(currentOpcode);
-            }
-            result.add(insn);
-
-            if (suffix != null) {
-                result.add(suffix);
-            }
-        }
-
-        return result;
-    }
-
-    /**
-     * Helper for {@link #finishProcessingAndGetList}, which assigns
-     * addresses to each instruction, possibly rewriting branches to
-     * fix ones that wouldn't otherwise be able to reach their
-     * targets.
-     */
-    private void assignAddressesAndFixBranches() {
-        for (;;) {
-            assignAddresses();
-            if (!fixBranches()) {
-                break;
-            }
-        }
-    }
-
-    /**
-     * Helper for {@link #assignAddressesAndFixBranches}, which
-     * assigns an address to each instruction, in order.
-     */
-    private void assignAddresses() {
-        int address = 0;
-        int size = insns.size();
-
-        for (int i = 0; i < size; i++) {
-            DalvInsn insn = insns.get(i);
-            insn.setAddress(address);
-            address += insn.codeSize();
-        }
-    }
-
-    /**
-     * Helper for {@link #assignAddressesAndFixBranches}, which checks
-     * the branch target size requirement of each branch instruction
-     * to make sure it fits. For instructions that don't fit, this
-     * rewrites them to use a {@code goto} of some sort. In the
-     * case of a conditional branch that doesn't fit, the sense of the
-     * test is reversed in order to branch around a {@code goto}
-     * to the original target.
-     *
-     * @return whether any branches had to be fixed
-     */
-    private boolean fixBranches() {
-        int size = insns.size();
-        boolean anyFixed = false;
-
-        for (int i = 0; i < size; i++) {
-            DalvInsn insn = insns.get(i);
-            if (!(insn instanceof TargetInsn)) {
-                // This loop only needs to inspect TargetInsns.
-                continue;
-            }
-
-            Dop opcode = insn.getOpcode();
-            TargetInsn target = (TargetInsn) insn;
-
-            if (opcode.getFormat().branchFits(target)) {
-                continue;
-            }
-
-            if (opcode.getFamily() == Opcodes.GOTO) {
-                // It is a goto; widen it if possible.
-                opcode = findOpcodeForInsn(insn, opcode);
-                if (opcode == null) {
-                    /*
-                     * The branch is already maximally large. This should
-                     * only be possible if a method somehow manages to have
-                     * more than 2^31 code units.
-                     */
-                    throw new UnsupportedOperationException("method too long");
-                }
-                insns.set(i, insn.withOpcode(opcode));
-            } else {
-                /*
-                 * It is a conditional: Reverse its sense, and arrange for
-                 * it to branch around an absolute goto to the original
-                 * branch target.
-                 *
-                 * Note: An invariant of the list being processed is
-                 * that every TargetInsn is followed by a CodeAddress.
-                 * Hence, it is always safe to get the next element
-                 * after a TargetInsn and cast it to CodeAddress, as
-                 * is happening a few lines down.
-                 *
-                 * Also note: Size gets incremented by one here, as we
-                 * have -- in the net -- added one additional element
-                 * to the list, so we increment i to match. The added
-                 * and changed elements will be inspected by a repeat
-                 * call to this method after this invocation returns.
-                 */
-                CodeAddress newTarget;
-                try {
-                    newTarget = (CodeAddress) insns.get(i + 1);
-                } catch (IndexOutOfBoundsException ex) {
-                    // The TargetInsn / CodeAddress invariant was violated.
-                    throw new IllegalStateException(
-                            "unpaired TargetInsn (dangling)");
-                } catch (ClassCastException ex) {
-                    // The TargetInsn / CodeAddress invariant was violated.
-                    throw new IllegalStateException("unpaired TargetInsn");
-                }
-                TargetInsn gotoInsn =
-                    new TargetInsn(Dops.GOTO, target.getPosition(),
-                            RegisterSpecList.EMPTY, target.getTarget());
-                insns.set(i, gotoInsn);
-                insns.add(i, target.withNewTargetAndReversed(newTarget));
-                size++;
-                i++;
-            }
-
-            anyFixed = true;
-        }
-
-        return anyFixed;
-    }
+    return anyFixed;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/PositionList.java b/dx/src/com/android/jack/dx/dex/code/PositionList.java
index 75432d8..9b4eedb 100644
--- a/dx/src/com/android/jack/dx/dex/code/PositionList.java
+++ b/dx/src/com/android/jack/dx/dex/code/PositionList.java
@@ -24,169 +24,169 @@
  * method to extract an instance out of a {@link DalvInsnList}.
  */
 public final class PositionList extends FixedSizeList {
-    /** {@code non-null;} empty instance */
-    public static final PositionList EMPTY = new PositionList(0);
+  /** {@code non-null;} empty instance */
+  public static final PositionList EMPTY = new PositionList(0);
+
+  /**
+   * constant for {@link #make} to indicate that no actual position
+   * information should be returned
+   */
+  public static final int NONE = 1;
+
+  /**
+   * constant for {@link #make} to indicate that only line number
+   * transitions should be returned
+   */
+  public static final int LINES = 2;
+
+  /**
+   * constant for {@link #make} to indicate that only "important" position
+   * information should be returned. This includes block starts and
+   * instructions that might throw.
+   */
+  public static final int IMPORTANT = 3;
+
+  /**
+   * Extracts and returns the source position information out of an
+   * instruction list.
+   *
+   * @param insns {@code non-null;} instructions to convert
+   * @param howMuch how much information should be included; one of the
+   * static constants defined by this class
+   * @return {@code non-null;} the positions list
+   */
+  public static PositionList make(DalvInsnList insns, int howMuch) {
+    switch (howMuch) {
+      case NONE: {
+        return EMPTY;
+      }
+      case LINES:
+      case IMPORTANT: {
+        // Valid.
+        break;
+      }
+      default: {
+        throw new IllegalArgumentException("bogus howMuch");
+      }
+    }
+
+    SourcePosition noInfo = SourcePosition.NO_INFO;
+    SourcePosition cur = noInfo;
+    int sz = insns.size();
+    PositionList.Entry[] arr = new PositionList.Entry[sz];
+    boolean lastWasTarget = false;
+    int at = 0;
+
+    for (int i = 0; i < sz; i++) {
+      DalvInsn insn = insns.get(i);
+
+      if (insn instanceof CodeAddress) {
+        lastWasTarget = true;;
+        continue;
+      }
+
+      SourcePosition pos = insn.getPosition();
+
+      if (pos.equals(noInfo) || pos.sameLine(cur)) {
+        continue;
+      }
+
+      if ((howMuch == IMPORTANT) && !lastWasTarget) {
+        continue;
+      }
+
+      cur = pos;
+      arr[at] = new PositionList.Entry(insn.getAddress(), pos);
+      at++;
+
+      lastWasTarget = false;
+    }
+
+    PositionList result = new PositionList(at);
+    for (int i = 0; i < at; i++) {
+      result.set(i, arr[i]);
+    }
+
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size {@code >= 0;} the size of the list
+   */
+  public PositionList(int size) {
+    super(size);
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Entry get(int n) {
+    return (Entry) get0(n);
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param entry {@code non-null;} the entry to set at {@code n}
+   */
+  public void set(int n, Entry entry) {
+    set0(n, entry);
+  }
+
+  /**
+   * Entry in a position list.
+   */
+  public static class Entry {
+    /** {@code >= 0;} address of this entry */
+    private final int address;
+
+    /** {@code non-null;} corresponding source position information */
+    private final SourcePosition position;
 
     /**
-     * constant for {@link #make} to indicate that no actual position
-     * information should be returned
-     */
-    public static final int NONE = 1;
-
-    /**
-     * constant for {@link #make} to indicate that only line number
-     * transitions should be returned
-     */
-    public static final int LINES = 2;
-
-    /**
-     * constant for {@link #make} to indicate that only "important" position
-     * information should be returned. This includes block starts and
-     * instructions that might throw.
-     */
-    public static final int IMPORTANT = 3;
-
-    /**
-     * Extracts and returns the source position information out of an
-     * instruction list.
+     * Constructs an instance.
      *
-     * @param insns {@code non-null;} instructions to convert
-     * @param howMuch how much information should be included; one of the
-     * static constants defined by this class
-     * @return {@code non-null;} the positions list
+     * @param address {@code >= 0;} address of this entry
+     * @param position {@code non-null;} corresponding source position information
      */
-    public static PositionList make(DalvInsnList insns, int howMuch) {
-        switch (howMuch) {
-            case NONE: {
-                return EMPTY;
-            }
-            case LINES:
-            case IMPORTANT: {
-                // Valid.
-                break;
-            }
-            default: {
-                throw new IllegalArgumentException("bogus howMuch");
-            }
-        }
+    public Entry(int address, SourcePosition position) {
+      if (address < 0) {
+        throw new IllegalArgumentException("address < 0");
+      }
 
-        SourcePosition noInfo = SourcePosition.NO_INFO;
-        SourcePosition cur = noInfo;
-        int sz = insns.size();
-        PositionList.Entry[] arr = new PositionList.Entry[sz];
-        boolean lastWasTarget = false;
-        int at = 0;
+      if (position == null) {
+        throw new NullPointerException("position == null");
+      }
 
-        for (int i = 0; i < sz; i++) {
-            DalvInsn insn = insns.get(i);
-
-            if (insn instanceof CodeAddress) {
-                lastWasTarget = true;;
-                continue;
-            }
-
-            SourcePosition pos = insn.getPosition();
-
-            if (pos.equals(noInfo) || pos.sameLine(cur)) {
-                continue;
-            }
-
-            if ((howMuch == IMPORTANT) && !lastWasTarget) {
-                continue;
-            }
-
-            cur = pos;
-            arr[at] = new PositionList.Entry(insn.getAddress(), pos);
-            at++;
-
-            lastWasTarget = false;
-        }
-
-        PositionList result = new PositionList(at);
-        for (int i = 0; i < at; i++) {
-            result.set(i, arr[i]);
-        }
-
-        result.setImmutable();
-        return result;
+      this.address = address;
+      this.position = position;
     }
 
     /**
-     * Constructs an instance. All indices initially contain {@code null}.
+     * Gets the address.
      *
-     * @param size {@code >= 0;} the size of the list
+     * @return {@code >= 0;} the address
      */
-    public PositionList(int size) {
-        super(size);
+    public int getAddress() {
+      return address;
     }
 
     /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
+     * Gets the source position information.
      *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
+     * @return {@code non-null;} the position information
      */
-    public Entry get(int n) {
-        return (Entry) get0(n);
+    public SourcePosition getPosition() {
+      return position;
     }
-
-    /**
-     * Sets the entry at the given index.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param entry {@code non-null;} the entry to set at {@code n}
-     */
-    public void set(int n, Entry entry) {
-        set0(n, entry);
-    }
-
-    /**
-     * Entry in a position list.
-     */
-    public static class Entry {
-        /** {@code >= 0;} address of this entry */
-        private final int address;
-
-        /** {@code non-null;} corresponding source position information */
-        private final SourcePosition position;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param address {@code >= 0;} address of this entry
-         * @param position {@code non-null;} corresponding source position information
-         */
-        public Entry (int address, SourcePosition position) {
-            if (address < 0) {
-                throw new IllegalArgumentException("address < 0");
-            }
-
-            if (position == null) {
-                throw new NullPointerException("position == null");
-            }
-
-            this.address = address;
-            this.position = position;
-        }
-
-        /**
-         * Gets the address.
-         *
-         * @return {@code >= 0;} the address
-         */
-        public int getAddress() {
-            return address;
-        }
-
-        /**
-         * Gets the source position information.
-         *
-         * @return {@code non-null;} the position information
-         */
-        public SourcePosition getPosition() {
-            return position;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/RopToDop.java b/dx/src/com/android/jack/dx/dex/code/RopToDop.java
index 6f64397..5ea7830 100644
--- a/dx/src/com/android/jack/dx/dex/code/RopToDop.java
+++ b/dx/src/com/android/jack/dx/dex/code/RopToDop.java
@@ -35,553 +35,578 @@
  * {@link Dop} instances.
  */
 public final class RopToDop {
-    /** {@code non-null;} map from all the common rops to dalvik opcodes */
-    private static final HashMap<Rop, Dop> MAP;
+  /** {@code non-null;} map from all the common rops to dalvik opcodes */
+  private static final HashMap<Rop, Dop> MAP;
 
-    /**
-     * This class is uninstantiable.
+  /**
+   * This class is uninstantiable.
+   */
+  private RopToDop() {
+    // This space intentionally left blank.
+  }
+
+  /*
+   * The following comment lists each opcode that should be considered
+   * the "head" of an opcode chain, in terms of the process of fitting
+   * an instruction's arguments to an actual opcode. This list is
+   * automatically generated and may be of use in double-checking the
+   * manually-generated static initialization code for this class.
+   *
+   * TODO(dx team): Make opcode-gen produce useful code in this case instead
+   * of just a comment.
+   */
+
+  // BEGIN(first-opcodes); GENERATED AUTOMATICALLY BY opcode-gen
+  //     Opcodes.NOP
+  //     Opcodes.MOVE
+  //     Opcodes.MOVE_WIDE
+  //     Opcodes.MOVE_OBJECT
+  //     Opcodes.MOVE_RESULT
+  //     Opcodes.MOVE_RESULT_WIDE
+  //     Opcodes.MOVE_RESULT_OBJECT
+  //     Opcodes.MOVE_EXCEPTION
+  //     Opcodes.RETURN_VOID
+  //     Opcodes.RETURN
+  //     Opcodes.RETURN_WIDE
+  //     Opcodes.RETURN_OBJECT
+  //     Opcodes.CONST_4
+  //     Opcodes.CONST_WIDE_16
+  //     Opcodes.CONST_STRING
+  //     Opcodes.CONST_CLASS
+  //     Opcodes.MONITOR_ENTER
+  //     Opcodes.MONITOR_EXIT
+  //     Opcodes.CHECK_CAST
+  //     Opcodes.INSTANCE_OF
+  //     Opcodes.ARRAY_LENGTH
+  //     Opcodes.NEW_INSTANCE
+  //     Opcodes.NEW_ARRAY
+  //     Opcodes.FILLED_NEW_ARRAY
+  //     Opcodes.FILL_ARRAY_DATA
+  //     Opcodes.THROW
+  //     Opcodes.GOTO
+  //     Opcodes.PACKED_SWITCH
+  //     Opcodes.SPARSE_SWITCH
+  //     Opcodes.CMPL_FLOAT
+  //     Opcodes.CMPG_FLOAT
+  //     Opcodes.CMPL_DOUBLE
+  //     Opcodes.CMPG_DOUBLE
+  //     Opcodes.CMP_LONG
+  //     Opcodes.IF_EQ
+  //     Opcodes.IF_NE
+  //     Opcodes.IF_LT
+  //     Opcodes.IF_GE
+  //     Opcodes.IF_GT
+  //     Opcodes.IF_LE
+  //     Opcodes.IF_EQZ
+  //     Opcodes.IF_NEZ
+  //     Opcodes.IF_LTZ
+  //     Opcodes.IF_GEZ
+  //     Opcodes.IF_GTZ
+  //     Opcodes.IF_LEZ
+  //     Opcodes.AGET
+  //     Opcodes.AGET_WIDE
+  //     Opcodes.AGET_OBJECT
+  //     Opcodes.AGET_BOOLEAN
+  //     Opcodes.AGET_BYTE
+  //     Opcodes.AGET_CHAR
+  //     Opcodes.AGET_SHORT
+  //     Opcodes.APUT
+  //     Opcodes.APUT_WIDE
+  //     Opcodes.APUT_OBJECT
+  //     Opcodes.APUT_BOOLEAN
+  //     Opcodes.APUT_BYTE
+  //     Opcodes.APUT_CHAR
+  //     Opcodes.APUT_SHORT
+  //     Opcodes.IGET
+  //     Opcodes.IGET_WIDE
+  //     Opcodes.IGET_OBJECT
+  //     Opcodes.IGET_BOOLEAN
+  //     Opcodes.IGET_BYTE
+  //     Opcodes.IGET_CHAR
+  //     Opcodes.IGET_SHORT
+  //     Opcodes.IPUT
+  //     Opcodes.IPUT_WIDE
+  //     Opcodes.IPUT_OBJECT
+  //     Opcodes.IPUT_BOOLEAN
+  //     Opcodes.IPUT_BYTE
+  //     Opcodes.IPUT_CHAR
+  //     Opcodes.IPUT_SHORT
+  //     Opcodes.SGET
+  //     Opcodes.SGET_WIDE
+  //     Opcodes.SGET_OBJECT
+  //     Opcodes.SGET_BOOLEAN
+  //     Opcodes.SGET_BYTE
+  //     Opcodes.SGET_CHAR
+  //     Opcodes.SGET_SHORT
+  //     Opcodes.SPUT
+  //     Opcodes.SPUT_WIDE
+  //     Opcodes.SPUT_OBJECT
+  //     Opcodes.SPUT_BOOLEAN
+  //     Opcodes.SPUT_BYTE
+  //     Opcodes.SPUT_CHAR
+  //     Opcodes.SPUT_SHORT
+  //     Opcodes.INVOKE_VIRTUAL
+  //     Opcodes.INVOKE_SUPER
+  //     Opcodes.INVOKE_DIRECT
+  //     Opcodes.INVOKE_STATIC
+  //     Opcodes.INVOKE_INTERFACE
+  //     Opcodes.NEG_INT
+  //     Opcodes.NOT_INT
+  //     Opcodes.NEG_LONG
+  //     Opcodes.NOT_LONG
+  //     Opcodes.NEG_FLOAT
+  //     Opcodes.NEG_DOUBLE
+  //     Opcodes.INT_TO_LONG
+  //     Opcodes.INT_TO_FLOAT
+  //     Opcodes.INT_TO_DOUBLE
+  //     Opcodes.LONG_TO_INT
+  //     Opcodes.LONG_TO_FLOAT
+  //     Opcodes.LONG_TO_DOUBLE
+  //     Opcodes.FLOAT_TO_INT
+  //     Opcodes.FLOAT_TO_LONG
+  //     Opcodes.FLOAT_TO_DOUBLE
+  //     Opcodes.DOUBLE_TO_INT
+  //     Opcodes.DOUBLE_TO_LONG
+  //     Opcodes.DOUBLE_TO_FLOAT
+  //     Opcodes.INT_TO_BYTE
+  //     Opcodes.INT_TO_CHAR
+  //     Opcodes.INT_TO_SHORT
+  //     Opcodes.ADD_INT_2ADDR
+  //     Opcodes.SUB_INT_2ADDR
+  //     Opcodes.MUL_INT_2ADDR
+  //     Opcodes.DIV_INT_2ADDR
+  //     Opcodes.REM_INT_2ADDR
+  //     Opcodes.AND_INT_2ADDR
+  //     Opcodes.OR_INT_2ADDR
+  //     Opcodes.XOR_INT_2ADDR
+  //     Opcodes.SHL_INT_2ADDR
+  //     Opcodes.SHR_INT_2ADDR
+  //     Opcodes.USHR_INT_2ADDR
+  //     Opcodes.ADD_LONG_2ADDR
+  //     Opcodes.SUB_LONG_2ADDR
+  //     Opcodes.MUL_LONG_2ADDR
+  //     Opcodes.DIV_LONG_2ADDR
+  //     Opcodes.REM_LONG_2ADDR
+  //     Opcodes.AND_LONG_2ADDR
+  //     Opcodes.OR_LONG_2ADDR
+  //     Opcodes.XOR_LONG_2ADDR
+  //     Opcodes.SHL_LONG_2ADDR
+  //     Opcodes.SHR_LONG_2ADDR
+  //     Opcodes.USHR_LONG_2ADDR
+  //     Opcodes.ADD_FLOAT_2ADDR
+  //     Opcodes.SUB_FLOAT_2ADDR
+  //     Opcodes.MUL_FLOAT_2ADDR
+  //     Opcodes.DIV_FLOAT_2ADDR
+  //     Opcodes.REM_FLOAT_2ADDR
+  //     Opcodes.ADD_DOUBLE_2ADDR
+  //     Opcodes.SUB_DOUBLE_2ADDR
+  //     Opcodes.MUL_DOUBLE_2ADDR
+  //     Opcodes.DIV_DOUBLE_2ADDR
+  //     Opcodes.REM_DOUBLE_2ADDR
+  //     Opcodes.ADD_INT_LIT8
+  //     Opcodes.RSUB_INT_LIT8
+  //     Opcodes.MUL_INT_LIT8
+  //     Opcodes.DIV_INT_LIT8
+  //     Opcodes.REM_INT_LIT8
+  //     Opcodes.AND_INT_LIT8
+  //     Opcodes.OR_INT_LIT8
+  //     Opcodes.XOR_INT_LIT8
+  //     Opcodes.SHL_INT_LIT8
+  //     Opcodes.SHR_INT_LIT8
+  //     Opcodes.USHR_INT_LIT8
+  // END(first-opcodes)
+
+  static {
+    /*
+     * Note: The choices made here are to pick the optimistically
+     * smallest Dalvik opcode, and leave it to later processing to
+     * pessimize. See the automatically-generated comment above
+     * for reference.
      */
-    private RopToDop() {
-        // This space intentionally left blank.
+    MAP = new HashMap<Rop, Dop>(400);
+    MAP.put(Rops.NOP, Dops.NOP);
+    MAP.put(Rops.MOVE_INT, Dops.MOVE);
+    MAP.put(Rops.MOVE_LONG, Dops.MOVE_WIDE);
+    MAP.put(Rops.MOVE_FLOAT, Dops.MOVE);
+    MAP.put(Rops.MOVE_DOUBLE, Dops.MOVE_WIDE);
+    MAP.put(Rops.MOVE_OBJECT, Dops.MOVE_OBJECT);
+    MAP.put(Rops.MOVE_PARAM_INT, Dops.MOVE);
+    MAP.put(Rops.MOVE_PARAM_LONG, Dops.MOVE_WIDE);
+    MAP.put(Rops.MOVE_PARAM_FLOAT, Dops.MOVE);
+    MAP.put(Rops.MOVE_PARAM_DOUBLE, Dops.MOVE_WIDE);
+    MAP.put(Rops.MOVE_PARAM_OBJECT, Dops.MOVE_OBJECT);
+
+    /*
+     * Note: No entry for MOVE_EXCEPTION, since it varies by
+     * exception type. (That is, there is no unique instance to
+     * add to the map.)
+     */
+
+MAP.put(Rops.CONST_INT, Dops.CONST_4);
+    MAP.put(Rops.CONST_LONG, Dops.CONST_WIDE_16);
+    MAP.put(Rops.CONST_FLOAT, Dops.CONST_4);
+    MAP.put(Rops.CONST_DOUBLE, Dops.CONST_WIDE_16);
+
+    /*
+     * Note: No entry for CONST_OBJECT, since it needs to turn
+     * into either CONST_STRING or CONST_CLASS.
+     */
+
+/*
+       * TODO(dx team): I think the only case of this is for null, and
+       * const/4 should cover that.
+       */
+    MAP.put(Rops.CONST_OBJECT_NOTHROW, Dops.CONST_4);
+
+    MAP.put(Rops.GOTO, Dops.GOTO);
+    MAP.put(Rops.IF_EQZ_INT, Dops.IF_EQZ);
+    MAP.put(Rops.IF_NEZ_INT, Dops.IF_NEZ);
+    MAP.put(Rops.IF_LTZ_INT, Dops.IF_LTZ);
+    MAP.put(Rops.IF_GEZ_INT, Dops.IF_GEZ);
+    MAP.put(Rops.IF_LEZ_INT, Dops.IF_LEZ);
+    MAP.put(Rops.IF_GTZ_INT, Dops.IF_GTZ);
+    MAP.put(Rops.IF_EQZ_OBJECT, Dops.IF_EQZ);
+    MAP.put(Rops.IF_NEZ_OBJECT, Dops.IF_NEZ);
+    MAP.put(Rops.IF_EQ_INT, Dops.IF_EQ);
+    MAP.put(Rops.IF_NE_INT, Dops.IF_NE);
+    MAP.put(Rops.IF_LT_INT, Dops.IF_LT);
+    MAP.put(Rops.IF_GE_INT, Dops.IF_GE);
+    MAP.put(Rops.IF_LE_INT, Dops.IF_LE);
+    MAP.put(Rops.IF_GT_INT, Dops.IF_GT);
+    MAP.put(Rops.IF_EQ_OBJECT, Dops.IF_EQ);
+    MAP.put(Rops.IF_NE_OBJECT, Dops.IF_NE);
+    MAP.put(Rops.SWITCH, Dops.SPARSE_SWITCH);
+    MAP.put(Rops.ADD_INT, Dops.ADD_INT_2ADDR);
+    MAP.put(Rops.ADD_LONG, Dops.ADD_LONG_2ADDR);
+    MAP.put(Rops.ADD_FLOAT, Dops.ADD_FLOAT_2ADDR);
+    MAP.put(Rops.ADD_DOUBLE, Dops.ADD_DOUBLE_2ADDR);
+    MAP.put(Rops.SUB_INT, Dops.SUB_INT_2ADDR);
+    MAP.put(Rops.SUB_LONG, Dops.SUB_LONG_2ADDR);
+    MAP.put(Rops.SUB_FLOAT, Dops.SUB_FLOAT_2ADDR);
+    MAP.put(Rops.SUB_DOUBLE, Dops.SUB_DOUBLE_2ADDR);
+    MAP.put(Rops.MUL_INT, Dops.MUL_INT_2ADDR);
+    MAP.put(Rops.MUL_LONG, Dops.MUL_LONG_2ADDR);
+    MAP.put(Rops.MUL_FLOAT, Dops.MUL_FLOAT_2ADDR);
+    MAP.put(Rops.MUL_DOUBLE, Dops.MUL_DOUBLE_2ADDR);
+    MAP.put(Rops.DIV_INT, Dops.DIV_INT_2ADDR);
+    MAP.put(Rops.DIV_LONG, Dops.DIV_LONG_2ADDR);
+    MAP.put(Rops.DIV_FLOAT, Dops.DIV_FLOAT_2ADDR);
+    MAP.put(Rops.DIV_DOUBLE, Dops.DIV_DOUBLE_2ADDR);
+    MAP.put(Rops.REM_INT, Dops.REM_INT_2ADDR);
+    MAP.put(Rops.REM_LONG, Dops.REM_LONG_2ADDR);
+    MAP.put(Rops.REM_FLOAT, Dops.REM_FLOAT_2ADDR);
+    MAP.put(Rops.REM_DOUBLE, Dops.REM_DOUBLE_2ADDR);
+    MAP.put(Rops.NEG_INT, Dops.NEG_INT);
+    MAP.put(Rops.NEG_LONG, Dops.NEG_LONG);
+    MAP.put(Rops.NEG_FLOAT, Dops.NEG_FLOAT);
+    MAP.put(Rops.NEG_DOUBLE, Dops.NEG_DOUBLE);
+    MAP.put(Rops.AND_INT, Dops.AND_INT_2ADDR);
+    MAP.put(Rops.AND_LONG, Dops.AND_LONG_2ADDR);
+    MAP.put(Rops.OR_INT, Dops.OR_INT_2ADDR);
+    MAP.put(Rops.OR_LONG, Dops.OR_LONG_2ADDR);
+    MAP.put(Rops.XOR_INT, Dops.XOR_INT_2ADDR);
+    MAP.put(Rops.XOR_LONG, Dops.XOR_LONG_2ADDR);
+    MAP.put(Rops.SHL_INT, Dops.SHL_INT_2ADDR);
+    MAP.put(Rops.SHL_LONG, Dops.SHL_LONG_2ADDR);
+    MAP.put(Rops.SHR_INT, Dops.SHR_INT_2ADDR);
+    MAP.put(Rops.SHR_LONG, Dops.SHR_LONG_2ADDR);
+    MAP.put(Rops.USHR_INT, Dops.USHR_INT_2ADDR);
+    MAP.put(Rops.USHR_LONG, Dops.USHR_LONG_2ADDR);
+    MAP.put(Rops.NOT_INT, Dops.NOT_INT);
+    MAP.put(Rops.NOT_LONG, Dops.NOT_LONG);
+
+    MAP.put(Rops.ADD_CONST_INT, Dops.ADD_INT_LIT8);
+    // Note: No dalvik ops for other types of add_const.
+
+    MAP.put(Rops.SUB_CONST_INT, Dops.RSUB_INT_LIT8);
+    /*
+     * Note: No dalvik ops for any type of sub_const; instead
+     * there's a *reverse* sub (constant - reg) for ints only.
+     */
+
+MAP.put(Rops.MUL_CONST_INT, Dops.MUL_INT_LIT8);
+    // Note: No dalvik ops for other types of mul_const.
+
+    MAP.put(Rops.DIV_CONST_INT, Dops.DIV_INT_LIT8);
+    // Note: No dalvik ops for other types of div_const.
+
+    MAP.put(Rops.REM_CONST_INT, Dops.REM_INT_LIT8);
+    // Note: No dalvik ops for other types of rem_const.
+
+    MAP.put(Rops.AND_CONST_INT, Dops.AND_INT_LIT8);
+    // Note: No dalvik op for and_const_long.
+
+    MAP.put(Rops.OR_CONST_INT, Dops.OR_INT_LIT8);
+    // Note: No dalvik op for or_const_long.
+
+    MAP.put(Rops.XOR_CONST_INT, Dops.XOR_INT_LIT8);
+    // Note: No dalvik op for xor_const_long.
+
+    MAP.put(Rops.SHL_CONST_INT, Dops.SHL_INT_LIT8);
+    // Note: No dalvik op for shl_const_long.
+
+    MAP.put(Rops.SHR_CONST_INT, Dops.SHR_INT_LIT8);
+    // Note: No dalvik op for shr_const_long.
+
+    MAP.put(Rops.USHR_CONST_INT, Dops.USHR_INT_LIT8);
+    // Note: No dalvik op for shr_const_long.
+
+    MAP.put(Rops.CMPL_LONG, Dops.CMP_LONG);
+    MAP.put(Rops.CMPL_FLOAT, Dops.CMPL_FLOAT);
+    MAP.put(Rops.CMPL_DOUBLE, Dops.CMPL_DOUBLE);
+    MAP.put(Rops.CMPG_FLOAT, Dops.CMPG_FLOAT);
+    MAP.put(Rops.CMPG_DOUBLE, Dops.CMPG_DOUBLE);
+    MAP.put(Rops.CONV_L2I, Dops.LONG_TO_INT);
+    MAP.put(Rops.CONV_F2I, Dops.FLOAT_TO_INT);
+    MAP.put(Rops.CONV_D2I, Dops.DOUBLE_TO_INT);
+    MAP.put(Rops.CONV_I2L, Dops.INT_TO_LONG);
+    MAP.put(Rops.CONV_F2L, Dops.FLOAT_TO_LONG);
+    MAP.put(Rops.CONV_D2L, Dops.DOUBLE_TO_LONG);
+    MAP.put(Rops.CONV_I2F, Dops.INT_TO_FLOAT);
+    MAP.put(Rops.CONV_L2F, Dops.LONG_TO_FLOAT);
+    MAP.put(Rops.CONV_D2F, Dops.DOUBLE_TO_FLOAT);
+    MAP.put(Rops.CONV_I2D, Dops.INT_TO_DOUBLE);
+    MAP.put(Rops.CONV_L2D, Dops.LONG_TO_DOUBLE);
+    MAP.put(Rops.CONV_F2D, Dops.FLOAT_TO_DOUBLE);
+    MAP.put(Rops.TO_BYTE, Dops.INT_TO_BYTE);
+    MAP.put(Rops.TO_CHAR, Dops.INT_TO_CHAR);
+    MAP.put(Rops.TO_SHORT, Dops.INT_TO_SHORT);
+    MAP.put(Rops.RETURN_VOID, Dops.RETURN_VOID);
+    MAP.put(Rops.RETURN_INT, Dops.RETURN);
+    MAP.put(Rops.RETURN_LONG, Dops.RETURN_WIDE);
+    MAP.put(Rops.RETURN_FLOAT, Dops.RETURN);
+    MAP.put(Rops.RETURN_DOUBLE, Dops.RETURN_WIDE);
+    MAP.put(Rops.RETURN_OBJECT, Dops.RETURN_OBJECT);
+    MAP.put(Rops.ARRAY_LENGTH, Dops.ARRAY_LENGTH);
+    MAP.put(Rops.THROW, Dops.THROW);
+    MAP.put(Rops.MONITOR_ENTER, Dops.MONITOR_ENTER);
+    MAP.put(Rops.MONITOR_EXIT, Dops.MONITOR_EXIT);
+    MAP.put(Rops.AGET_INT, Dops.AGET);
+    MAP.put(Rops.AGET_LONG, Dops.AGET_WIDE);
+    MAP.put(Rops.AGET_FLOAT, Dops.AGET);
+    MAP.put(Rops.AGET_DOUBLE, Dops.AGET_WIDE);
+    MAP.put(Rops.AGET_OBJECT, Dops.AGET_OBJECT);
+    MAP.put(Rops.AGET_BOOLEAN, Dops.AGET_BOOLEAN);
+    MAP.put(Rops.AGET_BYTE, Dops.AGET_BYTE);
+    MAP.put(Rops.AGET_CHAR, Dops.AGET_CHAR);
+    MAP.put(Rops.AGET_SHORT, Dops.AGET_SHORT);
+    MAP.put(Rops.APUT_INT, Dops.APUT);
+    MAP.put(Rops.APUT_LONG, Dops.APUT_WIDE);
+    MAP.put(Rops.APUT_FLOAT, Dops.APUT);
+    MAP.put(Rops.APUT_DOUBLE, Dops.APUT_WIDE);
+    MAP.put(Rops.APUT_OBJECT, Dops.APUT_OBJECT);
+    MAP.put(Rops.APUT_BOOLEAN, Dops.APUT_BOOLEAN);
+    MAP.put(Rops.APUT_BYTE, Dops.APUT_BYTE);
+    MAP.put(Rops.APUT_CHAR, Dops.APUT_CHAR);
+    MAP.put(Rops.APUT_SHORT, Dops.APUT_SHORT);
+    MAP.put(Rops.NEW_INSTANCE, Dops.NEW_INSTANCE);
+    MAP.put(Rops.CHECK_CAST, Dops.CHECK_CAST);
+    MAP.put(Rops.INSTANCE_OF, Dops.INSTANCE_OF);
+
+    MAP.put(Rops.GET_FIELD_LONG, Dops.IGET_WIDE);
+    MAP.put(Rops.GET_FIELD_FLOAT, Dops.IGET);
+    MAP.put(Rops.GET_FIELD_DOUBLE, Dops.IGET_WIDE);
+    MAP.put(Rops.GET_FIELD_OBJECT, Dops.IGET_OBJECT);
+    /*
+     * Note: No map entries for get_field_* for non-long integral types,
+     * since they need to be handled specially (see dopFor() below).
+     */
+
+MAP.put(Rops.GET_STATIC_LONG, Dops.SGET_WIDE);
+    MAP.put(Rops.GET_STATIC_FLOAT, Dops.SGET);
+    MAP.put(Rops.GET_STATIC_DOUBLE, Dops.SGET_WIDE);
+    MAP.put(Rops.GET_STATIC_OBJECT, Dops.SGET_OBJECT);
+    /*
+     * Note: No map entries for get_static* for non-long integral types,
+     * since they need to be handled specially (see dopFor() below).
+     */
+
+MAP.put(Rops.PUT_FIELD_LONG, Dops.IPUT_WIDE);
+    MAP.put(Rops.PUT_FIELD_FLOAT, Dops.IPUT);
+    MAP.put(Rops.PUT_FIELD_DOUBLE, Dops.IPUT_WIDE);
+    MAP.put(Rops.PUT_FIELD_OBJECT, Dops.IPUT_OBJECT);
+    /*
+     * Note: No map entries for put_field_* for non-long integral types,
+     * since they need to be handled specially (see dopFor() below).
+     */
+
+MAP.put(Rops.PUT_STATIC_LONG, Dops.SPUT_WIDE);
+    MAP.put(Rops.PUT_STATIC_FLOAT, Dops.SPUT);
+    MAP.put(Rops.PUT_STATIC_DOUBLE, Dops.SPUT_WIDE);
+    MAP.put(Rops.PUT_STATIC_OBJECT, Dops.SPUT_OBJECT);
+    /*
+     * Note: No map entries for put_static* for non-long integral types,
+     * since they need to be handled specially (see dopFor() below).
+     */
+
+    /*
+     * Note: No map entries for invoke*, new_array, and
+     * filled_new_array, since they need to be handled specially
+     * (see dopFor() below).
+     */
+  }
+
+  /**
+   * Returns the dalvik opcode appropriate for the given register-based
+   * instruction.
+   *
+   * @param insn {@code non-null;} the original instruction
+   * @return the corresponding dalvik opcode; one of the constants in
+   * {@link Dops}
+   */
+  public static Dop dopFor(Insn insn) {
+    Rop rop = insn.getOpcode();
+
+    /*
+     * First, just try looking up the rop in the MAP of easy
+     * cases.
+     */
+    Dop result = MAP.get(rop);
+    if (result != null) {
+      return result;
     }
 
     /*
-     * The following comment lists each opcode that should be considered
-     * the "head" of an opcode chain, in terms of the process of fitting
-     * an instruction's arguments to an actual opcode. This list is
-     * automatically generated and may be of use in double-checking the
-     * manually-generated static initialization code for this class.
+     * There was no easy case for the rop, so look up the opcode, and
+     * do something special for each:
      *
-     * TODO: Make opcode-gen produce useful code in this case instead
-     * of just a comment.
+     * The move_exception, new_array, filled_new_array, and
+     * invoke* opcodes won't be found in MAP, since they'll each
+     * have different source and/or result register types / lists.
+     *
+     * The get* and put* opcodes for (non-long) integral types
+     * aren't in the map, since the type signatures aren't
+     * sufficient to distinguish between the types (the salient
+     * source or result will always be just "int").
+     *
+     * And const instruction need to distinguish between strings and
+     * classes.
      */
 
-    // BEGIN(first-opcodes); GENERATED AUTOMATICALLY BY opcode-gen
-    //     Opcodes.NOP
-    //     Opcodes.MOVE
-    //     Opcodes.MOVE_WIDE
-    //     Opcodes.MOVE_OBJECT
-    //     Opcodes.MOVE_RESULT
-    //     Opcodes.MOVE_RESULT_WIDE
-    //     Opcodes.MOVE_RESULT_OBJECT
-    //     Opcodes.MOVE_EXCEPTION
-    //     Opcodes.RETURN_VOID
-    //     Opcodes.RETURN
-    //     Opcodes.RETURN_WIDE
-    //     Opcodes.RETURN_OBJECT
-    //     Opcodes.CONST_4
-    //     Opcodes.CONST_WIDE_16
-    //     Opcodes.CONST_STRING
-    //     Opcodes.CONST_CLASS
-    //     Opcodes.MONITOR_ENTER
-    //     Opcodes.MONITOR_EXIT
-    //     Opcodes.CHECK_CAST
-    //     Opcodes.INSTANCE_OF
-    //     Opcodes.ARRAY_LENGTH
-    //     Opcodes.NEW_INSTANCE
-    //     Opcodes.NEW_ARRAY
-    //     Opcodes.FILLED_NEW_ARRAY
-    //     Opcodes.FILL_ARRAY_DATA
-    //     Opcodes.THROW
-    //     Opcodes.GOTO
-    //     Opcodes.PACKED_SWITCH
-    //     Opcodes.SPARSE_SWITCH
-    //     Opcodes.CMPL_FLOAT
-    //     Opcodes.CMPG_FLOAT
-    //     Opcodes.CMPL_DOUBLE
-    //     Opcodes.CMPG_DOUBLE
-    //     Opcodes.CMP_LONG
-    //     Opcodes.IF_EQ
-    //     Opcodes.IF_NE
-    //     Opcodes.IF_LT
-    //     Opcodes.IF_GE
-    //     Opcodes.IF_GT
-    //     Opcodes.IF_LE
-    //     Opcodes.IF_EQZ
-    //     Opcodes.IF_NEZ
-    //     Opcodes.IF_LTZ
-    //     Opcodes.IF_GEZ
-    //     Opcodes.IF_GTZ
-    //     Opcodes.IF_LEZ
-    //     Opcodes.AGET
-    //     Opcodes.AGET_WIDE
-    //     Opcodes.AGET_OBJECT
-    //     Opcodes.AGET_BOOLEAN
-    //     Opcodes.AGET_BYTE
-    //     Opcodes.AGET_CHAR
-    //     Opcodes.AGET_SHORT
-    //     Opcodes.APUT
-    //     Opcodes.APUT_WIDE
-    //     Opcodes.APUT_OBJECT
-    //     Opcodes.APUT_BOOLEAN
-    //     Opcodes.APUT_BYTE
-    //     Opcodes.APUT_CHAR
-    //     Opcodes.APUT_SHORT
-    //     Opcodes.IGET
-    //     Opcodes.IGET_WIDE
-    //     Opcodes.IGET_OBJECT
-    //     Opcodes.IGET_BOOLEAN
-    //     Opcodes.IGET_BYTE
-    //     Opcodes.IGET_CHAR
-    //     Opcodes.IGET_SHORT
-    //     Opcodes.IPUT
-    //     Opcodes.IPUT_WIDE
-    //     Opcodes.IPUT_OBJECT
-    //     Opcodes.IPUT_BOOLEAN
-    //     Opcodes.IPUT_BYTE
-    //     Opcodes.IPUT_CHAR
-    //     Opcodes.IPUT_SHORT
-    //     Opcodes.SGET
-    //     Opcodes.SGET_WIDE
-    //     Opcodes.SGET_OBJECT
-    //     Opcodes.SGET_BOOLEAN
-    //     Opcodes.SGET_BYTE
-    //     Opcodes.SGET_CHAR
-    //     Opcodes.SGET_SHORT
-    //     Opcodes.SPUT
-    //     Opcodes.SPUT_WIDE
-    //     Opcodes.SPUT_OBJECT
-    //     Opcodes.SPUT_BOOLEAN
-    //     Opcodes.SPUT_BYTE
-    //     Opcodes.SPUT_CHAR
-    //     Opcodes.SPUT_SHORT
-    //     Opcodes.INVOKE_VIRTUAL
-    //     Opcodes.INVOKE_SUPER
-    //     Opcodes.INVOKE_DIRECT
-    //     Opcodes.INVOKE_STATIC
-    //     Opcodes.INVOKE_INTERFACE
-    //     Opcodes.NEG_INT
-    //     Opcodes.NOT_INT
-    //     Opcodes.NEG_LONG
-    //     Opcodes.NOT_LONG
-    //     Opcodes.NEG_FLOAT
-    //     Opcodes.NEG_DOUBLE
-    //     Opcodes.INT_TO_LONG
-    //     Opcodes.INT_TO_FLOAT
-    //     Opcodes.INT_TO_DOUBLE
-    //     Opcodes.LONG_TO_INT
-    //     Opcodes.LONG_TO_FLOAT
-    //     Opcodes.LONG_TO_DOUBLE
-    //     Opcodes.FLOAT_TO_INT
-    //     Opcodes.FLOAT_TO_LONG
-    //     Opcodes.FLOAT_TO_DOUBLE
-    //     Opcodes.DOUBLE_TO_INT
-    //     Opcodes.DOUBLE_TO_LONG
-    //     Opcodes.DOUBLE_TO_FLOAT
-    //     Opcodes.INT_TO_BYTE
-    //     Opcodes.INT_TO_CHAR
-    //     Opcodes.INT_TO_SHORT
-    //     Opcodes.ADD_INT_2ADDR
-    //     Opcodes.SUB_INT_2ADDR
-    //     Opcodes.MUL_INT_2ADDR
-    //     Opcodes.DIV_INT_2ADDR
-    //     Opcodes.REM_INT_2ADDR
-    //     Opcodes.AND_INT_2ADDR
-    //     Opcodes.OR_INT_2ADDR
-    //     Opcodes.XOR_INT_2ADDR
-    //     Opcodes.SHL_INT_2ADDR
-    //     Opcodes.SHR_INT_2ADDR
-    //     Opcodes.USHR_INT_2ADDR
-    //     Opcodes.ADD_LONG_2ADDR
-    //     Opcodes.SUB_LONG_2ADDR
-    //     Opcodes.MUL_LONG_2ADDR
-    //     Opcodes.DIV_LONG_2ADDR
-    //     Opcodes.REM_LONG_2ADDR
-    //     Opcodes.AND_LONG_2ADDR
-    //     Opcodes.OR_LONG_2ADDR
-    //     Opcodes.XOR_LONG_2ADDR
-    //     Opcodes.SHL_LONG_2ADDR
-    //     Opcodes.SHR_LONG_2ADDR
-    //     Opcodes.USHR_LONG_2ADDR
-    //     Opcodes.ADD_FLOAT_2ADDR
-    //     Opcodes.SUB_FLOAT_2ADDR
-    //     Opcodes.MUL_FLOAT_2ADDR
-    //     Opcodes.DIV_FLOAT_2ADDR
-    //     Opcodes.REM_FLOAT_2ADDR
-    //     Opcodes.ADD_DOUBLE_2ADDR
-    //     Opcodes.SUB_DOUBLE_2ADDR
-    //     Opcodes.MUL_DOUBLE_2ADDR
-    //     Opcodes.DIV_DOUBLE_2ADDR
-    //     Opcodes.REM_DOUBLE_2ADDR
-    //     Opcodes.ADD_INT_LIT8
-    //     Opcodes.RSUB_INT_LIT8
-    //     Opcodes.MUL_INT_LIT8
-    //     Opcodes.DIV_INT_LIT8
-    //     Opcodes.REM_INT_LIT8
-    //     Opcodes.AND_INT_LIT8
-    //     Opcodes.OR_INT_LIT8
-    //     Opcodes.XOR_INT_LIT8
-    //     Opcodes.SHL_INT_LIT8
-    //     Opcodes.SHR_INT_LIT8
-    //     Opcodes.USHR_INT_LIT8
-    // END(first-opcodes)
+switch (rop.getOpcode()) {
+      case RegOps.MOVE_EXCEPTION:
+        return Dops.MOVE_EXCEPTION;
+      case RegOps.INVOKE_STATIC:
+        return Dops.INVOKE_STATIC;
+      case RegOps.INVOKE_VIRTUAL:
+        return Dops.INVOKE_VIRTUAL;
+      case RegOps.INVOKE_SUPER:
+        return Dops.INVOKE_SUPER;
+      case RegOps.INVOKE_DIRECT:
+        return Dops.INVOKE_DIRECT;
+      case RegOps.INVOKE_INTERFACE:
+        return Dops.INVOKE_INTERFACE;
+      case RegOps.NEW_ARRAY:
+        return Dops.NEW_ARRAY;
+      case RegOps.FILLED_NEW_ARRAY:
+        return Dops.FILLED_NEW_ARRAY;
+      case RegOps.FILL_ARRAY_DATA:
+        return Dops.FILL_ARRAY_DATA;
+      case RegOps.MOVE_RESULT: {
+        RegisterSpec resultReg = insn.getResult();
 
-    static {
-        /*
-         * Note: The choices made here are to pick the optimistically
-         * smallest Dalvik opcode, and leave it to later processing to
-         * pessimize. See the automatically-generated comment above
-         * for reference.
-         */
-        MAP = new HashMap<Rop, Dop>(400);
-        MAP.put(Rops.NOP,               Dops.NOP);
-        MAP.put(Rops.MOVE_INT,          Dops.MOVE);
-        MAP.put(Rops.MOVE_LONG,         Dops.MOVE_WIDE);
-        MAP.put(Rops.MOVE_FLOAT,        Dops.MOVE);
-        MAP.put(Rops.MOVE_DOUBLE,       Dops.MOVE_WIDE);
-        MAP.put(Rops.MOVE_OBJECT,       Dops.MOVE_OBJECT);
-        MAP.put(Rops.MOVE_PARAM_INT,    Dops.MOVE);
-        MAP.put(Rops.MOVE_PARAM_LONG,   Dops.MOVE_WIDE);
-        MAP.put(Rops.MOVE_PARAM_FLOAT,  Dops.MOVE);
-        MAP.put(Rops.MOVE_PARAM_DOUBLE, Dops.MOVE_WIDE);
-        MAP.put(Rops.MOVE_PARAM_OBJECT, Dops.MOVE_OBJECT);
+        if (resultReg == null) {
+          return Dops.NOP;
+        } else {
+          switch (resultReg.getBasicType()) {
+            case Type.BT_INT:
+            case Type.BT_FLOAT:
+            case Type.BT_BOOLEAN:
+            case Type.BT_BYTE:
+            case Type.BT_CHAR:
+            case Type.BT_SHORT:
+              return Dops.MOVE_RESULT;
+            case Type.BT_LONG:
+            case Type.BT_DOUBLE:
+              return Dops.MOVE_RESULT_WIDE;
+            case Type.BT_OBJECT:
+              return Dops.MOVE_RESULT_OBJECT;
+            default: {
+              throw new RuntimeException("Unexpected basic type");
+            }
+          }
+        }
+      }
 
-        /*
-         * Note: No entry for MOVE_EXCEPTION, since it varies by
-         * exception type. (That is, there is no unique instance to
-         * add to the map.)
-         */
-
-        MAP.put(Rops.CONST_INT,         Dops.CONST_4);
-        MAP.put(Rops.CONST_LONG,        Dops.CONST_WIDE_16);
-        MAP.put(Rops.CONST_FLOAT,       Dops.CONST_4);
-        MAP.put(Rops.CONST_DOUBLE,      Dops.CONST_WIDE_16);
-
-        /*
-         * Note: No entry for CONST_OBJECT, since it needs to turn
-         * into either CONST_STRING or CONST_CLASS.
-         */
-
-        /*
-         * TODO: I think the only case of this is for null, and
-         * const/4 should cover that.
-         */
-        MAP.put(Rops.CONST_OBJECT_NOTHROW, Dops.CONST_4);
-
-        MAP.put(Rops.GOTO,                 Dops.GOTO);
-        MAP.put(Rops.IF_EQZ_INT,           Dops.IF_EQZ);
-        MAP.put(Rops.IF_NEZ_INT,           Dops.IF_NEZ);
-        MAP.put(Rops.IF_LTZ_INT,           Dops.IF_LTZ);
-        MAP.put(Rops.IF_GEZ_INT,           Dops.IF_GEZ);
-        MAP.put(Rops.IF_LEZ_INT,           Dops.IF_LEZ);
-        MAP.put(Rops.IF_GTZ_INT,           Dops.IF_GTZ);
-        MAP.put(Rops.IF_EQZ_OBJECT,        Dops.IF_EQZ);
-        MAP.put(Rops.IF_NEZ_OBJECT,        Dops.IF_NEZ);
-        MAP.put(Rops.IF_EQ_INT,            Dops.IF_EQ);
-        MAP.put(Rops.IF_NE_INT,            Dops.IF_NE);
-        MAP.put(Rops.IF_LT_INT,            Dops.IF_LT);
-        MAP.put(Rops.IF_GE_INT,            Dops.IF_GE);
-        MAP.put(Rops.IF_LE_INT,            Dops.IF_LE);
-        MAP.put(Rops.IF_GT_INT,            Dops.IF_GT);
-        MAP.put(Rops.IF_EQ_OBJECT,         Dops.IF_EQ);
-        MAP.put(Rops.IF_NE_OBJECT,         Dops.IF_NE);
-        MAP.put(Rops.SWITCH,               Dops.SPARSE_SWITCH);
-        MAP.put(Rops.ADD_INT,              Dops.ADD_INT_2ADDR);
-        MAP.put(Rops.ADD_LONG,             Dops.ADD_LONG_2ADDR);
-        MAP.put(Rops.ADD_FLOAT,            Dops.ADD_FLOAT_2ADDR);
-        MAP.put(Rops.ADD_DOUBLE,           Dops.ADD_DOUBLE_2ADDR);
-        MAP.put(Rops.SUB_INT,              Dops.SUB_INT_2ADDR);
-        MAP.put(Rops.SUB_LONG,             Dops.SUB_LONG_2ADDR);
-        MAP.put(Rops.SUB_FLOAT,            Dops.SUB_FLOAT_2ADDR);
-        MAP.put(Rops.SUB_DOUBLE,           Dops.SUB_DOUBLE_2ADDR);
-        MAP.put(Rops.MUL_INT,              Dops.MUL_INT_2ADDR);
-        MAP.put(Rops.MUL_LONG,             Dops.MUL_LONG_2ADDR);
-        MAP.put(Rops.MUL_FLOAT,            Dops.MUL_FLOAT_2ADDR);
-        MAP.put(Rops.MUL_DOUBLE,           Dops.MUL_DOUBLE_2ADDR);
-        MAP.put(Rops.DIV_INT,              Dops.DIV_INT_2ADDR);
-        MAP.put(Rops.DIV_LONG,             Dops.DIV_LONG_2ADDR);
-        MAP.put(Rops.DIV_FLOAT,            Dops.DIV_FLOAT_2ADDR);
-        MAP.put(Rops.DIV_DOUBLE,           Dops.DIV_DOUBLE_2ADDR);
-        MAP.put(Rops.REM_INT,              Dops.REM_INT_2ADDR);
-        MAP.put(Rops.REM_LONG,             Dops.REM_LONG_2ADDR);
-        MAP.put(Rops.REM_FLOAT,            Dops.REM_FLOAT_2ADDR);
-        MAP.put(Rops.REM_DOUBLE,           Dops.REM_DOUBLE_2ADDR);
-        MAP.put(Rops.NEG_INT,              Dops.NEG_INT);
-        MAP.put(Rops.NEG_LONG,             Dops.NEG_LONG);
-        MAP.put(Rops.NEG_FLOAT,            Dops.NEG_FLOAT);
-        MAP.put(Rops.NEG_DOUBLE,           Dops.NEG_DOUBLE);
-        MAP.put(Rops.AND_INT,              Dops.AND_INT_2ADDR);
-        MAP.put(Rops.AND_LONG,             Dops.AND_LONG_2ADDR);
-        MAP.put(Rops.OR_INT,               Dops.OR_INT_2ADDR);
-        MAP.put(Rops.OR_LONG,              Dops.OR_LONG_2ADDR);
-        MAP.put(Rops.XOR_INT,              Dops.XOR_INT_2ADDR);
-        MAP.put(Rops.XOR_LONG,             Dops.XOR_LONG_2ADDR);
-        MAP.put(Rops.SHL_INT,              Dops.SHL_INT_2ADDR);
-        MAP.put(Rops.SHL_LONG,             Dops.SHL_LONG_2ADDR);
-        MAP.put(Rops.SHR_INT,              Dops.SHR_INT_2ADDR);
-        MAP.put(Rops.SHR_LONG,             Dops.SHR_LONG_2ADDR);
-        MAP.put(Rops.USHR_INT,             Dops.USHR_INT_2ADDR);
-        MAP.put(Rops.USHR_LONG,            Dops.USHR_LONG_2ADDR);
-        MAP.put(Rops.NOT_INT,              Dops.NOT_INT);
-        MAP.put(Rops.NOT_LONG,             Dops.NOT_LONG);
-
-        MAP.put(Rops.ADD_CONST_INT,        Dops.ADD_INT_LIT8);
-        // Note: No dalvik ops for other types of add_const.
-
-        MAP.put(Rops.SUB_CONST_INT,        Dops.RSUB_INT_LIT8);
-        /*
-         * Note: No dalvik ops for any type of sub_const; instead
-         * there's a *reverse* sub (constant - reg) for ints only.
-         */
-
-        MAP.put(Rops.MUL_CONST_INT,        Dops.MUL_INT_LIT8);
-        // Note: No dalvik ops for other types of mul_const.
-
-        MAP.put(Rops.DIV_CONST_INT,        Dops.DIV_INT_LIT8);
-        // Note: No dalvik ops for other types of div_const.
-
-        MAP.put(Rops.REM_CONST_INT,        Dops.REM_INT_LIT8);
-        // Note: No dalvik ops for other types of rem_const.
-
-        MAP.put(Rops.AND_CONST_INT,        Dops.AND_INT_LIT8);
-        // Note: No dalvik op for and_const_long.
-
-        MAP.put(Rops.OR_CONST_INT,         Dops.OR_INT_LIT8);
-        // Note: No dalvik op for or_const_long.
-
-        MAP.put(Rops.XOR_CONST_INT,        Dops.XOR_INT_LIT8);
-        // Note: No dalvik op for xor_const_long.
-
-        MAP.put(Rops.SHL_CONST_INT,        Dops.SHL_INT_LIT8);
-        // Note: No dalvik op for shl_const_long.
-
-        MAP.put(Rops.SHR_CONST_INT,        Dops.SHR_INT_LIT8);
-        // Note: No dalvik op for shr_const_long.
-
-        MAP.put(Rops.USHR_CONST_INT,       Dops.USHR_INT_LIT8);
-        // Note: No dalvik op for shr_const_long.
-
-        MAP.put(Rops.CMPL_LONG,            Dops.CMP_LONG);
-        MAP.put(Rops.CMPL_FLOAT,           Dops.CMPL_FLOAT);
-        MAP.put(Rops.CMPL_DOUBLE,          Dops.CMPL_DOUBLE);
-        MAP.put(Rops.CMPG_FLOAT,           Dops.CMPG_FLOAT);
-        MAP.put(Rops.CMPG_DOUBLE,          Dops.CMPG_DOUBLE);
-        MAP.put(Rops.CONV_L2I,             Dops.LONG_TO_INT);
-        MAP.put(Rops.CONV_F2I,             Dops.FLOAT_TO_INT);
-        MAP.put(Rops.CONV_D2I,             Dops.DOUBLE_TO_INT);
-        MAP.put(Rops.CONV_I2L,             Dops.INT_TO_LONG);
-        MAP.put(Rops.CONV_F2L,             Dops.FLOAT_TO_LONG);
-        MAP.put(Rops.CONV_D2L,             Dops.DOUBLE_TO_LONG);
-        MAP.put(Rops.CONV_I2F,             Dops.INT_TO_FLOAT);
-        MAP.put(Rops.CONV_L2F,             Dops.LONG_TO_FLOAT);
-        MAP.put(Rops.CONV_D2F,             Dops.DOUBLE_TO_FLOAT);
-        MAP.put(Rops.CONV_I2D,             Dops.INT_TO_DOUBLE);
-        MAP.put(Rops.CONV_L2D,             Dops.LONG_TO_DOUBLE);
-        MAP.put(Rops.CONV_F2D,             Dops.FLOAT_TO_DOUBLE);
-        MAP.put(Rops.TO_BYTE,              Dops.INT_TO_BYTE);
-        MAP.put(Rops.TO_CHAR,              Dops.INT_TO_CHAR);
-        MAP.put(Rops.TO_SHORT,             Dops.INT_TO_SHORT);
-        MAP.put(Rops.RETURN_VOID,          Dops.RETURN_VOID);
-        MAP.put(Rops.RETURN_INT,           Dops.RETURN);
-        MAP.put(Rops.RETURN_LONG,          Dops.RETURN_WIDE);
-        MAP.put(Rops.RETURN_FLOAT,         Dops.RETURN);
-        MAP.put(Rops.RETURN_DOUBLE,        Dops.RETURN_WIDE);
-        MAP.put(Rops.RETURN_OBJECT,        Dops.RETURN_OBJECT);
-        MAP.put(Rops.ARRAY_LENGTH,         Dops.ARRAY_LENGTH);
-        MAP.put(Rops.THROW,                Dops.THROW);
-        MAP.put(Rops.MONITOR_ENTER,        Dops.MONITOR_ENTER);
-        MAP.put(Rops.MONITOR_EXIT,         Dops.MONITOR_EXIT);
-        MAP.put(Rops.AGET_INT,             Dops.AGET);
-        MAP.put(Rops.AGET_LONG,            Dops.AGET_WIDE);
-        MAP.put(Rops.AGET_FLOAT,           Dops.AGET);
-        MAP.put(Rops.AGET_DOUBLE,          Dops.AGET_WIDE);
-        MAP.put(Rops.AGET_OBJECT,          Dops.AGET_OBJECT);
-        MAP.put(Rops.AGET_BOOLEAN,         Dops.AGET_BOOLEAN);
-        MAP.put(Rops.AGET_BYTE,            Dops.AGET_BYTE);
-        MAP.put(Rops.AGET_CHAR,            Dops.AGET_CHAR);
-        MAP.put(Rops.AGET_SHORT,           Dops.AGET_SHORT);
-        MAP.put(Rops.APUT_INT,             Dops.APUT);
-        MAP.put(Rops.APUT_LONG,            Dops.APUT_WIDE);
-        MAP.put(Rops.APUT_FLOAT,           Dops.APUT);
-        MAP.put(Rops.APUT_DOUBLE,          Dops.APUT_WIDE);
-        MAP.put(Rops.APUT_OBJECT,          Dops.APUT_OBJECT);
-        MAP.put(Rops.APUT_BOOLEAN,         Dops.APUT_BOOLEAN);
-        MAP.put(Rops.APUT_BYTE,            Dops.APUT_BYTE);
-        MAP.put(Rops.APUT_CHAR,            Dops.APUT_CHAR);
-        MAP.put(Rops.APUT_SHORT,           Dops.APUT_SHORT);
-        MAP.put(Rops.NEW_INSTANCE,         Dops.NEW_INSTANCE);
-        MAP.put(Rops.CHECK_CAST,           Dops.CHECK_CAST);
-        MAP.put(Rops.INSTANCE_OF,          Dops.INSTANCE_OF);
-
-        MAP.put(Rops.GET_FIELD_LONG,       Dops.IGET_WIDE);
-        MAP.put(Rops.GET_FIELD_FLOAT,      Dops.IGET);
-        MAP.put(Rops.GET_FIELD_DOUBLE,     Dops.IGET_WIDE);
-        MAP.put(Rops.GET_FIELD_OBJECT,     Dops.IGET_OBJECT);
-        /*
-         * Note: No map entries for get_field_* for non-long integral types,
-         * since they need to be handled specially (see dopFor() below).
-         */
-
-        MAP.put(Rops.GET_STATIC_LONG,      Dops.SGET_WIDE);
-        MAP.put(Rops.GET_STATIC_FLOAT,     Dops.SGET);
-        MAP.put(Rops.GET_STATIC_DOUBLE,    Dops.SGET_WIDE);
-        MAP.put(Rops.GET_STATIC_OBJECT,    Dops.SGET_OBJECT);
-        /*
-         * Note: No map entries for get_static* for non-long integral types,
-         * since they need to be handled specially (see dopFor() below).
-         */
-
-        MAP.put(Rops.PUT_FIELD_LONG,       Dops.IPUT_WIDE);
-        MAP.put(Rops.PUT_FIELD_FLOAT,      Dops.IPUT);
-        MAP.put(Rops.PUT_FIELD_DOUBLE,     Dops.IPUT_WIDE);
-        MAP.put(Rops.PUT_FIELD_OBJECT,     Dops.IPUT_OBJECT);
-        /*
-         * Note: No map entries for put_field_* for non-long integral types,
-         * since they need to be handled specially (see dopFor() below).
-         */
-
-        MAP.put(Rops.PUT_STATIC_LONG,      Dops.SPUT_WIDE);
-        MAP.put(Rops.PUT_STATIC_FLOAT,     Dops.SPUT);
-        MAP.put(Rops.PUT_STATIC_DOUBLE,    Dops.SPUT_WIDE);
-        MAP.put(Rops.PUT_STATIC_OBJECT,    Dops.SPUT_OBJECT);
-        /*
-         * Note: No map entries for put_static* for non-long integral types,
-         * since they need to be handled specially (see dopFor() below).
-         */
-
-        /*
-         * Note: No map entries for invoke*, new_array, and
-         * filled_new_array, since they need to be handled specially
-         * (see dopFor() below).
-         */
+      case RegOps.GET_FIELD: {
+        CstFieldRef ref = (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
+        int basicType = ref.getBasicType();
+        switch (basicType) {
+          case Type.BT_BOOLEAN:
+            return Dops.IGET_BOOLEAN;
+          case Type.BT_BYTE:
+            return Dops.IGET_BYTE;
+          case Type.BT_CHAR:
+            return Dops.IGET_CHAR;
+          case Type.BT_SHORT:
+            return Dops.IGET_SHORT;
+          case Type.BT_INT:
+            return Dops.IGET;
+        }
+        break;
+      }
+      case RegOps.PUT_FIELD: {
+        CstFieldRef ref = (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
+        int basicType = ref.getBasicType();
+        switch (basicType) {
+          case Type.BT_BOOLEAN:
+            return Dops.IPUT_BOOLEAN;
+          case Type.BT_BYTE:
+            return Dops.IPUT_BYTE;
+          case Type.BT_CHAR:
+            return Dops.IPUT_CHAR;
+          case Type.BT_SHORT:
+            return Dops.IPUT_SHORT;
+          case Type.BT_INT:
+            return Dops.IPUT;
+        }
+        break;
+      }
+      case RegOps.GET_STATIC: {
+        CstFieldRef ref = (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
+        int basicType = ref.getBasicType();
+        switch (basicType) {
+          case Type.BT_BOOLEAN:
+            return Dops.SGET_BOOLEAN;
+          case Type.BT_BYTE:
+            return Dops.SGET_BYTE;
+          case Type.BT_CHAR:
+            return Dops.SGET_CHAR;
+          case Type.BT_SHORT:
+            return Dops.SGET_SHORT;
+          case Type.BT_INT:
+            return Dops.SGET;
+        }
+        break;
+      }
+      case RegOps.PUT_STATIC: {
+        CstFieldRef ref = (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
+        int basicType = ref.getBasicType();
+        switch (basicType) {
+          case Type.BT_BOOLEAN:
+            return Dops.SPUT_BOOLEAN;
+          case Type.BT_BYTE:
+            return Dops.SPUT_BYTE;
+          case Type.BT_CHAR:
+            return Dops.SPUT_CHAR;
+          case Type.BT_SHORT:
+            return Dops.SPUT_SHORT;
+          case Type.BT_INT:
+            return Dops.SPUT;
+        }
+        break;
+      }
+      case RegOps.CONST: {
+        Constant cst = ((ThrowingCstInsn) insn).getConstant();
+        if (cst instanceof CstType) {
+          return Dops.CONST_CLASS;
+        } else if (cst instanceof CstString) {
+          return Dops.CONST_STRING;
+        }
+        break;
+      }
     }
 
-    /**
-     * Returns the dalvik opcode appropriate for the given register-based
-     * instruction.
-     *
-     * @param insn {@code non-null;} the original instruction
-     * @return the corresponding dalvik opcode; one of the constants in
-     * {@link Dops}
-     */
-    public static Dop dopFor(Insn insn) {
-        Rop rop = insn.getOpcode();
-
-        /*
-         * First, just try looking up the rop in the MAP of easy
-         * cases.
-         */
-        Dop result = MAP.get(rop);
-        if (result != null) {
-            return result;
-        }
-
-        /*
-         * There was no easy case for the rop, so look up the opcode, and
-         * do something special for each:
-         *
-         * The move_exception, new_array, filled_new_array, and
-         * invoke* opcodes won't be found in MAP, since they'll each
-         * have different source and/or result register types / lists.
-         *
-         * The get* and put* opcodes for (non-long) integral types
-         * aren't in the map, since the type signatures aren't
-         * sufficient to distinguish between the types (the salient
-         * source or result will always be just "int").
-         *
-         * And const instruction need to distinguish between strings and
-         * classes.
-         */
-
-        switch (rop.getOpcode()) {
-            case RegOps.MOVE_EXCEPTION:   return Dops.MOVE_EXCEPTION;
-            case RegOps.INVOKE_STATIC:    return Dops.INVOKE_STATIC;
-            case RegOps.INVOKE_VIRTUAL:   return Dops.INVOKE_VIRTUAL;
-            case RegOps.INVOKE_SUPER:     return Dops.INVOKE_SUPER;
-            case RegOps.INVOKE_DIRECT:    return Dops.INVOKE_DIRECT;
-            case RegOps.INVOKE_INTERFACE: return Dops.INVOKE_INTERFACE;
-            case RegOps.NEW_ARRAY:        return Dops.NEW_ARRAY;
-            case RegOps.FILLED_NEW_ARRAY: return Dops.FILLED_NEW_ARRAY;
-            case RegOps.FILL_ARRAY_DATA:  return Dops.FILL_ARRAY_DATA;
-            case RegOps.MOVE_RESULT: {
-                RegisterSpec resultReg = insn.getResult();
-
-                if (resultReg == null) {
-                    return Dops.NOP;
-                } else {
-                    switch (resultReg.getBasicType()) {
-                        case Type.BT_INT:
-                        case Type.BT_FLOAT:
-                        case Type.BT_BOOLEAN:
-                        case Type.BT_BYTE:
-                        case Type.BT_CHAR:
-                        case Type.BT_SHORT:
-                            return Dops.MOVE_RESULT;
-                        case Type.BT_LONG:
-                        case Type.BT_DOUBLE:
-                            return Dops.MOVE_RESULT_WIDE;
-                        case Type.BT_OBJECT:
-                            return Dops.MOVE_RESULT_OBJECT;
-                        default: {
-                            throw new RuntimeException("Unexpected basic type");
-                        }
-                    }
-                }
-            }
-
-            case RegOps.GET_FIELD: {
-                CstFieldRef ref =
-                    (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
-                int basicType = ref.getBasicType();
-                switch (basicType) {
-                    case Type.BT_BOOLEAN: return Dops.IGET_BOOLEAN;
-                    case Type.BT_BYTE:    return Dops.IGET_BYTE;
-                    case Type.BT_CHAR:    return Dops.IGET_CHAR;
-                    case Type.BT_SHORT:   return Dops.IGET_SHORT;
-                    case Type.BT_INT:     return Dops.IGET;
-                }
-                break;
-            }
-            case RegOps.PUT_FIELD: {
-                CstFieldRef ref =
-                    (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
-                int basicType = ref.getBasicType();
-                switch (basicType) {
-                    case Type.BT_BOOLEAN: return Dops.IPUT_BOOLEAN;
-                    case Type.BT_BYTE:    return Dops.IPUT_BYTE;
-                    case Type.BT_CHAR:    return Dops.IPUT_CHAR;
-                    case Type.BT_SHORT:   return Dops.IPUT_SHORT;
-                    case Type.BT_INT:     return Dops.IPUT;
-                }
-                break;
-            }
-            case RegOps.GET_STATIC: {
-                CstFieldRef ref =
-                    (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
-                int basicType = ref.getBasicType();
-                switch (basicType) {
-                    case Type.BT_BOOLEAN: return Dops.SGET_BOOLEAN;
-                    case Type.BT_BYTE:    return Dops.SGET_BYTE;
-                    case Type.BT_CHAR:    return Dops.SGET_CHAR;
-                    case Type.BT_SHORT:   return Dops.SGET_SHORT;
-                    case Type.BT_INT:     return Dops.SGET;
-                }
-                break;
-            }
-            case RegOps.PUT_STATIC: {
-                CstFieldRef ref =
-                    (CstFieldRef) ((ThrowingCstInsn) insn).getConstant();
-                int basicType = ref.getBasicType();
-                switch (basicType) {
-                    case Type.BT_BOOLEAN: return Dops.SPUT_BOOLEAN;
-                    case Type.BT_BYTE:    return Dops.SPUT_BYTE;
-                    case Type.BT_CHAR:    return Dops.SPUT_CHAR;
-                    case Type.BT_SHORT:   return Dops.SPUT_SHORT;
-                    case Type.BT_INT:     return Dops.SPUT;
-                }
-                break;
-            }
-            case RegOps.CONST: {
-                Constant cst = ((ThrowingCstInsn) insn).getConstant();
-                if (cst instanceof CstType) {
-                    return Dops.CONST_CLASS;
-                } else if (cst instanceof CstString) {
-                    return Dops.CONST_STRING;
-                }
-                break;
-            }
-        }
-
-        throw new RuntimeException("unknown rop: " + rop);
-    }
+    throw new RuntimeException("unknown rop: " + rop);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/RopTranslator.java b/dx/src/com/android/jack/dx/dex/code/RopTranslator.java
index 29b7400..ef0b7f6 100644
--- a/dx/src/com/android/jack/dx/dex/code/RopTranslator.java
+++ b/dx/src/com/android/jack/dx/dex/code/RopTranslator.java
@@ -47,836 +47,802 @@
  * #translate} method is the thing to call on this class.
  */
 public final class RopTranslator {
-    /** {@code non-null;} options for dex output */
-    private final DexOptions dexOptions;
 
-    /** {@code non-null;} method to translate */
-    private final RopMethod method;
+  /** {@code non-null;} method to translate */
+  private final RopMethod method;
 
-    /**
-     * how much position info to preserve; one of the static
-     * constants in {@link PositionList}
+  /**
+   * how much position info to preserve; one of the static
+   * constants in {@link PositionList}
+   */
+  private final int positionInfo;
+
+  /** {@code null-ok;} local variable info to use */
+  private final LocalVariableInfo locals;
+
+  /** {@code non-null;} container for all the address objects for the method */
+  private final BlockAddresses addresses;
+
+  /** {@code non-null;} list of output instructions in-progress */
+  private final OutputCollector output;
+
+  /** {@code non-null;} visitor to use during translation */
+  private final TranslationVisitor translationVisitor;
+
+  /** {@code >= 0;} register count for the method */
+  private final int regCount;
+
+  /** {@code null-ok;} block output order; becomes non-null in {@link #pickOrder} */
+  private int[] order;
+
+  /** size, in register units, of all the parameters to this method */
+  private final int paramSize;
+
+  /**
+   * true if the parameters to this method happen to be in proper order
+   * at the end of the frame (as the optimizer emits them)
+   */
+  private boolean paramsAreInOrder;
+
+  /**
+   * Translates a {@link RopMethod}. This may modify the given
+   * input.
+   *
+   * @param method {@code non-null;} the original method
+   * @param positionInfo how much position info to preserve; one of the
+   * static constants in {@link PositionList}
+   * @param locals {@code null-ok;} local variable information to use
+   * @param paramSize size, in register units, of all the parameters to
+   * this method
+   * @param dexOptions {@code non-null;} options for dex output
+   * @return {@code non-null;} the translated version
+   */
+  public static DalvCode translate(RopMethod method, int positionInfo, LocalVariableInfo locals,
+      int paramSize, DexOptions dexOptions) {
+    RopTranslator translator =
+        new RopTranslator(method, positionInfo, locals, paramSize, dexOptions);
+    return translator.translateAndGetResult();
+  }
+
+  /**
+   * Constructs an instance. This method is private. Use {@link #translate}.
+   *
+   * @param method {@code non-null;} the original method
+   * @param positionInfo how much position info to preserve; one of the
+   * static constants in {@link PositionList}
+   * @param locals {@code null-ok;} local variable information to use
+   * @param paramSize size, in register units, of all the parameters to
+   * this method
+   * @param dexOptions {@code non-null;} options for dex output
+   */
+  private RopTranslator(RopMethod method, int positionInfo, LocalVariableInfo locals, int paramSize,
+      DexOptions dexOptions) {
+    this.method = method;
+    this.positionInfo = positionInfo;
+    this.locals = locals;
+    this.addresses = new BlockAddresses(method);
+    this.paramSize = paramSize;
+    this.order = null;
+    this.paramsAreInOrder = calculateParamsAreInOrder(method, paramSize);
+
+    BasicBlockList blocks = method.getBlocks();
+    int bsz = blocks.size();
+
+    /*
+     * Max possible instructions includes three code address
+     * objects per basic block (to the first and last instruction,
+     * and just past the end of the block), and the possibility of
+     * an extra goto at the end of each basic block.
      */
-    private final int positionInfo;
+    int maxInsns = (bsz * 3) + blocks.getInstructionCount();
 
-    /** {@code null-ok;} local variable info to use */
-    private final LocalVariableInfo locals;
+    if (locals != null) {
+      /*
+       * If we're tracking locals, then there's could be another
+       * extra instruction per block (for the locals state at the
+       * start of the block) as well as one for each interblock
+       * local introduction.
+       */
+      maxInsns += bsz + locals.getAssignmentCount();
+    }
 
-    /** {@code non-null;} container for all the address objects for the method */
-    private final BlockAddresses addresses;
+    /*
+     * If params are not in order, we will need register space
+     * for them before this is all over...
+     */
+    this.regCount = blocks.getRegCount() + (paramsAreInOrder ? 0 : this.paramSize);
 
+    this.output = new OutputCollector(dexOptions, maxInsns, bsz * 3, regCount);
+
+    if (locals != null) {
+      this.translationVisitor = new LocalVariableAwareTranslationVisitor(output, locals);
+    } else {
+      this.translationVisitor = new TranslationVisitor(output);
+    }
+  }
+
+  /**
+   * Checks to see if the move-param instructions that occur in this
+   * method happen to slot the params in an order at the top of the
+   * stack frame that matches dalvik's calling conventions. This will
+   * alway result in "true" for methods that have run through the
+   * SSA optimizer.
+   *
+   * @param paramSize size, in register units, of all the parameters
+   * to this method
+   */
+  private static boolean calculateParamsAreInOrder(RopMethod method, final int paramSize) {
+    final boolean[] paramsAreInOrder = {true};
+    final int initialRegCount = method.getBlocks().getRegCount();
+
+    /*
+     * We almost could just check the first block here, but the
+     * {@code cf} layer will put in a second move-param in a
+     * subsequent block in the case of synchronized methods.
+     */
+    method.getBlocks().forEachInsn(new Insn.BaseVisitor() {
+      @Override
+      public void visitPlainCstInsn(PlainCstInsn insn) {
+        if (insn.getOpcode().getOpcode() == RegOps.MOVE_PARAM) {
+          int param = ((CstInteger) insn.getConstant()).getValue();
+
+          paramsAreInOrder[0] = paramsAreInOrder[0]
+              && ((initialRegCount - paramSize + param) == insn.getResult().getReg());
+        }
+      }
+    });
+
+    return paramsAreInOrder[0];
+  }
+
+  /**
+   * Does the translation and returns the result.
+   *
+   * @return {@code non-null;} the result
+   */
+  private DalvCode translateAndGetResult() {
+    pickOrder();
+    outputInstructions();
+
+    StdCatchBuilder catches = new StdCatchBuilder(method, order, addresses);
+
+    return new DalvCode(positionInfo, output.getFinisher(), catches);
+  }
+
+  /**
+   * Performs initial creation of output instructions based on the
+   * original blocks.
+   */
+  private void outputInstructions() {
+    BasicBlockList blocks = method.getBlocks();
+    int[] order = this.order;
+    int len = order.length;
+
+    // Process the blocks in output order.
+    for (int i = 0; i < len; i++) {
+      int nextI = i + 1;
+      int nextLabel = (nextI == order.length) ? -1 : order[nextI];
+      outputBlock(blocks.labelToBlock(order[i]), nextLabel);
+    }
+  }
+
+  /**
+   * Helper for {@link #outputInstructions}, which does the processing
+   * and output of one block.
+   *
+   * @param block {@code non-null;} the block to process and output
+   * @param nextLabel {@code >= -1;} the next block that will be processed, or
+   * {@code -1} if there is no next block
+   */
+  private void outputBlock(BasicBlock block, int nextLabel) {
+    // Append the code address for this block.
+    CodeAddress startAddress = addresses.getStart(block);
+    output.add(startAddress);
+
+    // Append the local variable state for the block.
+    if (locals != null) {
+      RegisterSpecSet starts = locals.getStarts(block);
+      output.add(new LocalSnapshot(startAddress.getPosition(), starts));
+    }
+
+    /*
+     * Choose and append an output instruction for each original
+     * instruction.
+     */
+    translationVisitor.setBlock(block, addresses.getLast(block));
+    block.getInsns().forEach(translationVisitor);
+
+    // Insert the block end code address.
+    output.add(addresses.getEnd(block));
+
+    // Set up for end-of-block activities.
+
+    int succ = block.getPrimarySuccessor();
+    Insn lastInsn = block.getLastInsn();
+
+    /*
+     * Check for (and possibly correct for) a non-optimal choice of
+     * which block will get output next.
+     */
+
+if ((succ >= 0) && (succ != nextLabel)) {
+      /*
+       * The block has a "primary successor" and that primary
+       * successor isn't the next block to be output.
+       */
+      Rop lastRop = lastInsn.getOpcode();
+      if ((lastRop.getBranchingness() == Rop.BRANCH_IF)
+          && (block.getSecondarySuccessor() == nextLabel)) {
+        /*
+         * The block ends with an "if" of some sort, and its
+         * secondary successor (the "then") is in fact the
+         * next block to output. So, reverse the sense of
+         * the test, so that we can just emit the next block
+         * without an interstitial goto.
+         */
+        output.reverseBranch(1, addresses.getStart(succ));
+      } else {
+        /*
+         * Our only recourse is to add a goto here to get the
+         * flow to be correct.
+         */
+        TargetInsn insn = new TargetInsn(Dops.GOTO, lastInsn.getPosition(), RegisterSpecList.EMPTY,
+            addresses.getStart(succ));
+        output.add(insn);
+      }
+    }
+  }
+
+  /**
+   * Picks an order for the blocks by doing "trace" analysis.
+   */
+  private void pickOrder() {
+    BasicBlockList blocks = method.getBlocks();
+    int sz = blocks.size();
+    int maxLabel = blocks.getMaxLabel();
+    int[] workSet = Bits.makeBitSet(maxLabel);
+    int[] tracebackSet = Bits.makeBitSet(maxLabel);
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = blocks.get(i);
+      Bits.set(workSet, one.getLabel());
+    }
+
+    int[] order = new int[sz];
+    int at = 0;
+
+    /*
+     * Starting with the designated "first label" (that is, the
+     * first block of the method), add that label to the order,
+     * and then pick its first as-yet unordered successor to
+     * immediately follow it, giving top priority to the primary
+     * (aka default) successor (if any). Keep following successors
+     * until the trace runs out of possibilities. Then, continue
+     * by finding an unordered chain containing the first as-yet
+     * unordered block, and adding it to the order, and so on.
+     */
+    for (int label = method.getFirstLabel(); label != -1; label = Bits.findFirst(workSet, 0)) {
+
+      /*
+       * Attempt to trace backward from the chosen block to an
+       * as-yet unordered predecessor which lists the chosen
+       * block as its primary successor, and so on, until we
+       * fail to find such an unordered predecessor. Start the
+       * trace with that block. Note that the first block in the
+       * method has no predecessors, so in that case this loop
+       * will simply terminate with zero iterations and without
+       * picking a new starter block.
+       */
+      traceBack: for (;;) {
+        IntList preds = method.labelToPredecessors(label);
+        int psz = preds.size();
+
+        for (int i = 0; i < psz; i++) {
+          int predLabel = preds.get(i);
+
+          if (Bits.get(tracebackSet, predLabel)) {
+            /*
+             * We found a predecessor loop; stop tracing back
+             * from here.
+             */
+            break;
+          }
+
+          if (!Bits.get(workSet, predLabel)) {
+            // This one's already ordered.
+            continue;
+          }
+
+          BasicBlock pred = blocks.labelToBlock(predLabel);
+          if (pred.getPrimarySuccessor() == label) {
+            // Found one!
+            label = predLabel;
+            Bits.set(tracebackSet, label);
+            continue traceBack;
+          }
+        }
+
+        // Failed to find a better block to start the trace.
+        break;
+      }
+
+      /*
+       * Trace a path from the chosen block to one of its
+       * unordered successors (hopefully the primary), and so
+       * on, until we run out of unordered successors.
+       */
+      while (label != -1) {
+        Bits.clear(workSet, label);
+        Bits.clear(tracebackSet, label);
+        order[at] = label;
+        at++;
+
+        BasicBlock one = blocks.labelToBlock(label);
+        BasicBlock preferredBlock = blocks.preferredSuccessorOf(one);
+
+        if (preferredBlock == null) {
+          break;
+        }
+
+        int preferred = preferredBlock.getLabel();
+        int primary = one.getPrimarySuccessor();
+
+        if (Bits.get(workSet, preferred)) {
+          /*
+           * Order the current block's preferred successor
+           * next, as it has yet to be scheduled.
+           */
+          label = preferred;
+        } else if ((primary != preferred) && (primary >= 0) && Bits.get(workSet, primary)) {
+          /*
+           * The primary is available, so use that.
+           */
+          label = primary;
+        } else {
+          /*
+           * There's no obvious candidate, so pick the first
+           * one that's available, if any.
+           */
+          IntList successors = one.getSuccessors();
+          int ssz = successors.size();
+          label = -1;
+          for (int i = 0; i < ssz; i++) {
+            int candidate = successors.get(i);
+            if (Bits.get(workSet, candidate)) {
+              label = candidate;
+              break;
+            }
+          }
+        }
+      }
+    }
+
+    if (at != sz) {
+      // There was a duplicate block label.
+      throw new RuntimeException("shouldn't happen");
+    }
+
+    this.order = order;
+  }
+
+  /**
+   * Gets the complete register list (result and sources) out of a
+   * given rop instruction. For insns that are commutative, have
+   * two register sources, and have a source equal to the result,
+   * place that source first.
+   *
+   * @param insn {@code non-null;} instruction in question
+   * @return {@code non-null;} the instruction's complete register list
+   */
+  private static RegisterSpecList getRegs(Insn insn) {
+    return getRegs(insn, insn.getResult());
+  }
+
+  /**
+   * Gets the complete register list (result and sources) out of a
+   * given rop instruction. For insns that are commutative, have
+   * two register sources, and have a source equal to the result,
+   * place that source first.
+   *
+   * @param insn {@code non-null;} instruction in question
+   * @param resultReg {@code null-ok;} the real result to use (ignore the insn's)
+   * @return {@code non-null;} the instruction's complete register list
+   */
+  private static RegisterSpecList getRegs(Insn insn, RegisterSpec resultReg) {
+    RegisterSpecList regs = insn.getSources();
+
+    if (insn.getOpcode().isCommutative() && (regs.size() == 2)
+        && (resultReg.getReg() == regs.get(1).getReg())) {
+
+      /*
+       * For commutative ops which have two register sources,
+       * if the second source is the same register as the result,
+       * swap the sources so that an opcode of form 12x can be selected
+       * instead of one of form 23x
+       */
+
+regs = RegisterSpecList.make(regs.get(1), regs.get(0));
+    }
+
+    if (resultReg == null) {
+      return regs;
+    }
+
+    return regs.withFirst(resultReg);
+  }
+
+  /**
+   * Instruction visitor class for doing the instruction translation per se.
+   */
+  private class TranslationVisitor implements Insn.Visitor {
     /** {@code non-null;} list of output instructions in-progress */
     private final OutputCollector output;
 
-    /** {@code non-null;} visitor to use during translation */
-    private final TranslationVisitor translationVisitor;
-
-    /** {@code >= 0;} register count for the method */
-    private final int regCount;
-
-    /** {@code null-ok;} block output order; becomes non-null in {@link #pickOrder} */
-    private int[] order;
-
-    /** size, in register units, of all the parameters to this method */
-    private final int paramSize;
+    /** {@code non-null;} basic block being worked on */
+    private BasicBlock block;
 
     /**
-     * true if the parameters to this method happen to be in proper order
-     * at the end of the frame (as the optimizer emits them)
+     * {@code null-ok;} code address for the salient last instruction of the
+     * block (used before switches and throwing instructions)
      */
-    private boolean paramsAreInOrder;
+    private CodeAddress lastAddress;
 
     /**
-     * Translates a {@link RopMethod}. This may modify the given
-     * input.
+     * Constructs an instance.
      *
-     * @param method {@code non-null;} the original method
-     * @param positionInfo how much position info to preserve; one of the
-     * static constants in {@link PositionList}
-     * @param locals {@code null-ok;} local variable information to use
-     * @param paramSize size, in register units, of all the parameters to
-     * this method
-     * @param dexOptions {@code non-null;} options for dex output
-     * @return {@code non-null;} the translated version
+     * @param output {@code non-null;} destination for instruction output
      */
-    public static DalvCode translate(RopMethod method, int positionInfo,
-            LocalVariableInfo locals, int paramSize, DexOptions dexOptions) {
-        RopTranslator translator =
-            new RopTranslator(method, positionInfo, locals, paramSize, dexOptions);
-        return translator.translateAndGetResult();
+    public TranslationVisitor(OutputCollector output) {
+      this.output = output;
     }
 
     /**
-     * Constructs an instance. This method is private. Use {@link #translate}.
+     * Sets the block currently being worked on.
      *
-     * @param method {@code non-null;} the original method
-     * @param positionInfo how much position info to preserve; one of the
-     * static constants in {@link PositionList}
-     * @param locals {@code null-ok;} local variable information to use
-     * @param paramSize size, in register units, of all the parameters to
-     * this method
-     * @param dexOptions {@code non-null;} options for dex output
+     * @param block {@code non-null;} the block
+     * @param lastAddress {@code non-null;} code address for the salient
+     * last instruction of the block
      */
-    private RopTranslator(RopMethod method, int positionInfo, LocalVariableInfo locals,
-            int paramSize, DexOptions dexOptions) {
-        this.dexOptions = dexOptions;
-        this.method = method;
-        this.positionInfo = positionInfo;
-        this.locals = locals;
-        this.addresses = new BlockAddresses(method);
-        this.paramSize = paramSize;
-        this.order = null;
-        this.paramsAreInOrder = calculateParamsAreInOrder(method, paramSize);
+    public void setBlock(BasicBlock block, CodeAddress lastAddress) {
+      this.block = block;
+      this.lastAddress = lastAddress;
+    }
 
-        BasicBlockList blocks = method.getBlocks();
-        int bsz = blocks.size();
-
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainInsn(PlainInsn insn) {
+      Rop rop = insn.getOpcode();
+      if (rop.getOpcode() == RegOps.MARK_LOCAL) {
         /*
-         * Max possible instructions includes three code address
-         * objects per basic block (to the first and last instruction,
-         * and just past the end of the block), and the possibility of
-         * an extra goto at the end of each basic block.
+         * Ignore these. They're dealt with by
+         * the LocalVariableAwareTranslationVisitor
          */
-        int maxInsns = (bsz * 3) + blocks.getInstructionCount();
+        return;
+      }
+      if (rop.getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
+        // These get skipped
+        return;
+      }
 
-        if (locals != null) {
-            /*
-             * If we're tracking locals, then there's could be another
-             * extra instruction per block (for the locals state at the
-             * start of the block) as well as one for each interblock
-             * local introduction.
-             */
-            maxInsns += bsz + locals.getAssignmentCount();
+      SourcePosition pos = insn.getPosition();
+      Dop opcode = RopToDop.dopFor(insn);
+      DalvInsn di;
+
+      switch (rop.getBranchingness()) {
+        case Rop.BRANCH_NONE:
+        case Rop.BRANCH_RETURN:
+        case Rop.BRANCH_THROW: {
+          di = new SimpleInsn(opcode, pos, getRegs(insn));
+          break;
         }
-
-        /*
-         * If params are not in order, we will need register space
-         * for them before this is all over...
-         */
-        this.regCount = blocks.getRegCount()
-                + (paramsAreInOrder ? 0 : this.paramSize);
-
-        this.output = new OutputCollector(dexOptions, maxInsns, bsz * 3, regCount);
-
-        if (locals != null) {
-            this.translationVisitor =
-                new LocalVariableAwareTranslationVisitor(output, locals);
-        } else {
-            this.translationVisitor = new TranslationVisitor(output);
+        case Rop.BRANCH_GOTO: {
+          /*
+           * Code in the main translation loop will emit a
+           * goto if necessary (if the branch isn't to the
+           * immediately subsequent block).
+           */
+          return;
         }
+        case Rop.BRANCH_IF: {
+          int target = block.getSuccessors().get(1);
+          di = new TargetInsn(opcode, pos, getRegs(insn), addresses.getStart(target));
+          break;
+        }
+        default: {
+          throw new RuntimeException("shouldn't happen");
+        }
+      }
+
+      addOutput(di);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainCstInsn(PlainCstInsn insn) {
+      SourcePosition pos = insn.getPosition();
+      Dop opcode = RopToDop.dopFor(insn);
+      Rop rop = insn.getOpcode();
+      int ropOpcode = rop.getOpcode();
+      DalvInsn di;
+
+      if (rop.getBranchingness() != Rop.BRANCH_NONE) {
+        throw new RuntimeException("shouldn't happen");
+      }
+
+      if (ropOpcode == RegOps.MOVE_PARAM) {
+        if (!paramsAreInOrder) {
+          /*
+           * Parameters are not in order at the top of the reg space.
+           * We need to add moves.
+           */
+
+RegisterSpec dest = insn.getResult();
+          int param = ((CstInteger) insn.getConstant()).getValue();
+          RegisterSpec source = RegisterSpec.make(regCount - paramSize + param, dest.getType());
+          di = new SimpleInsn(opcode, pos, RegisterSpecList.make(dest, source));
+          addOutput(di);
+        }
+      } else {
+        // No moves required for the parameters
+        RegisterSpecList regs = getRegs(insn);
+        di = new CstInsn(opcode, pos, regs, insn.getConstant());
+        addOutput(di);
+      }
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitSwitchInsn(SwitchInsn insn) {
+      SourcePosition pos = insn.getPosition();
+      IntList cases = insn.getCases();
+      IntList successors = block.getSuccessors();
+      int casesSz = cases.size();
+      int succSz = successors.size();
+      int primarySuccessor = block.getPrimarySuccessor();
+
+      /*
+       * Check the assumptions that the number of cases is one
+       * less than the number of successors and that the last
+       * successor in the list is the primary (in this case, the
+       * default). This test is here to guard against forgetting
+       * to change this code if the way switch instructions are
+       * constructed also gets changed.
+       */
+      if ((casesSz != (succSz - 1)) || (primarySuccessor != successors.get(casesSz))) {
+        throw new RuntimeException("shouldn't happen");
+      }
+
+      CodeAddress[] switchTargets = new CodeAddress[casesSz];
+
+      for (int i = 0; i < casesSz; i++) {
+        int label = successors.get(i);
+        switchTargets[i] = addresses.getStart(label);
+      }
+
+      CodeAddress dataAddress = new CodeAddress(pos);
+      // make a new address that binds closely to the switch instruction
+      CodeAddress switchAddress = new CodeAddress(lastAddress.getPosition(), true);
+      SwitchData dataInsn = new SwitchData(pos, switchAddress, cases, switchTargets);
+      Dop opcode = dataInsn.isPacked() ? Dops.PACKED_SWITCH : Dops.SPARSE_SWITCH;
+      TargetInsn switchInsn = new TargetInsn(opcode, pos, getRegs(insn), dataAddress);
+
+      addOutput(switchAddress);
+      addOutput(switchInsn);
+
+      addOutputSuffix(new OddSpacer(pos));
+      addOutputSuffix(dataAddress);
+      addOutputSuffix(dataInsn);
     }
 
     /**
-     * Checks to see if the move-param instructions that occur in this
-     * method happen to slot the params in an order at the top of the
-     * stack frame that matches dalvik's calling conventions. This will
-     * alway result in "true" for methods that have run through the
-     * SSA optimizer.
+     * Looks forward to the current block's primary successor, returning
+     * the RegisterSpec of the result of the move-result-pseudo at the
+     * top of that block or null if none.
      *
-     * @param paramSize size, in register units, of all the parameters
-     * to this method
+     * @return {@code null-ok;} result of move-result-pseudo at the beginning of
+     * primary successor
      */
-    private static boolean calculateParamsAreInOrder(RopMethod method,
-            final int paramSize) {
-        final boolean[] paramsAreInOrder = { true };
-        final int initialRegCount = method.getBlocks().getRegCount();
+    private RegisterSpec getNextMoveResultPseudo() {
+      int label = block.getPrimarySuccessor();
 
-        /*
-         * We almost could just check the first block here, but the
-         * {@code cf} layer will put in a second move-param in a
-         * subsequent block in the case of synchronized methods.
-         */
-        method.getBlocks().forEachInsn(new Insn.BaseVisitor() {
-            @Override
-            public void visitPlainCstInsn(PlainCstInsn insn) {
-                if (insn.getOpcode().getOpcode()== RegOps.MOVE_PARAM) {
-                    int param =
-                        ((CstInteger) insn.getConstant()).getValue();
+      if (label < 0) {
+        return null;
+      }
 
-                    paramsAreInOrder[0] = paramsAreInOrder[0]
-                            && ((initialRegCount - paramSize + param)
-                                == insn.getResult().getReg());
-                }
-            }
-        });
+      Insn insn = method.getBlocks().labelToBlock(label).getInsns().get(0);
 
-        return paramsAreInOrder[0];
+      if (insn.getOpcode().getOpcode() != RegOps.MOVE_RESULT_PSEUDO) {
+        return null;
+      } else {
+        return insn.getResult();
+      }
     }
 
-    /**
-     * Does the translation and returns the result.
-     *
-     * @return {@code non-null;} the result
-     */
-    private DalvCode translateAndGetResult() {
-        pickOrder();
-        outputInstructions();
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingCstInsn(ThrowingCstInsn insn) {
+      SourcePosition pos = insn.getPosition();
+      Dop opcode = RopToDop.dopFor(insn);
+      Rop rop = insn.getOpcode();
+      Constant cst = insn.getConstant();
 
-        StdCatchBuilder catches =
-            new StdCatchBuilder(method, order, addresses);
+      if (rop.getBranchingness() != Rop.BRANCH_THROW) {
+        throw new RuntimeException("shouldn't happen");
+      }
 
-        return new DalvCode(positionInfo, output.getFinisher(), catches);
-    }
+      addOutput(lastAddress);
 
-    /**
-     * Performs initial creation of output instructions based on the
-     * original blocks.
-     */
-    private void outputInstructions() {
-        BasicBlockList blocks = method.getBlocks();
-        int[] order = this.order;
-        int len = order.length;
-
-        // Process the blocks in output order.
-        for (int i = 0; i < len; i++) {
-            int nextI = i + 1;
-            int nextLabel = (nextI == order.length) ? -1 : order[nextI];
-            outputBlock(blocks.labelToBlock(order[i]), nextLabel);
-        }
-    }
-
-    /**
-     * Helper for {@link #outputInstructions}, which does the processing
-     * and output of one block.
-     *
-     * @param block {@code non-null;} the block to process and output
-     * @param nextLabel {@code >= -1;} the next block that will be processed, or
-     * {@code -1} if there is no next block
-     */
-    private void outputBlock(BasicBlock block, int nextLabel) {
-        // Append the code address for this block.
-        CodeAddress startAddress = addresses.getStart(block);
-        output.add(startAddress);
-
-        // Append the local variable state for the block.
-        if (locals != null) {
-            RegisterSpecSet starts = locals.getStarts(block);
-            output.add(new LocalSnapshot(startAddress.getPosition(),
-                                         starts));
-        }
-
-        /*
-         * Choose and append an output instruction for each original
-         * instruction.
-         */
-        translationVisitor.setBlock(block, addresses.getLast(block));
-        block.getInsns().forEach(translationVisitor);
-
-        // Insert the block end code address.
-        output.add(addresses.getEnd(block));
-
-        // Set up for end-of-block activities.
-
-        int succ = block.getPrimarySuccessor();
-        Insn lastInsn = block.getLastInsn();
-
-        /*
-         * Check for (and possibly correct for) a non-optimal choice of
-         * which block will get output next.
-         */
-
-        if ((succ >= 0) && (succ != nextLabel)) {
-            /*
-             * The block has a "primary successor" and that primary
-             * successor isn't the next block to be output.
-             */
-            Rop lastRop = lastInsn.getOpcode();
-            if ((lastRop.getBranchingness() == Rop.BRANCH_IF) &&
-                    (block.getSecondarySuccessor() == nextLabel)) {
-                /*
-                 * The block ends with an "if" of some sort, and its
-                 * secondary successor (the "then") is in fact the
-                 * next block to output. So, reverse the sense of
-                 * the test, so that we can just emit the next block
-                 * without an interstitial goto.
-                 */
-                output.reverseBranch(1, addresses.getStart(succ));
-            } else {
-                /*
-                 * Our only recourse is to add a goto here to get the
-                 * flow to be correct.
-                 */
-                TargetInsn insn =
-                    new TargetInsn(Dops.GOTO, lastInsn.getPosition(),
-                            RegisterSpecList.EMPTY,
-                            addresses.getStart(succ));
-                output.add(insn);
-            }
-        }
-    }
-
-    /**
-     * Picks an order for the blocks by doing "trace" analysis.
-     */
-    private void pickOrder() {
-        BasicBlockList blocks = method.getBlocks();
-        int sz = blocks.size();
-        int maxLabel = blocks.getMaxLabel();
-        int[] workSet = Bits.makeBitSet(maxLabel);
-        int[] tracebackSet = Bits.makeBitSet(maxLabel);
-
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = blocks.get(i);
-            Bits.set(workSet, one.getLabel());
-        }
-
-        int[] order = new int[sz];
-        int at = 0;
-
-        /*
-         * Starting with the designated "first label" (that is, the
-         * first block of the method), add that label to the order,
-         * and then pick its first as-yet unordered successor to
-         * immediately follow it, giving top priority to the primary
-         * (aka default) successor (if any). Keep following successors
-         * until the trace runs out of possibilities. Then, continue
-         * by finding an unordered chain containing the first as-yet
-         * unordered block, and adding it to the order, and so on.
-         */
-        for (int label = method.getFirstLabel();
-             label != -1;
-             label = Bits.findFirst(workSet, 0)) {
-
-            /*
-             * Attempt to trace backward from the chosen block to an
-             * as-yet unordered predecessor which lists the chosen
-             * block as its primary successor, and so on, until we
-             * fail to find such an unordered predecessor. Start the
-             * trace with that block. Note that the first block in the
-             * method has no predecessors, so in that case this loop
-             * will simply terminate with zero iterations and without
-             * picking a new starter block.
-             */
-            traceBack:
-            for (;;) {
-                IntList preds = method.labelToPredecessors(label);
-                int psz = preds.size();
-
-                for (int i = 0; i < psz; i++) {
-                    int predLabel = preds.get(i);
-
-                    if (Bits.get(tracebackSet, predLabel)) {
-                        /*
-                         * We found a predecessor loop; stop tracing back
-                         * from here.
-                         */
-                        break;
-                    }
-
-                    if (!Bits.get(workSet, predLabel)) {
-                        // This one's already ordered.
-                        continue;
-                    }
-
-                    BasicBlock pred = blocks.labelToBlock(predLabel);
-                    if (pred.getPrimarySuccessor() == label) {
-                        // Found one!
-                        label = predLabel;
-                        Bits.set(tracebackSet, label);
-                        continue traceBack;
-                    }
-                }
-
-                // Failed to find a better block to start the trace.
-                break;
-            }
-
-            /*
-             * Trace a path from the chosen block to one of its
-             * unordered successors (hopefully the primary), and so
-             * on, until we run out of unordered successors.
-             */
-            while (label != -1) {
-                Bits.clear(workSet, label);
-                Bits.clear(tracebackSet, label);
-                order[at] = label;
-                at++;
-
-                BasicBlock one = blocks.labelToBlock(label);
-                BasicBlock preferredBlock = blocks.preferredSuccessorOf(one);
-
-                if (preferredBlock == null) {
-                    break;
-                }
-
-                int preferred = preferredBlock.getLabel();
-                int primary = one.getPrimarySuccessor();
-
-                if (Bits.get(workSet, preferred)) {
-                    /*
-                     * Order the current block's preferred successor
-                     * next, as it has yet to be scheduled.
-                     */
-                    label = preferred;
-                } else if ((primary != preferred) && (primary >= 0)
-                        && Bits.get(workSet, primary)) {
-                    /*
-                     * The primary is available, so use that.
-                     */
-                    label = primary;
-                } else {
-                    /*
-                     * There's no obvious candidate, so pick the first
-                     * one that's available, if any.
-                     */
-                    IntList successors = one.getSuccessors();
-                    int ssz = successors.size();
-                    label = -1;
-                    for (int i = 0; i < ssz; i++) {
-                        int candidate = successors.get(i);
-                        if (Bits.get(workSet, candidate)) {
-                            label = candidate;
-                            break;
-                        }
-                    }
-                }
-            }
-        }
-
-        if (at != sz) {
-            // There was a duplicate block label.
-            throw new RuntimeException("shouldn't happen");
-        }
-
-        this.order = order;
-    }
-
-    /**
-     * Gets the complete register list (result and sources) out of a
-     * given rop instruction. For insns that are commutative, have
-     * two register sources, and have a source equal to the result,
-     * place that source first.
-     *
-     * @param insn {@code non-null;} instruction in question
-     * @return {@code non-null;} the instruction's complete register list
-     */
-    private static RegisterSpecList getRegs(Insn insn) {
-        return getRegs(insn, insn.getResult());
-    }
-
-    /**
-     * Gets the complete register list (result and sources) out of a
-     * given rop instruction. For insns that are commutative, have
-     * two register sources, and have a source equal to the result,
-     * place that source first.
-     *
-     * @param insn {@code non-null;} instruction in question
-     * @param resultReg {@code null-ok;} the real result to use (ignore the insn's)
-     * @return {@code non-null;} the instruction's complete register list
-     */
-    private static RegisterSpecList getRegs(Insn insn,
-            RegisterSpec resultReg) {
+      if (rop.isCallLike()) {
         RegisterSpecList regs = insn.getSources();
+        DalvInsn di = new CstInsn(opcode, pos, regs, cst);
 
-        if (insn.getOpcode().isCommutative()
-                && (regs.size() == 2)
-                && (resultReg.getReg() == regs.get(1).getReg())) {
+        addOutput(di);
+      } else {
+        RegisterSpec realResult = getNextMoveResultPseudo();
 
-            /*
-             * For commutative ops which have two register sources,
-             * if the second source is the same register as the result,
-             * swap the sources so that an opcode of form 12x can be selected
-             * instead of one of form 23x
-             */
+        RegisterSpecList regs = getRegs(insn, realResult);
+        DalvInsn di;
 
-            regs = RegisterSpecList.make(regs.get(1), regs.get(0));
+        boolean hasResult = opcode.hasResult() || (rop.getOpcode() == RegOps.CHECK_CAST);
+
+        if (hasResult != (realResult != null)) {
+          throw new RuntimeException("Insn with result/move-result-pseudo mismatch " + insn);
         }
 
-        if (resultReg == null) {
-            return regs;
+        if ((rop.getOpcode() == RegOps.NEW_ARRAY) && (opcode.getOpcode() != Opcodes.NEW_ARRAY)) {
+          /*
+           * It's a type-specific new-array-<primitive>, and
+           * so it should be turned into a SimpleInsn (no
+           * constant ref as it's implicit).
+           */
+          di = new SimpleInsn(opcode, pos, regs);
+        } else {
+          /*
+           * This is the general case for constant-bearing
+           * instructions.
+           */
+          di = new CstInsn(opcode, pos, regs, cst);
         }
 
-        return regs.withFirst(resultReg);
+        addOutput(di);
+      }
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingInsn(ThrowingInsn insn) {
+      SourcePosition pos = insn.getPosition();
+      Dop opcode = RopToDop.dopFor(insn);
+      Rop rop = insn.getOpcode();
+      RegisterSpec realResult;
+
+      if (rop.getBranchingness() != Rop.BRANCH_THROW) {
+        throw new RuntimeException("shouldn't happen");
+      }
+
+      realResult = getNextMoveResultPseudo();
+
+      if (opcode.hasResult() != (realResult != null)) {
+        throw new RuntimeException("Insn with result/move-result-pseudo mismatch" + insn);
+      }
+
+      addOutput(lastAddress);
+
+      DalvInsn di = new SimpleInsn(opcode, pos, getRegs(insn, realResult));
+
+      addOutput(di);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
+      SourcePosition pos = insn.getPosition();
+      Constant cst = insn.getConstant();
+      ArrayList<Constant> values = insn.getInitValues();
+      Rop rop = insn.getOpcode();
+
+      if (rop.getBranchingness() != Rop.BRANCH_NONE) {
+        throw new RuntimeException("shouldn't happen");
+      }
+      CodeAddress dataAddress = new CodeAddress(pos);
+      ArrayData dataInsn = new ArrayData(pos, lastAddress, values, cst);
+
+      TargetInsn fillArrayDataInsn =
+          new TargetInsn(Dops.FILL_ARRAY_DATA, pos, getRegs(insn), dataAddress);
+
+      addOutput(lastAddress);
+      addOutput(fillArrayDataInsn);
+
+      addOutputSuffix(new OddSpacer(pos));
+      addOutputSuffix(dataAddress);
+      addOutputSuffix(dataInsn);
     }
 
     /**
-     * Instruction visitor class for doing the instruction translation per se.
+     * Adds to the output.
+     *
+     * @param insn {@code non-null;} instruction to add
      */
-    private class TranslationVisitor implements Insn.Visitor {
-        /** {@code non-null;} list of output instructions in-progress */
-        private final OutputCollector output;
-
-        /** {@code non-null;} basic block being worked on */
-        private BasicBlock block;
-
-        /**
-         * {@code null-ok;} code address for the salient last instruction of the
-         * block (used before switches and throwing instructions)
-         */
-        private CodeAddress lastAddress;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param output {@code non-null;} destination for instruction output
-         */
-        public TranslationVisitor(OutputCollector output) {
-            this.output = output;
-        }
-
-        /**
-         * Sets the block currently being worked on.
-         *
-         * @param block {@code non-null;} the block
-         * @param lastAddress {@code non-null;} code address for the salient
-         * last instruction of the block
-         */
-        public void setBlock(BasicBlock block, CodeAddress lastAddress) {
-            this.block = block;
-            this.lastAddress = lastAddress;
-        }
-
-        /** {@inheritDoc} */
-        public void visitPlainInsn(PlainInsn insn) {
-            Rop rop = insn.getOpcode();
-            if (rop.getOpcode() == RegOps.MARK_LOCAL) {
-                /*
-                 * Ignore these. They're dealt with by
-                 * the LocalVariableAwareTranslationVisitor
-                 */
-                return;
-            }
-            if (rop.getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
-                // These get skipped
-                return;
-            }
-
-            SourcePosition pos = insn.getPosition();
-            Dop opcode = RopToDop.dopFor(insn);
-            DalvInsn di;
-
-            switch (rop.getBranchingness()) {
-                case Rop.BRANCH_NONE:
-                case Rop.BRANCH_RETURN:
-                case Rop.BRANCH_THROW: {
-                    di = new SimpleInsn(opcode, pos, getRegs(insn));
-                    break;
-                }
-                case Rop.BRANCH_GOTO: {
-                    /*
-                     * Code in the main translation loop will emit a
-                     * goto if necessary (if the branch isn't to the
-                     * immediately subsequent block).
-                     */
-                    return;
-                }
-                case Rop.BRANCH_IF: {
-                    int target = block.getSuccessors().get(1);
-                    di = new TargetInsn(opcode, pos, getRegs(insn),
-                                        addresses.getStart(target));
-                    break;
-                }
-                default: {
-                    throw new RuntimeException("shouldn't happen");
-                }
-            }
-
-            addOutput(di);
-        }
-
-        /** {@inheritDoc} */
-        public void visitPlainCstInsn(PlainCstInsn insn) {
-            SourcePosition pos = insn.getPosition();
-            Dop opcode = RopToDop.dopFor(insn);
-            Rop rop = insn.getOpcode();
-            int ropOpcode = rop.getOpcode();
-            DalvInsn di;
-
-            if (rop.getBranchingness() != Rop.BRANCH_NONE) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            if (ropOpcode == RegOps.MOVE_PARAM) {
-                if (!paramsAreInOrder) {
-                    /*
-                     * Parameters are not in order at the top of the reg space.
-                     * We need to add moves.
-                     */
-
-                    RegisterSpec dest = insn.getResult();
-                    int param =
-                        ((CstInteger) insn.getConstant()).getValue();
-                    RegisterSpec source =
-                        RegisterSpec.make(regCount - paramSize + param,
-                                dest.getType());
-                    di = new SimpleInsn(opcode, pos,
-                                        RegisterSpecList.make(dest, source));
-                    addOutput(di);
-                }
-            } else {
-                // No moves required for the parameters
-                RegisterSpecList regs = getRegs(insn);
-                di = new CstInsn(opcode, pos, regs, insn.getConstant());
-                addOutput(di);
-            }
-        }
-
-        /** {@inheritDoc} */
-        public void visitSwitchInsn(SwitchInsn insn) {
-            SourcePosition pos = insn.getPosition();
-            IntList cases = insn.getCases();
-            IntList successors = block.getSuccessors();
-            int casesSz = cases.size();
-            int succSz = successors.size();
-            int primarySuccessor = block.getPrimarySuccessor();
-
-            /*
-             * Check the assumptions that the number of cases is one
-             * less than the number of successors and that the last
-             * successor in the list is the primary (in this case, the
-             * default). This test is here to guard against forgetting
-             * to change this code if the way switch instructions are
-             * constructed also gets changed.
-             */
-            if ((casesSz != (succSz - 1)) ||
-                (primarySuccessor != successors.get(casesSz))) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            CodeAddress[] switchTargets = new CodeAddress[casesSz];
-
-            for (int i = 0; i < casesSz; i++) {
-                int label = successors.get(i);
-                switchTargets[i] = addresses.getStart(label);
-            }
-
-            CodeAddress dataAddress = new CodeAddress(pos);
-            // make a new address that binds closely to the switch instruction
-            CodeAddress switchAddress =
-                new CodeAddress(lastAddress.getPosition(), true);
-            SwitchData dataInsn =
-                new SwitchData(pos, switchAddress, cases, switchTargets);
-            Dop opcode = dataInsn.isPacked() ?
-                Dops.PACKED_SWITCH : Dops.SPARSE_SWITCH;
-            TargetInsn switchInsn =
-                new TargetInsn(opcode, pos, getRegs(insn), dataAddress);
-
-            addOutput(switchAddress);
-            addOutput(switchInsn);
-
-            addOutputSuffix(new OddSpacer(pos));
-            addOutputSuffix(dataAddress);
-            addOutputSuffix(dataInsn);
-        }
-
-        /**
-         * Looks forward to the current block's primary successor, returning
-         * the RegisterSpec of the result of the move-result-pseudo at the
-         * top of that block or null if none.
-         *
-         * @return {@code null-ok;} result of move-result-pseudo at the beginning of
-         * primary successor
-         */
-        private RegisterSpec getNextMoveResultPseudo()
-        {
-            int label = block.getPrimarySuccessor();
-
-            if (label < 0) {
-                return null;
-            }
-
-            Insn insn
-                    = method.getBlocks().labelToBlock(label).getInsns().get(0);
-
-            if (insn.getOpcode().getOpcode() != RegOps.MOVE_RESULT_PSEUDO) {
-                return null;
-            } else {
-                return insn.getResult();
-            }
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingCstInsn(ThrowingCstInsn insn) {
-            SourcePosition pos = insn.getPosition();
-            Dop opcode = RopToDop.dopFor(insn);
-            Rop rop = insn.getOpcode();
-            Constant cst = insn.getConstant();
-
-            if (rop.getBranchingness() != Rop.BRANCH_THROW) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            addOutput(lastAddress);
-
-            if (rop.isCallLike()) {
-                RegisterSpecList regs = insn.getSources();
-                DalvInsn di = new CstInsn(opcode, pos, regs, cst);
-
-                addOutput(di);
-            } else {
-                RegisterSpec realResult = getNextMoveResultPseudo();
-
-                RegisterSpecList regs = getRegs(insn, realResult);
-                DalvInsn di;
-
-                boolean hasResult = opcode.hasResult()
-                        || (rop.getOpcode() == RegOps.CHECK_CAST);
-
-                if (hasResult != (realResult != null)) {
-                    throw new RuntimeException(
-                            "Insn with result/move-result-pseudo mismatch " +
-                            insn);
-                }
-
-                if ((rop.getOpcode() == RegOps.NEW_ARRAY) &&
-                    (opcode.getOpcode() != Opcodes.NEW_ARRAY)) {
-                    /*
-                     * It's a type-specific new-array-<primitive>, and
-                     * so it should be turned into a SimpleInsn (no
-                     * constant ref as it's implicit).
-                     */
-                    di = new SimpleInsn(opcode, pos, regs);
-                } else {
-                    /*
-                     * This is the general case for constant-bearing
-                     * instructions.
-                     */
-                    di = new CstInsn(opcode, pos, regs, cst);
-                }
-
-                addOutput(di);
-            }
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingInsn(ThrowingInsn insn) {
-            SourcePosition pos = insn.getPosition();
-            Dop opcode = RopToDop.dopFor(insn);
-            Rop rop = insn.getOpcode();
-            RegisterSpec realResult;
-
-            if (rop.getBranchingness() != Rop.BRANCH_THROW) {
-                throw new RuntimeException("shouldn't happen");
-            }
-
-            realResult = getNextMoveResultPseudo();
-
-            if (opcode.hasResult() != (realResult != null)) {
-                throw new RuntimeException(
-                        "Insn with result/move-result-pseudo mismatch" + insn);
-            }
-
-            addOutput(lastAddress);
-
-            DalvInsn di = new SimpleInsn(opcode, pos,
-                    getRegs(insn, realResult));
-
-            addOutput(di);
-        }
-
-        /** {@inheritDoc} */
-        public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
-            SourcePosition pos = insn.getPosition();
-            Constant cst = insn.getConstant();
-            ArrayList<Constant> values = insn.getInitValues();
-            Rop rop = insn.getOpcode();
-
-            if (rop.getBranchingness() != Rop.BRANCH_NONE) {
-                throw new RuntimeException("shouldn't happen");
-            }
-            CodeAddress dataAddress = new CodeAddress(pos);
-            ArrayData dataInsn =
-                new ArrayData(pos, lastAddress, values, cst);
-
-            TargetInsn fillArrayDataInsn =
-                new TargetInsn(Dops.FILL_ARRAY_DATA, pos, getRegs(insn),
-                        dataAddress);
-
-            addOutput(lastAddress);
-            addOutput(fillArrayDataInsn);
-
-            addOutputSuffix(new OddSpacer(pos));
-            addOutputSuffix(dataAddress);
-            addOutputSuffix(dataInsn);
-        }
-
-        /**
-         * Adds to the output.
-         *
-         * @param insn {@code non-null;} instruction to add
-         */
-        protected void addOutput(DalvInsn insn) {
-            output.add(insn);
-        }
-
-        /**
-         * Adds to the output suffix.
-         *
-         * @param insn {@code non-null;} instruction to add
-         */
-        protected void addOutputSuffix(DalvInsn insn) {
-            output.addSuffix(insn);
-        }
+    protected void addOutput(DalvInsn insn) {
+      output.add(insn);
     }
 
     /**
-     * Instruction visitor class for doing instruction translation with
-     * local variable tracking
+     * Adds to the output suffix.
+     *
+     * @param insn {@code non-null;} instruction to add
      */
-    private class LocalVariableAwareTranslationVisitor
-            extends TranslationVisitor {
-        /** {@code non-null;} local variable info */
-        private LocalVariableInfo locals;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param output {@code non-null;} destination for instruction output
-         * @param locals {@code non-null;} the local variable info
-         */
-        public LocalVariableAwareTranslationVisitor(OutputCollector output,
-                                                    LocalVariableInfo locals) {
-            super(output);
-            this.locals = locals;
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public void visitPlainInsn(PlainInsn insn) {
-            super.visitPlainInsn(insn);
-            addIntroductionIfNecessary(insn);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public void visitPlainCstInsn(PlainCstInsn insn) {
-            super.visitPlainCstInsn(insn);
-            addIntroductionIfNecessary(insn);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public void visitSwitchInsn(SwitchInsn insn) {
-            super.visitSwitchInsn(insn);
-            addIntroductionIfNecessary(insn);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public void visitThrowingCstInsn(ThrowingCstInsn insn) {
-            super.visitThrowingCstInsn(insn);
-            addIntroductionIfNecessary(insn);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public void visitThrowingInsn(ThrowingInsn insn) {
-            super.visitThrowingInsn(insn);
-            addIntroductionIfNecessary(insn);
-        }
-
-        /**
-         * Adds a {@link LocalStart} to the output if the given
-         * instruction in fact introduces a local variable.
-         *
-         * @param insn {@code non-null;} instruction in question
-         */
-        public void addIntroductionIfNecessary(Insn insn) {
-            RegisterSpec spec = locals.getAssignment(insn);
-
-            if (spec != null) {
-                addOutput(new LocalStart(insn.getPosition(), spec));
-            }
-        }
+    protected void addOutputSuffix(DalvInsn insn) {
+      output.addSuffix(insn);
     }
+  }
+
+  /**
+   * Instruction visitor class for doing instruction translation with
+   * local variable tracking
+   */
+  private class LocalVariableAwareTranslationVisitor extends TranslationVisitor {
+    /** {@code non-null;} local variable info */
+    private LocalVariableInfo locals;
+
+    /**
+     * Constructs an instance.
+     *
+     * @param output {@code non-null;} destination for instruction output
+     * @param locals {@code non-null;} the local variable info
+     */
+    public LocalVariableAwareTranslationVisitor(OutputCollector output, LocalVariableInfo locals) {
+      super(output);
+      this.locals = locals;
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainInsn(PlainInsn insn) {
+      super.visitPlainInsn(insn);
+      addIntroductionIfNecessary(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainCstInsn(PlainCstInsn insn) {
+      super.visitPlainCstInsn(insn);
+      addIntroductionIfNecessary(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitSwitchInsn(SwitchInsn insn) {
+      super.visitSwitchInsn(insn);
+      addIntroductionIfNecessary(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingCstInsn(ThrowingCstInsn insn) {
+      super.visitThrowingCstInsn(insn);
+      addIntroductionIfNecessary(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingInsn(ThrowingInsn insn) {
+      super.visitThrowingInsn(insn);
+      addIntroductionIfNecessary(insn);
+    }
+
+    /**
+     * Adds a {@link LocalStart} to the output if the given
+     * instruction in fact introduces a local variable.
+     *
+     * @param insn {@code non-null;} instruction in question
+     */
+    public void addIntroductionIfNecessary(Insn insn) {
+      RegisterSpec spec = locals.getAssignment(insn);
+
+      if (spec != null) {
+        addOutput(new LocalStart(insn.getPosition(), spec));
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/SimpleInsn.java b/dx/src/com/android/jack/dx/dex/code/SimpleInsn.java
index ca233e4..351c218 100644
--- a/dx/src/com/android/jack/dx/dex/code/SimpleInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/SimpleInsn.java
@@ -24,36 +24,35 @@
  * the base class.
  */
 public final class SimpleInsn extends FixedSizeInsn {
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param opcode the opcode; one of the constants from {@link Dops}
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} register list, including a
-     * result register if appropriate (that is, registers may be either
-     * ins or outs)
-     */
-    public SimpleInsn(Dop opcode, SourcePosition position,
-                      RegisterSpecList registers) {
-        super(opcode, position, registers);
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param opcode the opcode; one of the constants from {@link Dops}
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} register list, including a
+   * result register if appropriate (that is, registers may be either
+   * ins or outs)
+   */
+  public SimpleInsn(Dop opcode, SourcePosition position, RegisterSpecList registers) {
+    super(opcode, position, registers);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withOpcode(Dop opcode) {
-        return new SimpleInsn(opcode, getPosition(), getRegisters());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withOpcode(Dop opcode) {
+    return new SimpleInsn(opcode, getPosition(), getRegisters());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new SimpleInsn(getOpcode(), getPosition(), registers);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new SimpleInsn(getOpcode(), getPosition(), registers);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        return null;
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    return null;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/StdCatchBuilder.java b/dx/src/com/android/jack/dx/dex/code/StdCatchBuilder.java
index e7f75eb..04c6e0b 100644
--- a/dx/src/com/android/jack/dx/dex/code/StdCatchBuilder.java
+++ b/dx/src/com/android/jack/dx/dex/code/StdCatchBuilder.java
@@ -32,285 +32,275 @@
  * and associated data.
  */
 public final class StdCatchBuilder implements CatchBuilder {
-    /** the maximum range of a single catch handler, in code units */
-    private static final int MAX_CATCH_RANGE = 65535;
+  /** the maximum range of a single catch handler, in code units */
+  private static final int MAX_CATCH_RANGE = 65535;
 
-    /** {@code non-null;} method to build the list for */
-    private final RopMethod method;
+  /** {@code non-null;} method to build the list for */
+  private final RopMethod method;
 
-    /** {@code non-null;} block output order */
-    private final int[] order;
+  /** {@code non-null;} block output order */
+  private final int[] order;
 
-    /** {@code non-null;} address objects for each block */
-    private final BlockAddresses addresses;
+  /** {@code non-null;} address objects for each block */
+  private final BlockAddresses addresses;
 
-    /**
-     * Constructs an instance. It merely holds onto its parameters for
-     * a subsequent call to {@link #build}.
-     *
-     * @param method {@code non-null;} method to build the list for
-     * @param order {@code non-null;} block output order
-     * @param addresses {@code non-null;} address objects for each block
-     */
-    public StdCatchBuilder(RopMethod method, int[] order,
-            BlockAddresses addresses) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        if (order == null) {
-            throw new NullPointerException("order == null");
-        }
-
-        if (addresses == null) {
-            throw new NullPointerException("addresses == null");
-        }
-
-        this.method = method;
-        this.order = order;
-        this.addresses = addresses;
+  /**
+   * Constructs an instance. It merely holds onto its parameters for
+   * a subsequent call to {@link #build}.
+   *
+   * @param method {@code non-null;} method to build the list for
+   * @param order {@code non-null;} block output order
+   * @param addresses {@code non-null;} address objects for each block
+   */
+  public StdCatchBuilder(RopMethod method, int[] order, BlockAddresses addresses) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /** {@inheritDoc} */
-    public CatchTable build() {
-        return build(method, order, addresses);
+    if (order == null) {
+      throw new NullPointerException("order == null");
     }
 
-    /** {@inheritDoc} */
-    public boolean hasAnyCatches() {
-        BasicBlockList blocks = method.getBlocks();
-        int size = blocks.size();
-
-        for (int i = 0; i < size; i++) {
-            BasicBlock block = blocks.get(i);
-            TypeList catches = block.getLastInsn().getCatches();
-            if (catches.size() != 0) {
-                return true;
-            }
-        }
-
-        return false;
+    if (addresses == null) {
+      throw new NullPointerException("addresses == null");
     }
 
-    /** {@inheritDoc} */
-    public HashSet<Type> getCatchTypes() {
-        HashSet<Type> result = new HashSet<Type>(20);
-        BasicBlockList blocks = method.getBlocks();
-        int size = blocks.size();
+    this.method = method;
+    this.order = order;
+    this.addresses = addresses;
+  }
 
-        for (int i = 0; i < size; i++) {
-            BasicBlock block = blocks.get(i);
-            TypeList catches = block.getLastInsn().getCatches();
-            int catchSize = catches.size();
+  /** {@inheritDoc} */
+  @Override
+  public CatchTable build() {
+    return build(method, order, addresses);
+  }
 
-            for (int j = 0; j < catchSize; j++) {
-                result.add(catches.getType(j));
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public boolean hasAnyCatches() {
+    BasicBlockList blocks = method.getBlocks();
+    int size = blocks.size();
 
-        return result;
+    for (int i = 0; i < size; i++) {
+      BasicBlock block = blocks.get(i);
+      TypeList catches = block.getLastInsn().getCatches();
+      if (catches.size() != 0) {
+        return true;
+      }
     }
 
-    /**
-     * Builds and returns the catch table for a given method.
-     *
-     * @param method {@code non-null;} method to build the list for
-     * @param order {@code non-null;} block output order
-     * @param addresses {@code non-null;} address objects for each block
-     * @return {@code non-null;} the constructed table
-     */
-    public static CatchTable build(RopMethod method, int[] order,
-            BlockAddresses addresses) {
-        int len = order.length;
-        BasicBlockList blocks = method.getBlocks();
-        ArrayList<CatchTable.Entry> resultList =
-            new ArrayList<CatchTable.Entry>(len);
-        CatchHandlerList currentHandlers = CatchHandlerList.EMPTY;
-        BasicBlock currentStartBlock = null;
-        BasicBlock currentEndBlock = null;
+    return false;
+  }
 
-        for (int i = 0; i < len; i++) {
-            BasicBlock block = blocks.labelToBlock(order[i]);
+  /** {@inheritDoc} */
+  @Override
+  public HashSet<Type> getCatchTypes() {
+    HashSet<Type> result = new HashSet<Type>(20);
+    BasicBlockList blocks = method.getBlocks();
+    int size = blocks.size();
 
-            if (!block.canThrow()) {
-                /*
-                 * There is no need to concern ourselves with the
-                 * placement of blocks that can't throw with respect
-                 * to the blocks that *can* throw.
-                 */
-                continue;
-            }
+    for (int i = 0; i < size; i++) {
+      BasicBlock block = blocks.get(i);
+      TypeList catches = block.getLastInsn().getCatches();
+      int catchSize = catches.size();
 
-            CatchHandlerList handlers = handlersFor(block, addresses);
-
-            if (currentHandlers.size() == 0) {
-                // This is the start of a new catch range.
-                currentStartBlock = block;
-                currentEndBlock = block;
-                currentHandlers = handlers;
-                continue;
-            }
-
-            if (currentHandlers.equals(handlers)
-                    && rangeIsValid(currentStartBlock, block, addresses)) {
-                /*
-                 * The block we are looking at now has the same handlers
-                 * as the block that started the currently open catch
-                 * range, and adding it to the currently open range won't
-                 * cause it to be too long.
-                 */
-                currentEndBlock = block;
-                continue;
-            }
-
-            /*
-             * The block we are looking at now has incompatible handlers,
-             * so we need to finish off the last entry and start a new
-             * one. Note: We only emit an entry if it has associated handlers.
-             */
-            if (currentHandlers.size() != 0) {
-                CatchTable.Entry entry =
-                    makeEntry(currentStartBlock, currentEndBlock,
-                            currentHandlers, addresses);
-                resultList.add(entry);
-            }
-
-            currentStartBlock = block;
-            currentEndBlock = block;
-            currentHandlers = handlers;
-        }
-
-        if (currentHandlers.size() != 0) {
-            // Emit an entry for the range that was left hanging.
-            CatchTable.Entry entry =
-                makeEntry(currentStartBlock, currentEndBlock,
-                        currentHandlers, addresses);
-            resultList.add(entry);
-        }
-
-        // Construct the final result.
-
-        int resultSz = resultList.size();
-
-        if (resultSz == 0) {
-            return CatchTable.EMPTY;
-        }
-
-        CatchTable result = new CatchTable(resultSz);
-
-        for (int i = 0; i < resultSz; i++) {
-            result.set(i, resultList.get(i));
-        }
-
-        result.setImmutable();
-        return result;
+      for (int j = 0; j < catchSize; j++) {
+        result.add(catches.getType(j));
+      }
     }
 
-    /**
-     * Makes the {@link CatchHandlerList} for the given basic block.
-     *
-     * @param block {@code non-null;} block to get entries for
-     * @param addresses {@code non-null;} address objects for each block
-     * @return {@code non-null;} array of entries
-     */
-    private static CatchHandlerList handlersFor(BasicBlock block,
-            BlockAddresses addresses) {
-        IntList successors = block.getSuccessors();
-        int succSize = successors.size();
-        int primary = block.getPrimarySuccessor();
-        TypeList catches = block.getLastInsn().getCatches();
-        int catchSize = catches.size();
+    return result;
+  }
 
-        if (catchSize == 0) {
-            return CatchHandlerList.EMPTY;
-        }
+  /**
+   * Builds and returns the catch table for a given method.
+   *
+   * @param method {@code non-null;} method to build the list for
+   * @param order {@code non-null;} block output order
+   * @param addresses {@code non-null;} address objects for each block
+   * @return {@code non-null;} the constructed table
+   */
+  public static CatchTable build(RopMethod method, int[] order, BlockAddresses addresses) {
+    int len = order.length;
+    BasicBlockList blocks = method.getBlocks();
+    ArrayList<CatchTable.Entry> resultList = new ArrayList<CatchTable.Entry>(len);
+    CatchHandlerList currentHandlers = CatchHandlerList.EMPTY;
+    BasicBlock currentStartBlock = null;
+    BasicBlock currentEndBlock = null;
 
-        if (((primary == -1) && (succSize != catchSize))
-                || ((primary != -1) &&
-                        ((succSize != (catchSize + 1))
-                                || (primary != successors.get(catchSize))))) {
-            /*
-             * Blocks that throw are supposed to list their primary
-             * successor -- if any -- last in the successors list, but
-             * that constraint appears to be violated here.
-             */
-            throw new RuntimeException(
-                    "shouldn't happen: weird successors list");
-        }
+    for (int i = 0; i < len; i++) {
+      BasicBlock block = blocks.labelToBlock(order[i]);
 
+      if (!block.canThrow()) {
         /*
-         * Reduce the effective catchSize if we spot a catch-all that
-         * isn't at the end.
+         * There is no need to concern ourselves with the
+         * placement of blocks that can't throw with respect
+         * to the blocks that *can* throw.
          */
-        for (int i = 0; i < catchSize; i++) {
-            Type type = catches.getType(i);
-            if (type.equals(Type.OBJECT)) {
-                catchSize = i + 1;
-                break;
-            }
-        }
+        continue;
+      }
 
-        CatchHandlerList result = new CatchHandlerList(catchSize);
+      CatchHandlerList handlers = handlersFor(block, addresses);
 
-        for (int i = 0; i < catchSize; i++) {
-            CstType oneType = new CstType(catches.getType(i));
-            CodeAddress oneHandler = addresses.getStart(successors.get(i));
-            result.set(i, oneType, oneHandler.getAddress());
-        }
+      if (currentHandlers.size() == 0) {
+        // This is the start of a new catch range.
+        currentStartBlock = block;
+        currentEndBlock = block;
+        currentHandlers = handlers;
+        continue;
+      }
 
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Makes a {@link CatchTable#Entry} for the given block range and
-     * handlers.
-     *
-     * @param start {@code non-null;} the start block for the range (inclusive)
-     * @param end {@code non-null;} the start block for the range (also inclusive)
-     * @param handlers {@code non-null;} the handlers for the range
-     * @param addresses {@code non-null;} address objects for each block
-     */
-    private static CatchTable.Entry makeEntry(BasicBlock start,
-            BasicBlock end, CatchHandlerList handlers,
-            BlockAddresses addresses) {
+      if (currentHandlers.equals(handlers) && rangeIsValid(currentStartBlock, block, addresses)) {
         /*
-         * We start at the *last* instruction of the start block, since
-         * that's the instruction that can throw...
+         * The block we are looking at now has the same handlers
+         * as the block that started the currently open catch
+         * range, and adding it to the currently open range won't
+         * cause it to be too long.
          */
-        CodeAddress startAddress = addresses.getLast(start);
+        currentEndBlock = block;
+        continue;
+      }
 
-        // ...And we end *after* the last instruction of the end block.
-        CodeAddress endAddress = addresses.getEnd(end);
+      /*
+       * The block we are looking at now has incompatible handlers,
+       * so we need to finish off the last entry and start a new
+       * one. Note: We only emit an entry if it has associated handlers.
+       */
+      if (currentHandlers.size() != 0) {
+        CatchTable.Entry entry =
+            makeEntry(currentStartBlock, currentEndBlock, currentHandlers, addresses);
+        resultList.add(entry);
+      }
 
-        return new CatchTable.Entry(startAddress.getAddress(),
-                endAddress.getAddress(), handlers);
+      currentStartBlock = block;
+      currentEndBlock = block;
+      currentHandlers = handlers;
     }
 
-    /**
-     * Gets whether the address range for the given two blocks is valid
-     * for a catch handler. This is true as long as the covered range is
-     * under 65536 code units.
-     *
-     * @param start {@code non-null;} the start block for the range (inclusive)
-     * @param end {@code non-null;} the start block for the range (also inclusive)
-     * @param addresses {@code non-null;} address objects for each block
-     * @return {@code true} if the range is valid as a catch range
+    if (currentHandlers.size() != 0) {
+      // Emit an entry for the range that was left hanging.
+      CatchTable.Entry entry =
+          makeEntry(currentStartBlock, currentEndBlock, currentHandlers, addresses);
+      resultList.add(entry);
+    }
+
+    // Construct the final result.
+
+    int resultSz = resultList.size();
+
+    if (resultSz == 0) {
+      return CatchTable.EMPTY;
+    }
+
+    CatchTable result = new CatchTable(resultSz);
+
+    for (int i = 0; i < resultSz; i++) {
+      result.set(i, resultList.get(i));
+    }
+
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Makes the {@link CatchHandlerList} for the given basic block.
+   *
+   * @param block {@code non-null;} block to get entries for
+   * @param addresses {@code non-null;} address objects for each block
+   * @return {@code non-null;} array of entries
+   */
+  private static CatchHandlerList handlersFor(BasicBlock block, BlockAddresses addresses) {
+    IntList successors = block.getSuccessors();
+    int succSize = successors.size();
+    int primary = block.getPrimarySuccessor();
+    TypeList catches = block.getLastInsn().getCatches();
+    int catchSize = catches.size();
+
+    if (catchSize == 0) {
+      return CatchHandlerList.EMPTY;
+    }
+
+    if (((primary == -1) && (succSize != catchSize)) || ((primary != -1)
+        && ((succSize != (catchSize + 1)) || (primary != successors.get(catchSize))))) {
+      /*
+       * Blocks that throw are supposed to list their primary
+       * successor -- if any -- last in the successors list, but
+       * that constraint appears to be violated here.
+       */
+      throw new RuntimeException("shouldn't happen: weird successors list");
+    }
+
+    /*
+     * Reduce the effective catchSize if we spot a catch-all that
+     * isn't at the end.
      */
-    private static boolean rangeIsValid(BasicBlock start, BasicBlock end,
-            BlockAddresses addresses) {
-        if (start == null) {
-            throw new NullPointerException("start == null");
-        }
-
-        if (end == null) {
-            throw new NullPointerException("end == null");
-        }
-
-        // See above about selection of instructions.
-        int startAddress = addresses.getLast(start).getAddress();
-        int endAddress = addresses.getEnd(end).getAddress();
-
-        return (endAddress - startAddress) <= MAX_CATCH_RANGE;
+    for (int i = 0; i < catchSize; i++) {
+      Type type = catches.getType(i);
+      if (type.equals(Type.OBJECT)) {
+        catchSize = i + 1;
+        break;
+      }
     }
+
+    CatchHandlerList result = new CatchHandlerList(catchSize);
+
+    for (int i = 0; i < catchSize; i++) {
+      CstType oneType = new CstType(catches.getType(i));
+      CodeAddress oneHandler = addresses.getStart(successors.get(i));
+      result.set(i, oneType, oneHandler.getAddress());
+    }
+
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Makes a {@link CatchTable#Entry} for the given block range and
+   * handlers.
+   *
+   * @param start {@code non-null;} the start block for the range (inclusive)
+   * @param end {@code non-null;} the start block for the range (also inclusive)
+   * @param handlers {@code non-null;} the handlers for the range
+   * @param addresses {@code non-null;} address objects for each block
+   */
+  private static CatchTable.Entry makeEntry(BasicBlock start, BasicBlock end,
+      CatchHandlerList handlers, BlockAddresses addresses) {
+    /*
+     * We start at the *last* instruction of the start block, since
+     * that's the instruction that can throw...
+     */
+    CodeAddress startAddress = addresses.getLast(start);
+
+    // ...And we end *after* the last instruction of the end block.
+    CodeAddress endAddress = addresses.getEnd(end);
+
+    return new CatchTable.Entry(startAddress.getAddress(), endAddress.getAddress(), handlers);
+  }
+
+  /**
+   * Gets whether the address range for the given two blocks is valid
+   * for a catch handler. This is true as long as the covered range is
+   * under 65536 code units.
+   *
+   * @param start {@code non-null;} the start block for the range (inclusive)
+   * @param end {@code non-null;} the start block for the range (also inclusive)
+   * @param addresses {@code non-null;} address objects for each block
+   * @return {@code true} if the range is valid as a catch range
+   */
+  private static boolean rangeIsValid(BasicBlock start, BasicBlock end, BlockAddresses addresses) {
+    if (start == null) {
+      throw new NullPointerException("start == null");
+    }
+
+    if (end == null) {
+      throw new NullPointerException("end == null");
+    }
+
+    // See above about selection of instructions.
+    int startAddress = addresses.getLast(start).getAddress();
+    int endAddress = addresses.getEnd(end).getAddress();
+
+    return (endAddress - startAddress) <= MAX_CATCH_RANGE;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/SwitchData.java b/dx/src/com/android/jack/dx/dex/code/SwitchData.java
index 0785fba..2e6c268 100644
--- a/dx/src/com/android/jack/dx/dex/code/SwitchData.java
+++ b/dx/src/com/android/jack/dx/dex/code/SwitchData.java
@@ -29,230 +29,229 @@
  * in either a "packed" or "sparse" form.
  */
 public final class SwitchData extends VariableSizeInsn {
-    /**
-     * {@code non-null;} address representing the instruction that uses this
-     * instance
-     */
-    private final CodeAddress user;
+  /**
+   * {@code non-null;} address representing the instruction that uses this
+   * instance
+   */
+  private final CodeAddress user;
 
-    /** {@code non-null;} sorted list of switch cases (keys) */
-    private final IntList cases;
+  /** {@code non-null;} sorted list of switch cases (keys) */
+  private final IntList cases;
 
-    /**
-     * {@code non-null;} corresponding list of code addresses; the branch
-     * target for each case
-     */
-    private final CodeAddress[] targets;
+  /**
+   * {@code non-null;} corresponding list of code addresses; the branch
+   * target for each case
+   */
+  private final CodeAddress[] targets;
 
-    /** whether the output table will be packed (vs. sparse) */
-    private final boolean packed;
+  /** whether the output table will be packed (vs. sparse) */
+  private final boolean packed;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param user {@code non-null;} address representing the instruction that
-     * uses this instance
-     * @param cases {@code non-null;} sorted list of switch cases (keys)
-     * @param targets {@code non-null;} corresponding list of code addresses; the
-     * branch target for each case
-     */
-    public SwitchData(SourcePosition position, CodeAddress user,
-                      IntList cases, CodeAddress[] targets) {
-        super(position, RegisterSpecList.EMPTY);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param user {@code non-null;} address representing the instruction that
+   * uses this instance
+   * @param cases {@code non-null;} sorted list of switch cases (keys)
+   * @param targets {@code non-null;} corresponding list of code addresses; the
+   * branch target for each case
+   */
+  public SwitchData(SourcePosition position, CodeAddress user, IntList cases,
+      CodeAddress[] targets) {
+    super(position, RegisterSpecList.EMPTY);
 
-        if (user == null) {
-            throw new NullPointerException("user == null");
-        }
-
-        if (cases == null) {
-            throw new NullPointerException("cases == null");
-        }
-
-        if (targets == null) {
-            throw new NullPointerException("targets == null");
-        }
-
-        int sz = cases.size();
-
-        if (sz != targets.length) {
-            throw new IllegalArgumentException("cases / targets mismatch");
-        }
-
-        if (sz > 65535) {
-            throw new IllegalArgumentException("too many cases");
-        }
-
-        this.user = user;
-        this.cases = cases;
-        this.targets = targets;
-        this.packed = shouldPack(cases);
+    if (user == null) {
+      throw new NullPointerException("user == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return packed ? (int) packedCodeSize(cases) :
-            (int) sparseCodeSize(cases);
+    if (cases == null) {
+      throw new NullPointerException("cases == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out) {
-        int baseAddress = user.getAddress();
-        int defaultTarget = Dops.PACKED_SWITCH.getFormat().codeSize();
-        int sz = targets.length;
+    if (targets == null) {
+      throw new NullPointerException("targets == null");
+    }
 
-        if (packed) {
-            int firstCase = (sz == 0) ? 0 : cases.get(0);
-            int lastCase = (sz == 0) ? 0 : cases.get(sz - 1);
-            int outSz = lastCase - firstCase + 1;
+    int sz = cases.size();
 
-            out.writeShort(Opcodes.PACKED_SWITCH_PAYLOAD);
-            out.writeShort(outSz);
-            out.writeInt(firstCase);
+    if (sz != targets.length) {
+      throw new IllegalArgumentException("cases / targets mismatch");
+    }
 
-            int caseAt = 0;
-            for (int i = 0; i < outSz; i++) {
-                int outCase = firstCase + i;
-                int oneCase = cases.get(caseAt);
-                int relTarget;
+    if (sz > 65535) {
+      throw new IllegalArgumentException("too many cases");
+    }
 
-                if (oneCase > outCase) {
-                    relTarget = defaultTarget;
-                } else {
-                    relTarget = targets[caseAt].getAddress() - baseAddress;
-                    caseAt++;
-                }
+    this.user = user;
+    this.cases = cases;
+    this.targets = targets;
+    this.packed = shouldPack(cases);
+  }
 
-                out.writeInt(relTarget);
-            }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return packed ? (int) packedCodeSize(cases) : (int) sparseCodeSize(cases);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out) {
+    int baseAddress = user.getAddress();
+    int defaultTarget = Dops.PACKED_SWITCH.getFormat().codeSize();
+    int sz = targets.length;
+
+    if (packed) {
+      int firstCase = (sz == 0) ? 0 : cases.get(0);
+      int lastCase = (sz == 0) ? 0 : cases.get(sz - 1);
+      int outSz = lastCase - firstCase + 1;
+
+      out.writeShort(Opcodes.PACKED_SWITCH_PAYLOAD);
+      out.writeShort(outSz);
+      out.writeInt(firstCase);
+
+      int caseAt = 0;
+      for (int i = 0; i < outSz; i++) {
+        int outCase = firstCase + i;
+        int oneCase = cases.get(caseAt);
+        int relTarget;
+
+        if (oneCase > outCase) {
+          relTarget = defaultTarget;
         } else {
-            out.writeShort(Opcodes.SPARSE_SWITCH_PAYLOAD);
-            out.writeShort(sz);
-
-            for (int i = 0; i < sz; i++) {
-                out.writeInt(cases.get(i));
-            }
-
-            for (int i = 0; i < sz; i++) {
-                int relTarget = targets[i].getAddress() - baseAddress;
-                out.writeInt(relTarget);
-            }
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new SwitchData(getPosition(), user, cases, targets);
-    }
-
-    /**
-     * Returns whether or not this instance's data will be output as packed.
-     *
-     * @return {@code true} iff the data is to be packed
-     */
-    public boolean isPacked() {
-        return packed;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        int sz = targets.length;
-        for (int i = 0; i < sz; i++) {
-            sb.append("\n    ");
-            sb.append(cases.get(i));
-            sb.append(": ");
-            sb.append(targets[i]);
+          relTarget = targets[caseAt].getAddress() - baseAddress;
+          caseAt++;
         }
 
-        return sb.toString();
+        out.writeInt(relTarget);
+      }
+    } else {
+      out.writeShort(Opcodes.SPARSE_SWITCH_PAYLOAD);
+      out.writeShort(sz);
+
+      for (int i = 0; i < sz; i++) {
+        out.writeInt(cases.get(i));
+      }
+
+      for (int i = 0; i < sz; i++) {
+        int relTarget = targets[i].getAddress() - baseAddress;
+        out.writeInt(relTarget);
+      }
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new SwitchData(getPosition(), user, cases, targets);
+  }
+
+  /**
+   * Returns whether or not this instance's data will be output as packed.
+   *
+   * @return {@code true} iff the data is to be packed
+   */
+  public boolean isPacked() {
+    return packed;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    int sz = targets.length;
+    for (int i = 0; i < sz; i++) {
+      sb.append("\n    ");
+      sb.append(cases.get(i));
+      sb.append(": ");
+      sb.append(targets[i]);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String listingString0(boolean noteIndices) {
-        int baseAddress = user.getAddress();
-        StringBuffer sb = new StringBuffer(100);
-        int sz = targets.length;
+    return sb.toString();
+  }
 
-        sb.append(packed ? "packed" : "sparse");
-        sb.append("-switch-payload // for switch @ ");
-        sb.append(Hex.u2(baseAddress));
+  /** {@inheritDoc} */
+  @Override
+  protected String listingString0(boolean noteIndices) {
+    int baseAddress = user.getAddress();
+    StringBuffer sb = new StringBuffer(100);
+    int sz = targets.length;
 
-        for (int i = 0; i < sz; i++) {
-            int absTarget = targets[i].getAddress();
-            int relTarget = absTarget - baseAddress;
-            sb.append("\n  ");
-            sb.append(cases.get(i));
-            sb.append(": ");
-            sb.append(Hex.u4(absTarget));
-            sb.append(" // ");
-            sb.append(Hex.s4(relTarget));
-        }
+    sb.append(packed ? "packed" : "sparse");
+    sb.append("-switch-payload // for switch @ ");
+    sb.append(Hex.u2(baseAddress));
 
-        return sb.toString();
+    for (int i = 0; i < sz; i++) {
+      int absTarget = targets[i].getAddress();
+      int relTarget = absTarget - baseAddress;
+      sb.append("\n  ");
+      sb.append(cases.get(i));
+      sb.append(": ");
+      sb.append(Hex.u4(absTarget));
+      sb.append(" // ");
+      sb.append(Hex.s4(relTarget));
     }
 
-    /**
-     * Gets the size of a packed table for the given cases, in 16-bit code
-     * units.
-     *
-     * @param cases {@code non-null;} sorted list of cases
-     * @return {@code >= -1;} the packed table size or {@code -1} if the
-     * cases couldn't possibly be represented as a packed table
+    return sb.toString();
+  }
+
+  /**
+   * Gets the size of a packed table for the given cases, in 16-bit code
+   * units.
+   *
+   * @param cases {@code non-null;} sorted list of cases
+   * @return {@code >= -1;} the packed table size or {@code -1} if the
+   * cases couldn't possibly be represented as a packed table
+   */
+  private static long packedCodeSize(IntList cases) {
+    int sz = cases.size();
+    long low = cases.get(0);
+    long high = cases.get(sz - 1);
+    long result = ((high - low + 1)) * 2 + 4;
+
+    return (result <= 0x7fffffff) ? result : -1;
+  }
+
+  /**
+   * Gets the size of a sparse table for the given cases, in 16-bit code
+   * units.
+   *
+   * @param cases {@code non-null;} sorted list of cases
+   * @return {@code > 0;} the sparse table size
+   */
+  private static long sparseCodeSize(IntList cases) {
+    int sz = cases.size();
+
+    return (sz * 4L) + 2;
+  }
+
+  /**
+   * Determines whether the given list of cases warrant being packed.
+   *
+   * @param cases {@code non-null;} sorted list of cases
+   * @return {@code true} iff the table encoding the cases
+   * should be packed
+   */
+  private static boolean shouldPack(IntList cases) {
+    int sz = cases.size();
+
+    if (sz < 2) {
+      return true;
+    }
+
+    long packedSize = packedCodeSize(cases);
+    long sparseSize = sparseCodeSize(cases);
+
+    /*
+     * We pick the packed representation if it is possible and
+     * would be as small or smaller than 5/4 of the sparse
+     * representation. That is, we accept some size overhead on
+     * the packed representation, since that format is faster to
+     * execute at runtime.
      */
-    private static long packedCodeSize(IntList cases) {
-        int sz = cases.size();
-        long low = cases.get(0);
-        long high = cases.get(sz - 1);
-        long result = ((high - low + 1)) * 2 + 4;
-
-        return (result <= 0x7fffffff) ? result : -1;
-    }
-
-    /**
-     * Gets the size of a sparse table for the given cases, in 16-bit code
-     * units.
-     *
-     * @param cases {@code non-null;} sorted list of cases
-     * @return {@code > 0;} the sparse table size
-     */
-    private static long sparseCodeSize(IntList cases) {
-        int sz = cases.size();
-
-        return (sz * 4L) + 2;
-    }
-
-    /**
-     * Determines whether the given list of cases warrant being packed.
-     *
-     * @param cases {@code non-null;} sorted list of cases
-     * @return {@code true} iff the table encoding the cases
-     * should be packed
-     */
-    private static boolean shouldPack(IntList cases) {
-        int sz = cases.size();
-
-        if (sz < 2) {
-            return true;
-        }
-
-        long packedSize = packedCodeSize(cases);
-        long sparseSize = sparseCodeSize(cases);
-
-        /*
-         * We pick the packed representation if it is possible and
-         * would be as small or smaller than 5/4 of the sparse
-         * representation. That is, we accept some size overhead on
-         * the packed representation, since that format is faster to
-         * execute at runtime.
-         */
-        return (packedSize >= 0) && (packedSize <= ((sparseSize * 5) / 4));
-    }
+    return (packedSize >= 0) && (packedSize <= ((sparseSize * 5) / 4));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/TargetInsn.java b/dx/src/com/android/jack/dx/dex/code/TargetInsn.java
index c957867..b97025d 100644
--- a/dx/src/com/android/jack/dx/dex/code/TargetInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/TargetInsn.java
@@ -23,110 +23,110 @@
  * Instruction which has a single branch target.
  */
 public final class TargetInsn extends FixedSizeInsn {
-    /** {@code non-null;} the branch target */
-    private CodeAddress target;
+  /** {@code non-null;} the branch target */
+  private CodeAddress target;
 
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}), and the target is initially
-     * {@code null}.
-     *
-     * @param opcode the opcode; one of the constants from {@link Dops}
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} register list, including a
-     * result register if appropriate (that is, registers may be either
-     * ins or outs)
-     * @param target {@code non-null;} the branch target
-     */
-    public TargetInsn(Dop opcode, SourcePosition position,
-                      RegisterSpecList registers, CodeAddress target) {
-        super(opcode, position, registers);
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}), and the target is initially
+   * {@code null}.
+   *
+   * @param opcode the opcode; one of the constants from {@link Dops}
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} register list, including a
+   * result register if appropriate (that is, registers may be either
+   * ins or outs)
+   * @param target {@code non-null;} the branch target
+   */
+  public TargetInsn(Dop opcode, SourcePosition position, RegisterSpecList registers,
+      CodeAddress target) {
+    super(opcode, position, registers);
 
-        if (target == null) {
-            throw new NullPointerException("target == null");
-        }
-
-        this.target = target;
+    if (target == null) {
+      throw new NullPointerException("target == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withOpcode(Dop opcode) {
-        return new TargetInsn(opcode, getPosition(), getRegisters(), target);
+    this.target = target;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withOpcode(Dop opcode) {
+    return new TargetInsn(opcode, getPosition(), getRegisters(), target);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisters(RegisterSpecList registers) {
+    return new TargetInsn(getOpcode(), getPosition(), registers, target);
+  }
+
+  /**
+   * Returns an instance that is just like this one, except that its
+   * opcode has the opposite sense (as a test; e.g. a
+   * {@code lt} test becomes a {@code ge}), and its branch
+   * target is replaced by the one given, and all set-once values
+   * associated with the class (such as its address) are reset.
+   *
+   * @param target {@code non-null;} the new branch target
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public TargetInsn withNewTargetAndReversed(CodeAddress target) {
+    Dop opcode = getOpcode().getOppositeTest();
+
+    return new TargetInsn(opcode, getPosition(), getRegisters(), target);
+  }
+
+  /**
+   * Gets the unique branch target of this instruction.
+   *
+   * @return {@code non-null;} the branch target
+   */
+  public CodeAddress getTarget() {
+    return target;
+  }
+
+  /**
+   * Gets the target address of this instruction. This is only valid
+   * to call if the target instruction has been assigned an address,
+   * and it is merely a convenient shorthand for
+   * {@code getTarget().getAddress()}.
+   *
+   * @return {@code >= 0;} the target address
+   */
+  public int getTargetAddress() {
+    return target.getAddress();
+  }
+
+  /**
+   * Gets the branch offset of this instruction. This is only valid to
+   * call if both this and the target instruction each has been assigned
+   * an address, and it is merely a convenient shorthand for
+   * {@code getTargetAddress() - getAddress()}.
+   *
+   * @return the branch offset
+   */
+  public int getTargetOffset() {
+    return target.getAddress() - getAddress();
+  }
+
+  /**
+   * Returns whether the target offset is known.
+   *
+   * @return {@code true} if the target offset is known or
+   * {@code false} if not
+   */
+  public boolean hasTargetOffset() {
+    return hasAddress() && target.hasAddress();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected String argString() {
+    if (target == null) {
+      return "????";
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisters(RegisterSpecList registers) {
-        return new TargetInsn(getOpcode(), getPosition(), registers, target);
-    }
-
-    /**
-     * Returns an instance that is just like this one, except that its
-     * opcode has the opposite sense (as a test; e.g. a
-     * {@code lt} test becomes a {@code ge}), and its branch
-     * target is replaced by the one given, and all set-once values
-     * associated with the class (such as its address) are reset.
-     *
-     * @param target {@code non-null;} the new branch target
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public TargetInsn withNewTargetAndReversed(CodeAddress target) {
-        Dop opcode = getOpcode().getOppositeTest();
-
-        return new TargetInsn(opcode, getPosition(), getRegisters(), target);
-    }
-
-    /**
-     * Gets the unique branch target of this instruction.
-     *
-     * @return {@code non-null;} the branch target
-     */
-    public CodeAddress getTarget() {
-        return target;
-    }
-
-    /**
-     * Gets the target address of this instruction. This is only valid
-     * to call if the target instruction has been assigned an address,
-     * and it is merely a convenient shorthand for
-     * {@code getTarget().getAddress()}.
-     *
-     * @return {@code >= 0;} the target address
-     */
-    public int getTargetAddress() {
-        return target.getAddress();
-    }
-
-    /**
-     * Gets the branch offset of this instruction. This is only valid to
-     * call if both this and the target instruction each has been assigned
-     * an address, and it is merely a convenient shorthand for
-     * {@code getTargetAddress() - getAddress()}.
-     *
-     * @return the branch offset
-     */
-    public int getTargetOffset() {
-        return target.getAddress() - getAddress();
-    }
-
-    /**
-     * Returns whether the target offset is known.
-     *
-     * @return {@code true} if the target offset is known or
-     * {@code false} if not
-     */
-    public boolean hasTargetOffset() {
-        return hasAddress() && target.hasAddress();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected String argString() {
-        if (target == null) {
-            return "????";
-        }
-
-        return target.identifierString();
-    }
+    return target.identifierString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/VariableSizeInsn.java b/dx/src/com/android/jack/dx/dex/code/VariableSizeInsn.java
index 3110629..d3e5ba5 100644
--- a/dx/src/com/android/jack/dx/dex/code/VariableSizeInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/VariableSizeInsn.java
@@ -23,27 +23,26 @@
  * Pseudo-instruction base class for variable-sized instructions.
  */
 public abstract class VariableSizeInsn extends DalvInsn {
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     * @param registers {@code non-null;} source registers
-     */
-    public VariableSizeInsn(SourcePosition position,
-                            RegisterSpecList registers) {
-        super(Dops.SPECIAL_FORMAT, position, registers);
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   * @param registers {@code non-null;} source registers
+   */
+  public VariableSizeInsn(SourcePosition position, RegisterSpecList registers) {
+    super(Dops.SPECIAL_FORMAT, position, registers);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final DalvInsn withOpcode(Dop opcode) {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final DalvInsn withOpcode(Dop opcode) {
+    throw new RuntimeException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final DalvInsn withRegisterOffset(int delta) {
-        return withRegisters(getRegisters().withOffset(delta));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final DalvInsn withRegisterOffset(int delta) {
+    return withRegisters(getRegisters().withOffset(delta));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/ZeroSizeInsn.java b/dx/src/com/android/jack/dx/dex/code/ZeroSizeInsn.java
index d9a7f1b..4e1de10 100644
--- a/dx/src/com/android/jack/dx/dex/code/ZeroSizeInsn.java
+++ b/dx/src/com/android/jack/dx/dex/code/ZeroSizeInsn.java
@@ -26,37 +26,37 @@
  * about the code they are adjacent to.
  */
 public abstract class ZeroSizeInsn extends DalvInsn {
-    /**
-     * Constructs an instance. The output address of this instance is initially
-     * unknown ({@code -1}).
-     *
-     * @param position {@code non-null;} source position
-     */
-    public ZeroSizeInsn(SourcePosition position) {
-        super(Dops.SPECIAL_FORMAT, position, RegisterSpecList.EMPTY);
-    }
+  /**
+   * Constructs an instance. The output address of this instance is initially
+   * unknown ({@code -1}).
+   *
+   * @param position {@code non-null;} source position
+   */
+  public ZeroSizeInsn(SourcePosition position) {
+    super(Dops.SPECIAL_FORMAT, position, RegisterSpecList.EMPTY);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final int codeSize() {
-        return 0;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final int codeSize() {
+    return 0;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final void writeTo(AnnotatedOutput out) {
-        // Nothing to do here, for this class.
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final void writeTo(AnnotatedOutput out) {
+    // Nothing to do here, for this class.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final DalvInsn withOpcode(Dop opcode) {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final DalvInsn withOpcode(Dop opcode) {
+    throw new RuntimeException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public DalvInsn withRegisterOffset(int delta) {
-        return withRegisters(getRegisters().withOffset(delta));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public DalvInsn withRegisterOffset(int delta) {
+    return withRegisters(getRegisters().withOffset(delta));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form10t.java b/dx/src/com/android/jack/dx/dex/code/form/Form10t.java
index 6f27986..cc484ba 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form10t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form10t.java
@@ -26,61 +26,60 @@
  * for details.
  */
 public final class Form10t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form10t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form10t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form10t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form10t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    return branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!((insn instanceof TargetInsn) && (insn.getRegisters().size() == 0))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        return branchString(insn);
-    }
+    TargetInsn ti = (TargetInsn) insn;
+    return ti.hasTargetOffset() ? branchFits(ti) : true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    int offset = insn.getTargetOffset();
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 1;
-    }
+    // Note: A zero offset would fit, but it is prohibited by the spec.
+    return (offset != 0) && signedFitsInByte(offset);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!((insn instanceof TargetInsn) &&
-              (insn.getRegisters().size() == 0))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-        TargetInsn ti = (TargetInsn) insn;
-        return ti.hasTargetOffset() ? branchFits(ti) : true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        int offset = insn.getTargetOffset();
-
-        // Note: A zero offset would fit, but it is prohibited by the spec.
-        return (offset != 0) && signedFitsInByte(offset);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out, opcodeUnit(insn, (offset & 0xff)));
-    }
+    write(out, opcodeUnit(insn, (offset & 0xff)));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form10x.java b/dx/src/com/android/jack/dx/dex/code/form/Form10x.java
index 785f0fa..30dbd74 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form10x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form10x.java
@@ -26,47 +26,46 @@
  * for details.
  */
 public final class Form10x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form10x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form10x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form10x() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form10x() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        // This format has no arguments.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    // This format has no arguments.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 1;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 1;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        return (insn instanceof SimpleInsn) &&
-            (insn.getRegisters().size() == 0);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    return (insn instanceof SimpleInsn) && (insn.getRegisters().size() == 0);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        write(out, opcodeUnit(insn, 0));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    write(out, opcodeUnit(insn, 0));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form11n.java b/dx/src/com/android/jack/dx/dex/code/form/Form11n.java
index c30357e..7c4cf49 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form11n.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form11n.java
@@ -31,80 +31,77 @@
  * for details.
  */
 public final class Form11n extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form11n();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form11n();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form11n() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form11n() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 4);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+
+    if (!((insn instanceof CstInsn) && (regs.size() == 1)
+        && unsignedFitsInNibble(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 4);
-    }
+    CstLiteralBits cb = (CstLiteralBits) cst;
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 1;
-    }
+    return cb.fitsInInt() && signedFitsInNibble(cb.getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInNibble(regs.get(0).getReg()))) {
-            return false;
-        }
+    bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
+    return bits;
+  }
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int value = ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
 
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
-
-        CstLiteralBits cb = (CstLiteralBits) cst;
-
-        return cb.fitsInInt() && signedFitsInNibble(cb.getIntBits());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int value =
-            ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
-
-        write(out,
-              opcodeUnit(insn, makeByte(regs.get(0).getReg(), value & 0xf)));
-    }
+    write(out, opcodeUnit(insn, makeByte(regs.get(0).getReg(), value & 0xf)));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form11x.java b/dx/src/com/android/jack/dx/dex/code/form/Form11x.java
index a000202..24f35fa 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form11x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form11x.java
@@ -29,60 +29,59 @@
  * for details.
  */
 public final class Form11x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form11x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form11x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form11x() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form11x() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 1;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 1;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return (insn instanceof SimpleInsn) &&
-            (regs.size() == 1) &&
-            unsignedFitsInByte(regs.get(0).getReg());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return (insn instanceof SimpleInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        write(out, opcodeUnit(insn, regs.get(0).getReg()));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    write(out, opcodeUnit(insn, regs.get(0).getReg()));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form12x.java b/dx/src/com/android/jack/dx/dex/code/form/Form12x.java
index 4c93d27..e0aabe4 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form12x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form12x.java
@@ -30,133 +30,129 @@
  * for details.
  */
 public final class Form12x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form12x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form12x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form12x() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int sz = regs.size();
+
+    /*
+     * The (sz - 2) and (sz - 1) below makes this code work for
+     * both the two- and three-register ops. (See "case 3" in
+     * isCompatible(), below.)
      */
-    private Form12x() {
-        // This space intentionally left blank.
+
+return regs.get(sz - 2).regString() + ", " + regs.get(sz - 1).regString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!(insn instanceof SimpleInsn)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int sz = regs.size();
+    RegisterSpecList regs = insn.getRegisters();
+    RegisterSpec rs1;
+    RegisterSpec rs2;
 
+    switch (regs.size()) {
+      case 2: {
+        rs1 = regs.get(0);
+        rs2 = regs.get(1);
+        break;
+      }
+      case 3: {
         /*
-         * The (sz - 2) and (sz - 1) below makes this code work for
-         * both the two- and three-register ops. (See "case 3" in
-         * isCompatible(), below.)
+         * This format is allowed for ops that are effectively
+         * 3-arg but where the first two args are identical.
          */
-
-        return regs.get(sz - 2).regString() + ", " +
-            regs.get(sz - 1).regString();
+        rs1 = regs.get(1);
+        rs2 = regs.get(2);
+        if (rs1.getReg() != regs.get(0).getReg()) {
+          return false;
+        }
+        break;
+      }
+      default: {
+        return false;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+    return unsignedFitsInNibble(rs1.getReg()) && unsignedFitsInNibble(rs2.getReg());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 1;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
+    int r0 = regs.get(0).getReg();
+    int r1 = regs.get(1).getReg();
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!(insn instanceof SimpleInsn)) {
-            return false;
+    switch (regs.size()) {
+      case 2: {
+        bits.set(0, unsignedFitsInNibble(r0));
+        bits.set(1, unsignedFitsInNibble(r1));
+        break;
+      }
+      case 3: {
+        if (r0 != r1) {
+          bits.set(0, false);
+          bits.set(1, false);
+        } else {
+          boolean dstRegComp = unsignedFitsInNibble(r1);
+          bits.set(0, dstRegComp);
+          bits.set(1, dstRegComp);
         }
 
-        RegisterSpecList regs = insn.getRegisters();
-        RegisterSpec rs1;
-        RegisterSpec rs2;
-
-        switch (regs.size()) {
-            case 2: {
-                rs1 = regs.get(0);
-                rs2 = regs.get(1);
-                break;
-            }
-            case 3: {
-                /*
-                 * This format is allowed for ops that are effectively
-                 * 3-arg but where the first two args are identical.
-                 */
-                rs1 = regs.get(1);
-                rs2 = regs.get(2);
-                if (rs1.getReg() != regs.get(0).getReg()) {
-                    return false;
-                }
-                break;
-            }
-            default: {
-                return false;
-            }
-        }
-
-        return unsignedFitsInNibble(rs1.getReg()) &&
-            unsignedFitsInNibble(rs2.getReg());
+        bits.set(2, unsignedFitsInNibble(regs.get(2).getReg()));
+        break;
+      }
+      default: {
+        throw new AssertionError();
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
-        int r0 = regs.get(0).getReg();
-        int r1 = regs.get(1).getReg();
+    return bits;
+  }
 
-        switch (regs.size()) {
-          case 2: {
-            bits.set(0, unsignedFitsInNibble(r0));
-            bits.set(1, unsignedFitsInNibble(r1));
-            break;
-          }
-          case 3: {
-            if (r0 != r1) {
-                bits.set(0, false);
-                bits.set(1, false);
-            } else {
-                boolean dstRegComp = unsignedFitsInNibble(r1);
-                bits.set(0, dstRegComp);
-                bits.set(1, dstRegComp);
-            }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int sz = regs.size();
 
-            bits.set(2, unsignedFitsInNibble(regs.get(2).getReg()));
-            break;
-          }
-          default: {
-            throw new AssertionError();
-          }
-        }
+    /*
+     * The (sz - 2) and (sz - 1) below makes this code work for
+     * both the two- and three-register ops. (See "case 3" in
+     * isCompatible(), above.)
+     */
 
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int sz = regs.size();
-
-        /*
-         * The (sz - 2) and (sz - 1) below makes this code work for
-         * both the two- and three-register ops. (See "case 3" in
-         * isCompatible(), above.)
-         */
-
-        write(out, opcodeUnit(insn,
-                              makeByte(regs.get(sz - 2).getReg(),
-                                       regs.get(sz - 1).getReg())));
-    }
+write(out, opcodeUnit(insn, makeByte(regs.get(sz - 2).getReg(), regs.get(sz - 1).getReg())));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form20t.java b/dx/src/com/android/jack/dx/dex/code/form/Form20t.java
index e05042a..8044c02 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form20t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form20t.java
@@ -26,61 +26,60 @@
  * for details.
  */
 public final class Form20t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form20t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form20t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form20t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form20t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    return branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!((insn instanceof TargetInsn) && (insn.getRegisters().size() == 0))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        return branchString(insn);
-    }
+    TargetInsn ti = (TargetInsn) insn;
+    return ti.hasTargetOffset() ? branchFits(ti) : true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    int offset = insn.getTargetOffset();
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    // Note: A zero offset would fit, but it is prohibited by the spec.
+    return (offset != 0) && signedFitsInShort(offset);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!((insn instanceof TargetInsn) &&
-              (insn.getRegisters().size() == 0))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-        TargetInsn ti = (TargetInsn) insn;
-        return ti.hasTargetOffset() ? branchFits(ti) : true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        int offset = insn.getTargetOffset();
-
-        // Note: A zero offset would fit, but it is prohibited by the spec.
-        return (offset != 0) && signedFitsInShort(offset);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out, opcodeUnit(insn, 0), (short) offset);
-    }
+    write(out, opcodeUnit(insn, 0), (short) offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form21c.java b/dx/src/com/android/jack/dx/dex/code/form/Form21c.java
index 90415f1..fa77e8f 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form21c.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form21c.java
@@ -34,116 +34,112 @@
  * for details.
  */
 public final class Form21c extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form21c();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form21c();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form21c() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form21c() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + cstString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    if (noteIndices) {
+      return cstComment(insn);
+    } else {
+      return "";
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!(insn instanceof CstInsn)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + cstString(insn);
-    }
+    RegisterSpecList regs = insn.getRegisters();
+    RegisterSpec reg;
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        if (noteIndices) {
-            return cstComment(insn);
-        } else {
-            return "";
+    switch (regs.size()) {
+      case 1: {
+        reg = regs.get(0);
+        break;
+      }
+      case 2: {
+        /*
+         * This format is allowed for ops that are effectively
+         * 2-arg but where the two args are identical.
+         */
+        reg = regs.get(0);
+        if (reg.getReg() != regs.get(1).getReg()) {
+          return false;
         }
+        break;
+      }
+      default: {
+        return false;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
+    if (!unsignedFitsInByte(reg.getReg())) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!(insn instanceof CstInsn)) {
-            return false;
-        }
+    CstInsn ci = (CstInsn) insn;
+    int cpi = ci.getIndex();
+    Constant cst = ci.getConstant();
 
-        RegisterSpecList regs = insn.getRegisters();
-        RegisterSpec reg;
-
-        switch (regs.size()) {
-            case 1: {
-                reg = regs.get(0);
-                break;
-            }
-            case 2: {
-                /*
-                 * This format is allowed for ops that are effectively
-                 * 2-arg but where the two args are identical.
-                 */
-                reg = regs.get(0);
-                if (reg.getReg() != regs.get(1).getReg()) {
-                    return false;
-                }
-                break;
-            }
-            default: {
-                return false;
-            }
-        }
-
-        if (!unsignedFitsInByte(reg.getReg())) {
-            return false;
-        }
-
-        CstInsn ci = (CstInsn) insn;
-        int cpi = ci.getIndex();
-        Constant cst = ci.getConstant();
-
-        if (! unsignedFitsInShort(cpi)) {
-            return false;
-        }
-
-        return (cst instanceof CstType) ||
-            (cst instanceof CstFieldRef) ||
-            (cst instanceof CstString);
+    if (!unsignedFitsInShort(cpi)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int sz = regs.size();
-        BitSet bits = new BitSet(sz);
-        boolean compat = unsignedFitsInByte(regs.get(0).getReg());
+    return (cst instanceof CstType) || (cst instanceof CstFieldRef) || (cst instanceof CstString);
+  }
 
-        if (sz == 1) {
-            bits.set(0, compat);
-        } else {
-            if (regs.get(0).getReg() == regs.get(1).getReg()) {
-                bits.set(0, compat);
-                bits.set(1, compat);
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int sz = regs.size();
+    BitSet bits = new BitSet(sz);
+    boolean compat = unsignedFitsInByte(regs.get(0).getReg());
 
-        return bits;
+    if (sz == 1) {
+      bits.set(0, compat);
+    } else {
+      if (regs.get(0).getReg() == regs.get(1).getReg()) {
+        bits.set(0, compat);
+        bits.set(1, compat);
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int cpi = ((CstInsn) insn).getIndex();
+    return bits;
+  }
 
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              (short) cpi);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int cpi = ((CstInsn) insn).getIndex();
+
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), (short) cpi);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form21h.java b/dx/src/com/android/jack/dx/dex/code/form/Form21h.java
index 4a57f0a..585fa53 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form21h.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form21h.java
@@ -31,96 +31,93 @@
  * for details.
  */
 public final class Form21h extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form21h();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form21h();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form21h() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form21h() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return literalBitsComment(value, (regs.get(0).getCategory() == 1) ? 32 : 64);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstLiteralBits cb = (CstLiteralBits) cst;
 
-        return
-            literalBitsComment(value,
-                    (regs.get(0).getCategory() == 1) ? 32 : 64);
+    // Where the high bits are depends on the category of the target.
+    if (regs.get(0).getCategory() == 1) {
+      int bits = cb.getIntBits();
+      return ((bits & 0xffff) == 0);
+    } else {
+      long bits = cb.getLongBits();
+      return ((bits & 0xffffffffffffL) == 0);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
+
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits cb = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    short bits;
+
+    // Where the high bits are depends on the category of the target.
+    if (regs.get(0).getCategory() == 1) {
+      bits = (short) (cb.getIntBits() >>> 16);
+    } else {
+      bits = (short) (cb.getLongBits() >>> 48);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
-
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
-
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
-
-        CstLiteralBits cb = (CstLiteralBits) cst;
-
-        // Where the high bits are depends on the category of the target.
-        if (regs.get(0).getCategory() == 1) {
-            int bits = cb.getIntBits();
-            return ((bits & 0xffff) == 0);
-        } else {
-            long bits = cb.getLongBits();
-            return ((bits & 0xffffffffffffL) == 0);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits cb = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        short bits;
-
-        // Where the high bits are depends on the category of the target.
-        if (regs.get(0).getCategory() == 1) {
-            bits = (short) (cb.getIntBits() >>> 16);
-        } else {
-            bits = (short) (cb.getLongBits() >>> 48);
-        }
-
-        write(out, opcodeUnit(insn, regs.get(0).getReg()), bits);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), bits);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form21s.java b/dx/src/com/android/jack/dx/dex/code/form/Form21s.java
index 57dd12a..0852541 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form21s.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form21s.java
@@ -31,80 +31,76 @@
  * for details.
  */
 public final class Form21s extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form21s();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form21s();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form21s() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form21s() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 16);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 16);
-    }
+    CstLiteralBits cb = (CstLiteralBits) cst;
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    return cb.fitsInInt() && signedFitsInShort(cb.getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int value = ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
 
-        CstLiteralBits cb = (CstLiteralBits) cst;
-
-        return cb.fitsInInt() && signedFitsInShort(cb.getIntBits());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int value =
-            ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
-
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              (short) value);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), (short) value);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form21t.java b/dx/src/com/android/jack/dx/dex/code/form/Form21t.java
index 5836a5e..955eced 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form21t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form21t.java
@@ -29,78 +29,75 @@
  * for details.
  */
 public final class Form21t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form21t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form21t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form21t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form21t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+
+    if (!((insn instanceof TargetInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + branchString(insn);
-    }
+    TargetInsn ti = (TargetInsn) insn;
+    return ti.hasTargetOffset() ? branchFits(ti) : true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    int offset = insn.getTargetOffset();
 
-        if (!((insn instanceof TargetInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
+    // Note: A zero offset would fit, but it is prohibited by the spec.
+    return (offset != 0) && signedFitsInShort(offset);
+  }
 
-        TargetInsn ti = (TargetInsn) insn;
-        return ti.hasTargetOffset() ? branchFits(ti) : true;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        int offset = insn.getTargetOffset();
-
-        // Note: A zero offset would fit, but it is prohibited by the spec.
-        return (offset != 0) && signedFitsInShort(offset);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              (short) offset);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), (short) offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form22b.java b/dx/src/com/android/jack/dx/dex/code/form/Form22b.java
index a09b6c6..fcae319 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form22b.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form22b.java
@@ -31,83 +31,79 @@
  * for details.
  */
 public final class Form22b extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form22b();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form22b();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form22b() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form22b() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + regs.get(1).regString() + ", "
+        + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 8);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 2)
+        && unsignedFitsInByte(regs.get(0).getReg()) && unsignedFitsInByte(regs.get(1).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + regs.get(1).regString() +
-            ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 8);
-    }
+    CstLiteralBits cb = (CstLiteralBits) cst;
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    return cb.fitsInInt() && signedFitsInByte(cb.getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 2) &&
-              unsignedFitsInByte(regs.get(0).getReg()) &&
-              unsignedFitsInByte(regs.get(1).getReg()))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInByte(regs.get(1).getReg()));
+    return bits;
+  }
 
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int value = ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
 
-        CstLiteralBits cb = (CstLiteralBits) cst;
-
-        return cb.fitsInInt() && signedFitsInByte(cb.getIntBits());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInByte(regs.get(1).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int value =
-            ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
-
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              codeUnit(regs.get(1).getReg(), value & 0xff));
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()),
+        codeUnit(regs.get(1).getReg(), value & 0xff));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form22c.java b/dx/src/com/android/jack/dx/dex/code/form/Form22c.java
index d170e06..fdf51c4 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form22c.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form22c.java
@@ -32,84 +32,78 @@
  * for details.
  */
 public final class Form22c extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form22c();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form22c();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form22c() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form22c() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + regs.get(1).regString() + ", " + cstString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    if (noteIndices) {
+      return cstComment(insn);
+    } else {
+      return "";
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 2)
+        && unsignedFitsInNibble(regs.get(0).getReg())
+        && unsignedFitsInNibble(regs.get(1).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + regs.get(1).regString() +
-            ", " + cstString(insn);
+    CstInsn ci = (CstInsn) insn;
+    int cpi = ci.getIndex();
+
+    if (!unsignedFitsInShort(cpi)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        if (noteIndices) {
-            return cstComment(insn);
-        } else {
-            return "";
-        }
-    }
+    Constant cst = ci.getConstant();
+    return (cst instanceof CstType) || (cst instanceof CstFieldRef);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 2) &&
-              unsignedFitsInNibble(regs.get(0).getReg()) &&
-              unsignedFitsInNibble(regs.get(1).getReg()))) {
-            return false;
-        }
+    bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
+    return bits;
+  }
 
-        CstInsn ci = (CstInsn) insn;
-        int cpi = ci.getIndex();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int cpi = ((CstInsn) insn).getIndex();
 
-        if (! unsignedFitsInShort(cpi)) {
-            return false;
-        }
-
-        Constant cst = ci.getConstant();
-        return (cst instanceof CstType) ||
-            (cst instanceof CstFieldRef);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
-
-        bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int cpi = ((CstInsn) insn).getIndex();
-
-        write(out,
-              opcodeUnit(insn,
-                         makeByte(regs.get(0).getReg(), regs.get(1).getReg())),
-              (short) cpi);
-    }
+    write(out, opcodeUnit(insn, makeByte(regs.get(0).getReg(), regs.get(1).getReg())), (short) cpi);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form22s.java b/dx/src/com/android/jack/dx/dex/code/form/Form22s.java
index bbd66a3..1fcbd7601 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form22s.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form22s.java
@@ -31,84 +31,80 @@
  * for details.
  */
 public final class Form22s extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form22s();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form22s();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form22s() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form22s() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + regs.get(1).regString() + ", "
+        + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 16);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 2)
+        && unsignedFitsInNibble(regs.get(0).getReg())
+        && unsignedFitsInNibble(regs.get(1).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + regs.get(1).regString()
-            + ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 16);
-    }
+    CstLiteralBits cb = (CstLiteralBits) cst;
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    return cb.fitsInInt() && signedFitsInShort(cb.getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 2) &&
-              unsignedFitsInNibble(regs.get(0).getReg()) &&
-              unsignedFitsInNibble(regs.get(1).getReg()))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+    bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
+    return bits;
+  }
 
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int value = ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
 
-        CstLiteralBits cb = (CstLiteralBits) cst;
-
-        return cb.fitsInInt() && signedFitsInShort(cb.getIntBits());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
-
-        bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int value =
-            ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
-
-        write(out,
-              opcodeUnit(insn,
-                         makeByte(regs.get(0).getReg(), regs.get(1).getReg())),
-              (short) value);
-    }
+    write(out, opcodeUnit(insn, makeByte(regs.get(0).getReg(), regs.get(1).getReg())),
+        (short) value);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form22t.java b/dx/src/com/android/jack/dx/dex/code/form/Form22t.java
index 3e9cfdb..66dbde8 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form22t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form22t.java
@@ -29,82 +29,78 @@
  * for details.
  */
 public final class Form22t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form22t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form22t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form22t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form22t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + regs.get(1).regString() + ", " + branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+
+    if (!((insn instanceof TargetInsn) && (regs.size() == 2)
+        && unsignedFitsInNibble(regs.get(0).getReg())
+        && unsignedFitsInNibble(regs.get(1).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + regs.get(1).regString() +
-            ", " + branchString(insn);
-    }
+    TargetInsn ti = (TargetInsn) insn;
+    return ti.hasTargetOffset() ? branchFits(ti) : true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+    bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    int offset = insn.getTargetOffset();
 
-        if (!((insn instanceof TargetInsn) &&
-              (regs.size() == 2) &&
-              unsignedFitsInNibble(regs.get(0).getReg()) &&
-              unsignedFitsInNibble(regs.get(1).getReg()))) {
-            return false;
-        }
+    // Note: A zero offset would fit, but it is prohibited by the spec.
+    return (offset != 0) && signedFitsInShort(offset);
+  }
 
-        TargetInsn ti = (TargetInsn) insn;
-        return ti.hasTargetOffset() ? branchFits(ti) : true;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
-
-        bits.set(0, unsignedFitsInNibble(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInNibble(regs.get(1).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        int offset = insn.getTargetOffset();
-
-        // Note: A zero offset would fit, but it is prohibited by the spec.
-        return (offset != 0) && signedFitsInShort(offset);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out,
-              opcodeUnit(insn,
-                         makeByte(regs.get(0).getReg(), regs.get(1).getReg())),
-              (short) offset);
-    }
+    write(out, opcodeUnit(insn, makeByte(regs.get(0).getReg(), regs.get(1).getReg())),
+        (short) offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form22x.java b/dx/src/com/android/jack/dx/dex/code/form/Form22x.java
index f9e4d9c..e505566 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form22x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form22x.java
@@ -29,65 +29,61 @@
  * for details.
  */
 public final class Form22x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form22x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form22x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form22x() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form22x() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + regs.get(1).regString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + regs.get(1).regString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
 
-        return (insn instanceof SimpleInsn) &&
-            (regs.size() == 2) &&
-            unsignedFitsInByte(regs.get(0).getReg()) &&
-            unsignedFitsInShort(regs.get(1).getReg());
-    }
+    return (insn instanceof SimpleInsn) && (regs.size() == 2)
+        && unsignedFitsInByte(regs.get(0).getReg()) && unsignedFitsInShort(regs.get(1).getReg());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInShort(regs.get(1).getReg()));
-        return bits;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInShort(regs.get(1).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              (short) regs.get(1).getReg());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), (short) regs.get(1).getReg());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form23x.java b/dx/src/com/android/jack/dx/dex/code/form/Form23x.java
index 3261788..40dc9c0 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form23x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form23x.java
@@ -29,68 +29,65 @@
  * for details.
  */
 public final class Form23x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form23x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form23x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form23x() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form23x() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + regs.get(1).regString() +
-            ", " + regs.get(2).regString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + regs.get(1).regString() + ", "
+        + regs.get(2).regString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 2;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 2;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
 
-        return (insn instanceof SimpleInsn) &&
-            (regs.size() == 3) &&
-            unsignedFitsInByte(regs.get(0).getReg()) &&
-            unsignedFitsInByte(regs.get(1).getReg()) &&
-            unsignedFitsInByte(regs.get(2).getReg());
-    }
+    return (insn instanceof SimpleInsn) && (regs.size() == 3)
+        && unsignedFitsInByte(regs.get(0).getReg()) && unsignedFitsInByte(regs.get(1).getReg())
+        && unsignedFitsInByte(regs.get(2).getReg());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(3);
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(3);
 
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInByte(regs.get(1).getReg()));
-        bits.set(2, unsignedFitsInByte(regs.get(2).getReg()));
-        return bits;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInByte(regs.get(1).getReg()));
+    bits.set(2, unsignedFitsInByte(regs.get(2).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        write(out,
-              opcodeUnit(insn, regs.get(0).getReg()),
-              codeUnit(regs.get(1).getReg(), regs.get(2).getReg()));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    write(out, opcodeUnit(insn, regs.get(0).getReg()),
+        codeUnit(regs.get(1).getReg(), regs.get(2).getReg()));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form30t.java b/dx/src/com/android/jack/dx/dex/code/form/Form30t.java
index 743f806..579253f 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form30t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form30t.java
@@ -26,57 +26,56 @@
  * for details.
  */
 public final class Form30t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form30t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form30t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form30t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form30t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    return branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!((insn instanceof TargetInsn) && (insn.getRegisters().size() == 0))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        return branchString(insn);
-    }
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!((insn instanceof TargetInsn) &&
-              (insn.getRegisters().size() == 0))) {
-            return false;
-        }
-
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out, opcodeUnit(insn, 0), offset);
-    }
+    write(out, opcodeUnit(insn, 0), offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form31c.java b/dx/src/com/android/jack/dx/dex/code/form/Form31c.java
index 12e5f14..cd4877a 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form31c.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form31c.java
@@ -34,109 +34,107 @@
  * for details.
  */
 public final class Form31c extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form31c();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form31c();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form31c() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form31c() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + cstString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    if (noteIndices) {
+      return cstComment(insn);
+    } else {
+      return "";
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!(insn instanceof CstInsn)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + cstString(insn);
-    }
+    RegisterSpecList regs = insn.getRegisters();
+    RegisterSpec reg;
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        if (noteIndices) {
-            return cstComment(insn);
-        } else {
-            return "";
+    switch (regs.size()) {
+      case 1: {
+        reg = regs.get(0);
+        break;
+      }
+      case 2: {
+        /*
+         * This format is allowed for ops that are effectively
+         * 2-arg but where the two args are identical.
+         */
+        reg = regs.get(0);
+        if (reg.getReg() != regs.get(1).getReg()) {
+          return false;
         }
+        break;
+      }
+      default: {
+        return false;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
+    if (!unsignedFitsInByte(reg.getReg())) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!(insn instanceof CstInsn)) {
-            return false;
-        }
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        RegisterSpecList regs = insn.getRegisters();
-        RegisterSpec reg;
+    return (cst instanceof CstType) || (cst instanceof CstFieldRef) || (cst instanceof CstString);
+  }
 
-        switch (regs.size()) {
-            case 1: {
-                reg = regs.get(0);
-                break;
-            }
-            case 2: {
-                /*
-                 * This format is allowed for ops that are effectively
-                 * 2-arg but where the two args are identical.
-                 */
-                reg = regs.get(0);
-                if (reg.getReg() != regs.get(1).getReg()) {
-                    return false;
-                }
-                break;
-            }
-            default: {
-                return false;
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int sz = regs.size();
+    BitSet bits = new BitSet(sz);
+    boolean compat = unsignedFitsInByte(regs.get(0).getReg());
 
-        if (!unsignedFitsInByte(reg.getReg())) {
-            return false;
-        }
-
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
-
-        return (cst instanceof CstType) ||
-            (cst instanceof CstFieldRef) ||
-            (cst instanceof CstString);
+    if (sz == 1) {
+      bits.set(0, compat);
+    } else {
+      if (regs.get(0).getReg() == regs.get(1).getReg()) {
+        bits.set(0, compat);
+        bits.set(1, compat);
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int sz = regs.size();
-        BitSet bits = new BitSet(sz);
-        boolean compat = unsignedFitsInByte(regs.get(0).getReg());
+    return bits;
+  }
 
-        if (sz == 1) {
-            bits.set(0, compat);
-        } else {
-            if (regs.get(0).getReg() == regs.get(1).getReg()) {
-                bits.set(0, compat);
-                bits.set(1, compat);
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int cpi = ((CstInsn) insn).getIndex();
 
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int cpi = ((CstInsn) insn).getIndex();
-
-        write(out, opcodeUnit(insn, regs.get(0).getReg()), cpi);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), cpi);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form31i.java b/dx/src/com/android/jack/dx/dex/code/form/Form31i.java
index 8e45f18..4a10162 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form31i.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form31i.java
@@ -31,76 +31,74 @@
  * for details.
  */
 public final class Form31i extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form31i();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form31i();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form31i() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form31i() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 32);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + literalBitsString(value);
+    if (!(cst instanceof CstLiteralBits)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 32);
-    }
+    return ((CstLiteralBits) cst).fitsInInt();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int value = ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
 
-        if (!(cst instanceof CstLiteralBits)) {
-            return false;
-        }
-
-        return ((CstLiteralBits) cst).fitsInInt();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int value =
-            ((CstLiteralBits) ((CstInsn) insn).getConstant()).getIntBits();
-
-        write(out, opcodeUnit(insn, regs.get(0).getReg()), value);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), value);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form31t.java b/dx/src/com/android/jack/dx/dex/code/form/Form31t.java
index 8573615..603fd18 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form31t.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form31t.java
@@ -29,72 +29,71 @@
  * for details.
  */
 public final class Form31t extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form31t();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form31t();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form31t() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form31t() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + branchString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    return branchComment(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+
+    if (!((insn instanceof TargetInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + branchString(insn);
-    }
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        return branchComment(insn);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public boolean branchFits(TargetInsn insn) {
+    return true;
+  }
 
-        if (!((insn instanceof TargetInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int offset = ((TargetInsn) insn).getTargetOffset();
 
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean branchFits(TargetInsn insn) {
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int offset = ((TargetInsn) insn).getTargetOffset();
-
-        write(out, opcodeUnit(insn, regs.get(0).getReg()), offset);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form32x.java b/dx/src/com/android/jack/dx/dex/code/form/Form32x.java
index 2f856ce..07d18a2 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form32x.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form32x.java
@@ -29,66 +29,61 @@
  * for details.
  */
 public final class Form32x extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form32x();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form32x();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form32x() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form32x() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return regs.get(0).regString() + ", " + regs.get(1).regString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return regs.get(0).regString() + ", " + regs.get(1).regString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        // This format has no comment.
-        return "";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    // This format has no comment.
+    return "";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        return (insn instanceof SimpleInsn) &&
-            (regs.size() == 2) &&
-            unsignedFitsInShort(regs.get(0).getReg()) &&
-            unsignedFitsInShort(regs.get(1).getReg());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    return (insn instanceof SimpleInsn) && (regs.size() == 2)
+        && unsignedFitsInShort(regs.get(0).getReg()) && unsignedFitsInShort(regs.get(1).getReg());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(2);
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(2);
 
-        bits.set(0, unsignedFitsInShort(regs.get(0).getReg()));
-        bits.set(1, unsignedFitsInShort(regs.get(1).getReg()));
-        return bits;
-    }
+    bits.set(0, unsignedFitsInShort(regs.get(0).getReg()));
+    bits.set(1, unsignedFitsInShort(regs.get(1).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
 
-        write(out,
-              opcodeUnit(insn, 0),
-              (short) regs.get(0).getReg(),
-              (short) regs.get(1).getReg());
-    }
+    write(out, opcodeUnit(insn, 0), (short) regs.get(0).getReg(), (short) regs.get(1).getReg());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form35c.java b/dx/src/com/android/jack/dx/dex/code/form/Form35c.java
index df277ef..9fd6a03 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form35c.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form35c.java
@@ -34,178 +34,172 @@
  * for details.
  */
 public final class Form35c extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form35c();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form35c();
 
-    /** Maximal number of operands */
-    private static final int MAX_NUM_OPS = 5;
+  /** Maximal number of operands */
+  private static final int MAX_NUM_OPS = 5;
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form35c() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form35c() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = explicitize(insn.getRegisters());
+    return regListString(regs) + ", " + cstString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    if (noteIndices) {
+      return cstComment(insn);
+    } else {
+      return "";
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!(insn instanceof CstInsn)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = explicitize(insn.getRegisters());
-        return regListString(regs) + ", " + cstString(insn);
+    CstInsn ci = (CstInsn) insn;
+    int cpi = ci.getIndex();
+
+    if (!unsignedFitsInShort(cpi)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        if (noteIndices) {
-            return cstComment(insn);
-        } else {
-            return "";
-        }
+    Constant cst = ci.getConstant();
+    if (!((cst instanceof CstMethodRef) || (cst instanceof CstType))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
+    RegisterSpecList regs = ci.getRegisters();
+    return (wordCount(regs) >= 0);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int sz = regs.size();
+    BitSet bits = new BitSet(sz);
+
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec reg = regs.get(i);
+      /*
+       * The check below adds (category - 1) to the register, to
+       * account for the fact that the second half of a
+       * category-2 register has to be represented explicitly in
+       * the result.
+       */
+      bits.set(i, unsignedFitsInNibble(reg.getReg() + reg.getCategory() - 1));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!(insn instanceof CstInsn)) {
-            return false;
-        }
+    return bits;
+  }
 
-        CstInsn ci = (CstInsn) insn;
-        int cpi = ci.getIndex();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    int cpi = ((CstInsn) insn).getIndex();
+    RegisterSpecList regs = explicitize(insn.getRegisters());
+    int sz = regs.size();
+    int r0 = (sz > 0) ? regs.get(0).getReg() : 0;
+    int r1 = (sz > 1) ? regs.get(1).getReg() : 0;
+    int r2 = (sz > 2) ? regs.get(2).getReg() : 0;
+    int r3 = (sz > 3) ? regs.get(3).getReg() : 0;
+    int r4 = (sz > 4) ? regs.get(4).getReg() : 0;
 
-        if (! unsignedFitsInShort(cpi)) {
-            return false;
-        }
+    write(out, opcodeUnit(insn, makeByte(r4, sz)), // encode the fifth operand here
+        (short) cpi, codeUnit(r0, r1, r2, r3));
+  }
 
-        Constant cst = ci.getConstant();
-        if (!((cst instanceof CstMethodRef) ||
-              (cst instanceof CstType))) {
-            return false;
-        }
+  /**
+   * Gets the number of words required for the given register list, where
+   * category-2 values count as two words. Return {@code -1} if the
+   * list requires more than five words or contains registers that need
+   * more than a nibble to identify them.
+   *
+   * @param regs {@code non-null;} the register list in question
+   * @return {@code >= -1;} the number of words required, or {@code -1}
+   * if the list couldn't possibly fit in this format
+   */
+  private static int wordCount(RegisterSpecList regs) {
+    int sz = regs.size();
 
-        RegisterSpecList regs = ci.getRegisters();
-        return (wordCount(regs) >= 0);
+    if (sz > MAX_NUM_OPS) {
+      // It can't possibly fit.
+      return -1;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int sz = regs.size();
-        BitSet bits = new BitSet(sz);
+    int result = 0;
 
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec reg = regs.get(i);
-            /*
-             * The check below adds (category - 1) to the register, to
-             * account for the fact that the second half of a
-             * category-2 register has to be represented explicitly in
-             * the result.
-             */
-            bits.set(i, unsignedFitsInNibble(reg.getReg() +
-                                             reg.getCategory() - 1));
-        }
-
-        return bits;
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec one = regs.get(i);
+      result += one.getCategory();
+      /*
+       * The check below adds (category - 1) to the register, to
+       * account for the fact that the second half of a
+       * category-2 register has to be represented explicitly in
+       * the result.
+       */
+      if (!unsignedFitsInNibble(one.getReg() + one.getCategory() - 1)) {
+        return -1;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        int cpi = ((CstInsn) insn).getIndex();
-        RegisterSpecList regs = explicitize(insn.getRegisters());
-        int sz = regs.size();
-        int r0 = (sz > 0) ? regs.get(0).getReg() : 0;
-        int r1 = (sz > 1) ? regs.get(1).getReg() : 0;
-        int r2 = (sz > 2) ? regs.get(2).getReg() : 0;
-        int r3 = (sz > 3) ? regs.get(3).getReg() : 0;
-        int r4 = (sz > 4) ? regs.get(4).getReg() : 0;
+    return (result <= MAX_NUM_OPS) ? result : -1;
+  }
 
-        write(out,
-              opcodeUnit(insn,
-                         makeByte(r4, sz)), // encode the fifth operand here
-              (short) cpi,
-              codeUnit(r0, r1, r2, r3));
+  /**
+   * Returns a register list which is equivalent to the given one,
+   * except that it splits category-2 registers into two explicit
+   * entries. This returns the original list if no modification is
+   * required
+   *
+   * @param orig {@code non-null;} the original list
+   * @return {@code non-null;} the list with the described transformation
+   */
+  private static RegisterSpecList explicitize(RegisterSpecList orig) {
+    int wordCount = wordCount(orig);
+    int sz = orig.size();
+
+    if (wordCount == sz) {
+      return orig;
     }
 
-    /**
-     * Gets the number of words required for the given register list, where
-     * category-2 values count as two words. Return {@code -1} if the
-     * list requires more than five words or contains registers that need
-     * more than a nibble to identify them.
-     *
-     * @param regs {@code non-null;} the register list in question
-     * @return {@code >= -1;} the number of words required, or {@code -1}
-     * if the list couldn't possibly fit in this format
-     */
-    private static int wordCount(RegisterSpecList regs) {
-        int sz = regs.size();
+    RegisterSpecList result = new RegisterSpecList(wordCount);
+    int wordAt = 0;
 
-        if (sz > MAX_NUM_OPS) {
-            // It can't possibly fit.
-            return -1;
-        }
-
-        int result = 0;
-
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec one = regs.get(i);
-            result += one.getCategory();
-            /*
-             * The check below adds (category - 1) to the register, to
-             * account for the fact that the second half of a
-             * category-2 register has to be represented explicitly in
-             * the result.
-             */
-            if (!unsignedFitsInNibble(one.getReg() + one.getCategory() - 1)) {
-                return -1;
-            }
-        }
-
-        return (result <= MAX_NUM_OPS) ? result : -1;
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec one = orig.get(i);
+      result.set(wordAt, one);
+      if (one.getCategory() == 2) {
+        result.set(wordAt + 1, RegisterSpec.make(one.getReg() + 1, Type.VOID));
+        wordAt += 2;
+      } else {
+        wordAt++;
+      }
     }
 
-    /**
-     * Returns a register list which is equivalent to the given one,
-     * except that it splits category-2 registers into two explicit
-     * entries. This returns the original list if no modification is
-     * required
-     *
-     * @param orig {@code non-null;} the original list
-     * @return {@code non-null;} the list with the described transformation
-     */
-    private static RegisterSpecList explicitize(RegisterSpecList orig) {
-        int wordCount = wordCount(orig);
-        int sz = orig.size();
-
-        if (wordCount == sz) {
-            return orig;
-        }
-
-        RegisterSpecList result = new RegisterSpecList(wordCount);
-        int wordAt = 0;
-
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec one = orig.get(i);
-            result.set(wordAt, one);
-            if (one.getCategory() == 2) {
-                result.set(wordAt + 1,
-                           RegisterSpec.make(one.getReg() + 1, Type.VOID));
-                wordAt += 2;
-            } else {
-                wordAt++;
-            }
-        }
-
-        result.setImmutable();
-        return result;
-    }
+    result.setImmutable();
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form3rc.java b/dx/src/com/android/jack/dx/dex/code/form/Form3rc.java
index 35adc7a..ec0ca88 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form3rc.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form3rc.java
@@ -30,77 +30,72 @@
  * for details.
  */
 public final class Form3rc extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form3rc();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form3rc();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form3rc() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form3rc() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    return regRangeString(insn.getRegisters()) + ", " + cstString(insn);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    if (noteIndices) {
+      return cstComment(insn);
+    } else {
+      return "";
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 3;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    if (!(insn instanceof CstInsn)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        return regRangeString(insn.getRegisters()) + ", " +
-            cstString(insn);
+    CstInsn ci = (CstInsn) insn;
+    int cpi = ci.getIndex();
+    Constant cst = ci.getConstant();
+
+    if (!unsignedFitsInShort(cpi)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        if (noteIndices) {
-            return cstComment(insn);
-        } else {
-            return "";
-        }
+    if (!((cst instanceof CstMethodRef) || (cst instanceof CstType))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 3;
-    }
+    RegisterSpecList regs = ci.getRegisters();
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        if (!(insn instanceof CstInsn)) {
-            return false;
-        }
+    return (regs.size() == 0) || (isRegListSequential(regs)
+        && unsignedFitsInShort(regs.get(0).getReg()) && unsignedFitsInByte(regs.getWordCount()));
+  }
 
-        CstInsn ci = (CstInsn) insn;
-        int cpi = ci.getIndex();
-        Constant cst = ci.getConstant();
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    int cpi = ((CstInsn) insn).getIndex();
+    int firstReg = (regs.size() == 0) ? 0 : regs.get(0).getReg();
+    int count = regs.getWordCount();
 
-        if (! unsignedFitsInShort(cpi)) {
-            return false;
-        }
-
-        if (!((cst instanceof CstMethodRef) ||
-              (cst instanceof CstType))) {
-            return false;
-        }
-
-        RegisterSpecList regs = ci.getRegisters();
-        int sz = regs.size();
-
-        return (regs.size() == 0) ||
-            (isRegListSequential(regs) &&
-             unsignedFitsInShort(regs.get(0).getReg()) &&
-             unsignedFitsInByte(regs.getWordCount()));
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        int cpi = ((CstInsn) insn).getIndex();
-        int firstReg = (regs.size() == 0) ? 0 : regs.get(0).getReg();
-        int count = regs.getWordCount();
-
-        write(out, opcodeUnit(insn, count), (short) cpi, (short) firstReg);
-    }
+    write(out, opcodeUnit(insn, count), (short) cpi, (short) firstReg);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/Form51l.java b/dx/src/com/android/jack/dx/dex/code/form/Form51l.java
index 9dd086f..5555149 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/Form51l.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/Form51l.java
@@ -32,72 +32,70 @@
  * for details.
  */
 public final class Form51l extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new Form51l();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new Form51l();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private Form51l() {
-        // This space intentionally left blank.
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private Form51l() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+
+    return regs.get(0).regString() + ", " + literalBitsString(value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    return literalBitsComment(value, 64);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    return 5;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    if (!((insn instanceof CstInsn) && (regs.size() == 1)
+        && unsignedFitsInByte(regs.get(0).getReg()))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
+    CstInsn ci = (CstInsn) insn;
+    Constant cst = ci.getConstant();
 
-        return regs.get(0).regString() + ", " + literalBitsString(value);
-    }
+    return (cst instanceof CstLiteral64);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        CstLiteralBits value = (CstLiteralBits) ((CstInsn) insn).getConstant();
-        return literalBitsComment(value, 64);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public BitSet compatibleRegs(DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    BitSet bits = new BitSet(1);
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        return 5;
-    }
+    bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
+    return bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        if (!((insn instanceof CstInsn) &&
-              (regs.size() == 1) &&
-              unsignedFitsInByte(regs.get(0).getReg()))) {
-            return false;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    RegisterSpecList regs = insn.getRegisters();
+    long value = ((CstLiteral64) ((CstInsn) insn).getConstant()).getLongBits();
 
-        CstInsn ci = (CstInsn) insn;
-        Constant cst = ci.getConstant();
-
-        return (cst instanceof CstLiteral64);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public BitSet compatibleRegs(DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        BitSet bits = new BitSet(1);
-
-        bits.set(0, unsignedFitsInByte(regs.get(0).getReg()));
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        RegisterSpecList regs = insn.getRegisters();
-        long value =
-            ((CstLiteral64) ((CstInsn) insn).getConstant()).getLongBits();
-
-        write(out, opcodeUnit(insn, regs.get(0).getReg()), value);
-    }
+    write(out, opcodeUnit(insn, regs.get(0).getReg()), value);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/code/form/SpecialFormat.java b/dx/src/com/android/jack/dx/dex/code/form/SpecialFormat.java
index bce8a67..b0cf53a 100644
--- a/dx/src/com/android/jack/dx/dex/code/form/SpecialFormat.java
+++ b/dx/src/com/android/jack/dx/dex/code/form/SpecialFormat.java
@@ -29,44 +29,44 @@
  * always returns {@code true}.
  */
 public final class SpecialFormat extends InsnFormat {
-    /** {@code non-null;} unique instance of this class */
-    public static final InsnFormat THE_ONE = new SpecialFormat();
+  /** {@code non-null;} unique instance of this class */
+  public static final InsnFormat THE_ONE = new SpecialFormat();
 
-    /**
-     * Constructs an instance. This class is not publicly
-     * instantiable. Use {@link #THE_ONE}.
-     */
-    private SpecialFormat() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly
+   * instantiable. Use {@link #THE_ONE}.
+   */
+  private SpecialFormat() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnArgString(DalvInsn insn) {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnArgString(DalvInsn insn) {
+    throw new RuntimeException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String insnCommentString(DalvInsn insn, boolean noteIndices) {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String insnCommentString(DalvInsn insn, boolean noteIndices) {
+    throw new RuntimeException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int codeSize() {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int codeSize() {
+    throw new RuntimeException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCompatible(DalvInsn insn) {
-        return true;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCompatible(DalvInsn insn) {
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(AnnotatedOutput out, DalvInsn insn) {
-        throw new RuntimeException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(AnnotatedOutput out, DalvInsn insn) {
+    throw new RuntimeException("unsupported");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/AnnotationItem.java b/dx/src/com/android/jack/dx/dex/file/AnnotationItem.java
index c48c3d8..c7394c9 100644
--- a/dx/src/com/android/jack/dx/dex/file/AnnotationItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/AnnotationItem.java
@@ -32,187 +32,193 @@
  * element pairs.
  */
 public final class AnnotationItem extends OffsettedItem {
-    /** annotation visibility constant: visible at build time only */
-    private static final int VISIBILITY_BUILD = 0;
+  /** annotation visibility constant: visible at build time only */
+  private static final int VISIBILITY_BUILD = 0;
 
-    /** annotation visibility constant: visible at runtime */
-    private static final int VISIBILITY_RUNTIME = 1;
+  /** annotation visibility constant: visible at runtime */
+  private static final int VISIBILITY_RUNTIME = 1;
 
-    /** annotation visibility constant: visible at runtime only to system */
-    private static final int VISIBILITY_SYSTEM = 2;
+  /** annotation visibility constant: visible at runtime only to system */
+  private static final int VISIBILITY_SYSTEM = 2;
 
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 1;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 1;
 
-    /** {@code non-null;} unique instance of {@link #TypeIdSorter} */
-    private static final TypeIdSorter TYPE_ID_SORTER = new TypeIdSorter();
+  /** {@code non-null;} unique instance of {@link #TypeIdSorter} */
+  private static final TypeIdSorter TYPE_ID_SORTER = new TypeIdSorter();
 
-    /** {@code non-null;} the annotation to represent */
-    private final Annotation annotation;
+  /** {@code non-null;} the annotation to represent */
+  private final Annotation annotation;
 
-    /**
-     * {@code null-ok;} type reference for the annotation type; set during
-     * {@link #addContents}
-     */
-    private TypeIdItem type;
+  /**
+   * {@code null-ok;} type reference for the annotation type; set during
+   * {@link #addContents}
+   */
+  private TypeIdItem type;
 
-    /**
-     * {@code null-ok;} encoded form, ready for writing to a file; set during
-     * {@link #place0}
-     */
-    private byte[] encodedForm;
+  /**
+   * {@code null-ok;} encoded form, ready for writing to a file; set during
+   * {@link #place0}
+   */
+  private byte[] encodedForm;
 
-    /**
-     * Comparator that sorts (outer) instances by type id index.
-     */
-    private static class TypeIdSorter implements Comparator<AnnotationItem> {
-        /** {@inheritDoc} */
-        public int compare(AnnotationItem item1, AnnotationItem item2) {
-            int index1 = item1.type.getIndex();
-            int index2 = item2.type.getIndex();
-
-            if (index1 < index2) {
-                return -1;
-            } else if (index1 > index2) {
-                return 1;
-            }
-
-            return 0;
-        }
-    }
-
-    /**
-     * Sorts an array of instances, in place, by type id index,
-     * ignoring all other aspects of the elements. This is only valid
-     * to use after type id indices are known.
-     *
-     * @param array {@code non-null;} array to sort
-     */
-    public static void sortByTypeIdIndex(AnnotationItem[] array) {
-        Arrays.sort(array, TYPE_ID_SORTER);
-    }
-
-    /**
-     * Constructs an instance.
-     *
-     * @param annotation {@code non-null;} annotation to represent
-     */
-    public AnnotationItem(Annotation annotation) {
-        /*
-         * The write size isn't known up-front because (the variable-lengthed)
-         * leb128 type is used to represent some things.
-         */
-        super(ALIGNMENT, -1);
-
-        if (annotation == null) {
-            throw new NullPointerException("annotation == null");
-        }
-
-        this.annotation = annotation;
-        this.type = null;
-        this.encodedForm = null;
-    }
-
+  /**
+   * Comparator that sorts (outer) instances by type id index.
+   */
+  private static class TypeIdSorter implements Comparator<AnnotationItem> {
     /** {@inheritDoc} */
     @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_ANNOTATION_ITEM;
+    public int compare(AnnotationItem item1, AnnotationItem item2) {
+      int index1 = item1.type.getIndex();
+      int index2 = item2.type.getIndex();
+
+      if (index1 < index2) {
+        return -1;
+      } else if (index1 > index2) {
+        return 1;
+      }
+
+      return 0;
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return annotation.hashCode();
-    }
+  /**
+   * Sorts an array of instances, in place, by type id index,
+   * ignoring all other aspects of the elements. This is only valid
+   * to use after type id indices are known.
+   *
+   * @param array {@code non-null;} array to sort
+   */
+  public static void sortByTypeIdIndex(AnnotationItem[] array) {
+    Arrays.sort(array, TYPE_ID_SORTER);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(OffsettedItem other) {
-        AnnotationItem otherAnnotation = (AnnotationItem) other;
-
-        return annotation.compareTo(otherAnnotation.annotation);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return annotation.toHuman();
-    }
-
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        type = file.getTypeIds().intern(annotation.getType());
-        ValueEncoder.addContents(file, annotation);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // Encode the data and note the size.
-
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
-        ValueEncoder encoder = new ValueEncoder(addedTo.getFile(), out);
-
-        encoder.writeAnnotation(annotation, false);
-        encodedForm = out.toByteArray();
-
-        // Add one for the visibility byte in front of the encoded annotation.
-        setWriteSize(encodedForm.length + 1);
-    }
-
-    /**
-     * Write a (listing file) annotation for this instance to the given
-     * output, that consumes no bytes of output. This is for annotating
-     * a reference to this instance at the point of the reference.
-     *
-     * @param out {@code non-null;} where to output to
-     * @param prefix {@code non-null;} prefix for each line of output
+  /**
+   * Constructs an instance.
+   *
+   * @param annotation {@code non-null;} annotation to represent
+   */
+  public AnnotationItem(Annotation annotation) {
+    /*
+     * The write size isn't known up-front because (the variable-lengthed)
+     * leb128 type is used to represent some things.
      */
-    public void annotateTo(AnnotatedOutput out, String prefix) {
-        out.annotate(0, prefix + "visibility: " +
-                annotation.getVisibility().toHuman());
-        out.annotate(0, prefix + "type: " + annotation.getType().toHuman());
+    super(ALIGNMENT, -1);
 
-        for (NameValuePair pair : annotation.getNameValuePairs()) {
-            CstString name = pair.getName();
-            Constant value = pair.getValue();
-
-            out.annotate(0, prefix + name.toHuman() + ": " +
-                    ValueEncoder.constantToHuman(value));
-        }
+    if (annotation == null) {
+      throw new NullPointerException("annotation == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        AnnotationVisibility visibility = annotation.getVisibility();
+    this.annotation = annotation;
+    this.type = null;
+    this.encodedForm = null;
+  }
 
-        if (annotates) {
-            out.annotate(0, offsetString() + " annotation");
-            out.annotate(1, "  visibility: VISBILITY_" + visibility);
-        }
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_ANNOTATION_ITEM;
+  }
 
-        switch (visibility) {
-            case BUILD:   out.writeByte(VISIBILITY_BUILD); break;
-            case RUNTIME: out.writeByte(VISIBILITY_RUNTIME); break;
-            case SYSTEM:  out.writeByte(VISIBILITY_SYSTEM); break;
-            default: {
-                // EMBEDDED shouldn't appear at the top level.
-                throw new RuntimeException("shouldn't happen");
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return annotation.hashCode();
+  }
 
-        if (annotates) {
-            /*
-             * The output is to be annotated, so redo the work previously
-             * done by place0(), except this time annotations will actually
-             * get emitted.
-             */
-            ValueEncoder encoder = new ValueEncoder(file, out);
-            encoder.writeAnnotation(annotation, true);
-        } else {
-            out.write(encodedForm);
-        }
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(OffsettedItem other) {
+    AnnotationItem otherAnnotation = (AnnotationItem) other;
+
+    return annotation.compareTo(otherAnnotation.annotation);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return annotation.toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    type = file.getTypeIds().intern(annotation.getType());
+    ValueEncoder.addContents(file, annotation);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // Encode the data and note the size.
+
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
+    ValueEncoder encoder = new ValueEncoder(addedTo.getFile(), out);
+
+    encoder.writeAnnotation(annotation, false);
+    encodedForm = out.toByteArray();
+
+    // Add one for the visibility byte in front of the encoded annotation.
+    setWriteSize(encodedForm.length + 1);
+  }
+
+  /**
+   * Write a (listing file) annotation for this instance to the given
+   * output, that consumes no bytes of output. This is for annotating
+   * a reference to this instance at the point of the reference.
+   *
+   * @param out {@code non-null;} where to output to
+   * @param prefix {@code non-null;} prefix for each line of output
+   */
+  public void annotateTo(AnnotatedOutput out, String prefix) {
+    out.annotate(0, prefix + "visibility: " + annotation.getVisibility().toHuman());
+    out.annotate(0, prefix + "type: " + annotation.getType().toHuman());
+
+    for (NameValuePair pair : annotation.getNameValuePairs()) {
+      CstString name = pair.getName();
+      Constant value = pair.getValue();
+
+      out.annotate(0, prefix + name.toHuman() + ": " + ValueEncoder.constantToHuman(value));
     }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    AnnotationVisibility visibility = annotation.getVisibility();
+
+    if (annotates) {
+      out.annotate(0, offsetString() + " annotation");
+      out.annotate(1, "  visibility: VISBILITY_" + visibility);
+    }
+
+    switch (visibility) {
+      case BUILD:
+        out.writeByte(VISIBILITY_BUILD);
+        break;
+      case RUNTIME:
+        out.writeByte(VISIBILITY_RUNTIME);
+        break;
+      case SYSTEM:
+        out.writeByte(VISIBILITY_SYSTEM);
+        break;
+      default: {
+        // EMBEDDED shouldn't appear at the top level.
+        throw new RuntimeException("shouldn't happen");
+      }
+    }
+
+    if (annotates) {
+      /*
+       * The output is to be annotated, so redo the work previously
+       * done by place0(), except this time annotations will actually
+       * get emitted.
+       */
+      ValueEncoder encoder = new ValueEncoder(file, out);
+      encoder.writeAnnotation(annotation, true);
+    } else {
+      out.write(encodedForm);
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/AnnotationSetItem.java b/dx/src/com/android/jack/dx/dex/file/AnnotationSetItem.java
index 9672023..eea7fa6 100644
--- a/dx/src/com/android/jack/dx/dex/file/AnnotationSetItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/AnnotationSetItem.java
@@ -25,133 +25,133 @@
  * Set of annotations, where no annotation type appears more than once.
  */
 public final class AnnotationSetItem extends OffsettedItem {
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 4;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 4;
 
-    /** the size of an entry int the set: one {@code uint} */
-    private static final int ENTRY_WRITE_SIZE = 4;
+  /** the size of an entry int the set: one {@code uint} */
+  private static final int ENTRY_WRITE_SIZE = 4;
 
-    /** {@code non-null;} the set of annotations */
-    private final Annotations annotations;
+  /** {@code non-null;} the set of annotations */
+  private final Annotations annotations;
 
-    /**
-     * {@code non-null;} set of annotations as individual items in an array.
-     * <b>Note:</b> The contents have to get sorted by type id before
-     * writing.
-     */
-    private final AnnotationItem[] items;
+  /**
+   * {@code non-null;} set of annotations as individual items in an array.
+   * <b>Note:</b> The contents have to get sorted by type id before
+   * writing.
+   */
+  private final AnnotationItem[] items;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param annotations {@code non-null;} set of annotations
-     */
-    public AnnotationSetItem(Annotations annotations) {
-        super(ALIGNMENT, writeSize(annotations));
+  /**
+   * Constructs an instance.
+   *
+   * @param annotations {@code non-null;} set of annotations
+   */
+  public AnnotationSetItem(Annotations annotations) {
+    super(ALIGNMENT, writeSize(annotations));
 
-        this.annotations = annotations;
-        this.items = new AnnotationItem[annotations.size()];
+    this.annotations = annotations;
+    this.items = new AnnotationItem[annotations.size()];
 
-        int at = 0;
-        for (Annotation a : annotations.getAnnotations()) {
-            items[at] = new AnnotationItem(a);
-            at++;
-        }
+    int at = 0;
+    for (Annotation a : annotations.getAnnotations()) {
+      items[at] = new AnnotationItem(a);
+      at++;
+    }
+  }
+
+  /**
+   * Gets the write size for the given set.
+   *
+   * @param annotations {@code non-null;} the set
+   * @return {@code > 0;} the write size
+   */
+  private static int writeSize(Annotations annotations) {
+    // This includes an int size at the start of the list.
+
+    try {
+      return (annotations.size() * ENTRY_WRITE_SIZE) + 4;
+    } catch (NullPointerException ex) {
+      // Elucidate the exception.
+      throw new NullPointerException("list == null");
+    }
+  }
+
+  /**
+   * Gets the underlying annotations of this instance
+   *
+   * @return {@code non-null;} the annotations
+   */
+  public Annotations getAnnotations() {
+    return annotations;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return annotations.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(OffsettedItem other) {
+    AnnotationSetItem otherSet = (AnnotationSetItem) other;
+
+    return annotations.compareTo(otherSet.annotations);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_ANNOTATION_SET_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return annotations.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    MixedItemSection byteData = file.getByteData();
+    int size = items.length;
+
+    for (int i = 0; i < size; i++) {
+      items[i] = byteData.intern(items[i]);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // Sort the array to be in type id index order.
+    AnnotationItem.sortByTypeIdIndex(items);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    int size = items.length;
+
+    if (annotates) {
+      out.annotate(0, offsetString() + " annotation set");
+      out.annotate(4, "  size: " + Hex.u4(size));
     }
 
-    /**
-     * Gets the write size for the given set.
-     *
-     * @param annotations {@code non-null;} the set
-     * @return {@code > 0;} the write size
-     */
-    private static int writeSize(Annotations annotations) {
-        // This includes an int size at the start of the list.
+    out.writeInt(size);
 
-        try {
-            return (annotations.size() * ENTRY_WRITE_SIZE) + 4;
-        } catch (NullPointerException ex) {
-            // Elucidate the exception.
-            throw new NullPointerException("list == null");
-        }
+    for (int i = 0; i < size; i++) {
+      AnnotationItem item = items[i];
+      int offset = item.getAbsoluteOffset();
+
+      if (annotates) {
+        out.annotate(4, "  entries[" + Integer.toHexString(i) + "]: " + Hex.u4(offset));
+        items[i].annotateTo(out, "    ");
+      }
+
+      out.writeInt(offset);
     }
-
-    /**
-     * Gets the underlying annotations of this instance
-     *
-     * @return {@code non-null;} the annotations
-     */
-    public Annotations getAnnotations() {
-        return annotations;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return annotations.hashCode();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(OffsettedItem other) {
-        AnnotationSetItem otherSet = (AnnotationSetItem) other;
-
-        return annotations.compareTo(otherSet.annotations);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_ANNOTATION_SET_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return annotations.toString();
-    }
-
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        MixedItemSection byteData = file.getByteData();
-        int size = items.length;
-
-        for (int i = 0; i < size; i++) {
-            items[i] = byteData.intern(items[i]);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // Sort the array to be in type id index order.
-        AnnotationItem.sortByTypeIdIndex(items);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        int size = items.length;
-
-        if (annotates) {
-            out.annotate(0, offsetString() + " annotation set");
-            out.annotate(4, "  size: " + Hex.u4(size));
-        }
-
-        out.writeInt(size);
-
-        for (int i = 0; i < size; i++) {
-            AnnotationItem item = items[i];
-            int offset = item.getAbsoluteOffset();
-
-            if (annotates) {
-                out.annotate(4, "  entries[" + Integer.toHexString(i) + "]: " +
-                        Hex.u4(offset));
-                items[i].annotateTo(out, "    ");
-            }
-
-            out.writeInt(offset);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/AnnotationSetRefItem.java b/dx/src/com/android/jack/dx/dex/file/AnnotationSetRefItem.java
index a78dafc..2759ebd 100644
--- a/dx/src/com/android/jack/dx/dex/file/AnnotationSetRefItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/AnnotationSetRefItem.java
@@ -23,58 +23,59 @@
  * Indirect reference to an {@link AnnotationSetItem}.
  */
 public final class AnnotationSetRefItem extends OffsettedItem {
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 4;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 4;
 
-    /** write size of this class, in bytes */
-    private static final int WRITE_SIZE = 4;
+  /** write size of this class, in bytes */
+  private static final int WRITE_SIZE = 4;
 
-    /** {@code non-null;} the annotation set to refer to */
-    private AnnotationSetItem annotations;
+  /** {@code non-null;} the annotation set to refer to */
+  private AnnotationSetItem annotations;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param annotations {@code non-null;} the annotation set to refer to
-     */
-    public AnnotationSetRefItem(AnnotationSetItem annotations) {
-        super(ALIGNMENT, WRITE_SIZE);
+  /**
+   * Constructs an instance.
+   *
+   * @param annotations {@code non-null;} the annotation set to refer to
+   */
+  public AnnotationSetRefItem(AnnotationSetItem annotations) {
+    super(ALIGNMENT, WRITE_SIZE);
 
-        if (annotations == null) {
-            throw new NullPointerException("annotations == null");
-        }
-
-        this.annotations = annotations;
+    if (annotations == null) {
+      throw new NullPointerException("annotations == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_ANNOTATION_SET_REF_ITEM;
+    this.annotations = annotations;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_ANNOTATION_SET_REF_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    MixedItemSection wordData = file.getWordData();
+
+    annotations = wordData.intern(annotations);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return annotations.toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    int annotationsOff = annotations.getAbsoluteOffset();
+
+    if (out.annotates()) {
+      out.annotate(4, "  annotations_off: " + Hex.u4(annotationsOff));
     }
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        MixedItemSection wordData = file.getWordData();
-
-        annotations = wordData.intern(annotations);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return annotations.toHuman();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        int annotationsOff = annotations.getAbsoluteOffset();
-
-        if (out.annotates()) {
-            out.annotate(4, "  annotations_off: " + Hex.u4(annotationsOff));
-        }
-
-        out.writeInt(annotationsOff);
-    }
+    out.writeInt(annotationsOff);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/AnnotationUtils.java b/dx/src/com/android/jack/dx/dex/file/AnnotationUtils.java
index 868f82b..99bd2b9 100644
--- a/dx/src/com/android/jack/dx/dex/file/AnnotationUtils.java
+++ b/dx/src/com/android/jack/dx/dex/file/AnnotationUtils.java
@@ -16,6 +16,8 @@
 
 package com.android.jack.dx.dex.file;
 
+import static com.android.jack.dx.rop.annotation.AnnotationVisibility.SYSTEM;
+
 import com.android.jack.dx.rop.annotation.Annotation;
 import com.android.jack.dx.rop.annotation.NameValuePair;
 import com.android.jack.dx.rop.cst.Constant;
@@ -31,222 +33,219 @@
 
 import java.util.ArrayList;
 
-import static com.android.jack.dx.rop.annotation.AnnotationVisibility.*;
-
 /**
  * Utility class for dealing with annotations.
  */
 public final class AnnotationUtils {
-    /** {@code non-null;} type for {@code AnnotationDefault} annotations */
-    private static final CstType ANNOTATION_DEFAULT_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/AnnotationDefault;"));
+  /** {@code non-null;} type for {@code AnnotationDefault} annotations */
+  private static final CstType ANNOTATION_DEFAULT_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/AnnotationDefault;"));
 
-    /** {@code non-null;} type for {@code EnclosingClass} annotations */
-    private static final CstType ENCLOSING_CLASS_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/EnclosingClass;"));
+  /** {@code non-null;} type for {@code EnclosingClass} annotations */
+  private static final CstType ENCLOSING_CLASS_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/EnclosingClass;"));
 
-    /** {@code non-null;} type for {@code EnclosingMethod} annotations */
-    private static final CstType ENCLOSING_METHOD_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/EnclosingMethod;"));
+  /** {@code non-null;} type for {@code EnclosingMethod} annotations */
+  private static final CstType ENCLOSING_METHOD_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/EnclosingMethod;"));
 
-    /** {@code non-null;} type for {@code InnerClass} annotations */
-    private static final CstType INNER_CLASS_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/InnerClass;"));
+  /** {@code non-null;} type for {@code InnerClass} annotations */
+  private static final CstType INNER_CLASS_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/InnerClass;"));
 
-    /** {@code non-null;} type for {@code MemberClasses} annotations */
-    private static final CstType MEMBER_CLASSES_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/MemberClasses;"));
+  /** {@code non-null;} type for {@code MemberClasses} annotations */
+  private static final CstType MEMBER_CLASSES_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/MemberClasses;"));
 
-    /** {@code non-null;} type for {@code Signature} annotations */
-    private static final CstType SIGNATURE_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/Signature;"));
+  /** {@code non-null;} type for {@code Signature} annotations */
+  private static final CstType SIGNATURE_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/Signature;"));
 
-    /** {@code non-null;} type for {@code Throws} annotations */
-    private static final CstType THROWS_TYPE =
-        CstType.intern(Type.intern("Ldalvik/annotation/Throws;"));
+  /** {@code non-null;} type for {@code Throws} annotations */
+  private static final CstType THROWS_TYPE =
+      CstType.intern(Type.intern("Ldalvik/annotation/Throws;"));
 
-    /** {@code non-null;} the UTF-8 constant {@code "accessFlags"} */
-    private static final CstString ACCESS_FLAGS_STRING = new CstString("accessFlags");
+  /** {@code non-null;} the UTF-8 constant {@code "accessFlags"} */
+  private static final CstString ACCESS_FLAGS_STRING = new CstString("accessFlags");
 
-    /** {@code non-null;} the UTF-8 constant {@code "name"} */
-    private static final CstString NAME_STRING = new CstString("name");
+  /** {@code non-null;} the UTF-8 constant {@code "name"} */
+  private static final CstString NAME_STRING = new CstString("name");
 
-    /** {@code non-null;} the UTF-8 constant {@code "value"} */
-    private static final CstString VALUE_STRING = new CstString("value");
+  /** {@code non-null;} the UTF-8 constant {@code "value"} */
+  private static final CstString VALUE_STRING = new CstString("value");
 
-    /**
-     * This class is uninstantiable.
+  /**
+   * This class is uninstantiable.
+   */
+  private AnnotationUtils() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Constructs a standard {@code AnnotationDefault} annotation.
+   *
+   * @param defaults {@code non-null;} the defaults, itself as an annotation
+   * @return {@code non-null;} the constructed annotation
+   */
+  public static Annotation makeAnnotationDefault(Annotation defaults) {
+    Annotation result = new Annotation(ANNOTATION_DEFAULT_TYPE, SYSTEM);
+
+    result.put(new NameValuePair(VALUE_STRING, new CstAnnotation(defaults)));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs a standard {@code EnclosingClass} annotation.
+   *
+   * @param clazz {@code non-null;} the enclosing class
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeEnclosingClass(CstType clazz) {
+    Annotation result = new Annotation(ENCLOSING_CLASS_TYPE, SYSTEM);
+
+    result.put(new NameValuePair(VALUE_STRING, clazz));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs a standard {@code EnclosingMethod} annotation.
+   *
+   * @param method {@code non-null;} the enclosing method
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeEnclosingMethod(CstMethodRef method) {
+    Annotation result = new Annotation(ENCLOSING_METHOD_TYPE, SYSTEM);
+
+    result.put(new NameValuePair(VALUE_STRING, method));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs a standard {@code InnerClass} annotation.
+   *
+   * @param name {@code null-ok;} the original name of the class, or
+   * {@code null} to represent an anonymous class
+   * @param accessFlags the original access flags
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeInnerClass(CstString name, int accessFlags) {
+    Annotation result = new Annotation(INNER_CLASS_TYPE, SYSTEM);
+    Constant nameCst = (name != null) ? name : CstKnownNull.THE_ONE;
+
+    result.put(new NameValuePair(NAME_STRING, nameCst));
+    result.put(new NameValuePair(ACCESS_FLAGS_STRING, CstInteger.make(accessFlags)));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs a standard {@code MemberClasses} annotation.
+   *
+   * @param types {@code non-null;} the list of (the types of) the member classes
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeMemberClasses(TypeList types) {
+    CstArray array = makeCstArray(types);
+    Annotation result = new Annotation(MEMBER_CLASSES_TYPE, SYSTEM);
+    result.put(new NameValuePair(VALUE_STRING, array));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Constructs a standard {@code Signature} annotation.
+   *
+   * @param signature {@code non-null;} the signature string
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeSignature(CstString signature) {
+    Annotation result = new Annotation(SIGNATURE_TYPE, SYSTEM);
+
+    /*
+     * Split the string into pieces that are likely to be common
+     * across many signatures and the rest of the file.
      */
-    private AnnotationUtils() {
-        // This space intentionally left blank.
-    }
 
-    /**
-     * Constructs a standard {@code AnnotationDefault} annotation.
-     *
-     * @param defaults {@code non-null;} the defaults, itself as an annotation
-     * @return {@code non-null;} the constructed annotation
-     */
-    public static Annotation makeAnnotationDefault(Annotation defaults) {
-        Annotation result = new Annotation(ANNOTATION_DEFAULT_TYPE, SYSTEM);
+String raw = signature.getString();
+    int rawLength = raw.length();
+    ArrayList<String> pieces = new ArrayList<String>(20);
 
-        result.put(new NameValuePair(VALUE_STRING, new CstAnnotation(defaults)));
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Constructs a standard {@code EnclosingClass} annotation.
-     *
-     * @param clazz {@code non-null;} the enclosing class
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeEnclosingClass(CstType clazz) {
-        Annotation result = new Annotation(ENCLOSING_CLASS_TYPE, SYSTEM);
-
-        result.put(new NameValuePair(VALUE_STRING, clazz));
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Constructs a standard {@code EnclosingMethod} annotation.
-     *
-     * @param method {@code non-null;} the enclosing method
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeEnclosingMethod(CstMethodRef method) {
-        Annotation result = new Annotation(ENCLOSING_METHOD_TYPE, SYSTEM);
-
-        result.put(new NameValuePair(VALUE_STRING, method));
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Constructs a standard {@code InnerClass} annotation.
-     *
-     * @param name {@code null-ok;} the original name of the class, or
-     * {@code null} to represent an anonymous class
-     * @param accessFlags the original access flags
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeInnerClass(CstString name, int accessFlags) {
-        Annotation result = new Annotation(INNER_CLASS_TYPE, SYSTEM);
-        Constant nameCst = (name != null) ? name : CstKnownNull.THE_ONE;
-
-        result.put(new NameValuePair(NAME_STRING, nameCst));
-        result.put(new NameValuePair(ACCESS_FLAGS_STRING,
-                        CstInteger.make(accessFlags)));
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Constructs a standard {@code MemberClasses} annotation.
-     *
-     * @param types {@code non-null;} the list of (the types of) the member classes
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeMemberClasses(TypeList types) {
-        CstArray array = makeCstArray(types);
-        Annotation result = new Annotation(MEMBER_CLASSES_TYPE, SYSTEM);
-        result.put(new NameValuePair(VALUE_STRING, array));
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Constructs a standard {@code Signature} annotation.
-     *
-     * @param signature {@code non-null;} the signature string
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeSignature(CstString signature) {
-        Annotation result = new Annotation(SIGNATURE_TYPE, SYSTEM);
-
-        /*
-         * Split the string into pieces that are likely to be common
-         * across many signatures and the rest of the file.
-         */
-
-        String raw = signature.getString();
-        int rawLength = raw.length();
-        ArrayList<String> pieces = new ArrayList<String>(20);
-
-        for (int at = 0; at < rawLength; /*at*/) {
-            char c = raw.charAt(at);
-            int endAt = at + 1;
-            if (c == 'L') {
-                // Scan to ';' or '<'. Consume ';' but not '<'.
-                while (endAt < rawLength) {
-                    c = raw.charAt(endAt);
-                    if (c == ';') {
-                        endAt++;
-                        break;
-                    } else if (c == '<') {
-                        break;
-                    }
-                    endAt++;
-                }
-            } else {
-                // Scan to 'L' without consuming it.
-                while (endAt < rawLength) {
-                    c = raw.charAt(endAt);
-                    if (c == 'L') {
-                        break;
-                    }
-                    endAt++;
-                }
-            }
-
-            pieces.add(raw.substring(at, endAt));
-            at = endAt;
+    for (int at = 0; at < rawLength; /*at*/) {
+      char c = raw.charAt(at);
+      int endAt = at + 1;
+      if (c == 'L') {
+        // Scan to ';' or '<'. Consume ';' but not '<'.
+        while (endAt < rawLength) {
+          c = raw.charAt(endAt);
+          if (c == ';') {
+            endAt++;
+            break;
+          } else if (c == '<') {
+            break;
+          }
+          endAt++;
         }
-
-        int size = pieces.size();
-        CstArray.List list = new CstArray.List(size);
-
-        for (int i = 0; i < size; i++) {
-            list.set(i, new CstString(pieces.get(i)));
+      } else {
+        // Scan to 'L' without consuming it.
+        while (endAt < rawLength) {
+          c = raw.charAt(endAt);
+          if (c == 'L') {
+            break;
+          }
+          endAt++;
         }
+      }
 
-        list.setImmutable();
-
-        result.put(new NameValuePair(VALUE_STRING, new CstArray(list)));
-        result.setImmutable();
-        return result;
+      pieces.add(raw.substring(at, endAt));
+      at = endAt;
     }
 
-    /**
-     * Constructs a standard {@code Throws} annotation.
-     *
-     * @param types {@code non-null;} the list of thrown types
-     * @return {@code non-null;} the annotation
-     */
-    public static Annotation makeThrows(TypeList types) {
-        CstArray array = makeCstArray(types);
-        Annotation result = new Annotation(THROWS_TYPE, SYSTEM);
-        result.put(new NameValuePair(VALUE_STRING, array));
-        result.setImmutable();
-        return result;
+    int size = pieces.size();
+    CstArray.List list = new CstArray.List(size);
+
+    for (int i = 0; i < size; i++) {
+      list.set(i, new CstString(pieces.get(i)));
     }
 
-    /**
-     * Converts a {@link TypeList} to a {@link CstArray}.
-     *
-     * @param types {@code non-null;} the type list
-     * @return {@code non-null;} the corresponding array constant
-     */
-    private static CstArray makeCstArray(TypeList types) {
-        int size = types.size();
-        CstArray.List list = new CstArray.List(size);
+    list.setImmutable();
 
-        for (int i = 0; i < size; i++) {
-            list.set(i, CstType.intern(types.getType(i)));
-        }
+    result.put(new NameValuePair(VALUE_STRING, new CstArray(list)));
+    result.setImmutable();
+    return result;
+  }
 
-        list.setImmutable();
-        return new CstArray(list);
+  /**
+   * Constructs a standard {@code Throws} annotation.
+   *
+   * @param types {@code non-null;} the list of thrown types
+   * @return {@code non-null;} the annotation
+   */
+  public static Annotation makeThrows(TypeList types) {
+    CstArray array = makeCstArray(types);
+    Annotation result = new Annotation(THROWS_TYPE, SYSTEM);
+    result.put(new NameValuePair(VALUE_STRING, array));
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Converts a {@link TypeList} to a {@link CstArray}.
+   *
+   * @param types {@code non-null;} the type list
+   * @return {@code non-null;} the corresponding array constant
+   */
+  private static CstArray makeCstArray(TypeList types) {
+    int size = types.size();
+    CstArray.List list = new CstArray.List(size);
+
+    for (int i = 0; i < size; i++) {
+      list.set(i, CstType.intern(types.getType(i)));
     }
+
+    list.setImmutable();
+    return new CstArray(list);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/AnnotationsDirectoryItem.java b/dx/src/com/android/jack/dx/dex/file/AnnotationsDirectoryItem.java
index acde7fa..13f727a 100644
--- a/dx/src/com/android/jack/dx/dex/file/AnnotationsDirectoryItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/AnnotationsDirectoryItem.java
@@ -31,355 +31,342 @@
  * Per-class directory of annotations.
  */
 public final class AnnotationsDirectoryItem extends OffsettedItem {
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 4;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 4;
 
-    /** write size of this class's header, in bytes */
-    private static final int HEADER_SIZE = 16;
+  /** write size of this class's header, in bytes */
+  private static final int HEADER_SIZE = 16;
 
-    /** write size of a list element, in bytes */
-    private static final int ELEMENT_SIZE = 8;
+  /** write size of a list element, in bytes */
+  private static final int ELEMENT_SIZE = 8;
 
-    /** {@code null-ok;} the class-level annotations, if any */
-    private AnnotationSetItem classAnnotations;
+  /** {@code null-ok;} the class-level annotations, if any */
+  private AnnotationSetItem classAnnotations;
 
-    /** {@code null-ok;} the annotated fields, if any */
-    private ArrayList<FieldAnnotationStruct> fieldAnnotations;
+  /** {@code null-ok;} the annotated fields, if any */
+  private ArrayList<FieldAnnotationStruct> fieldAnnotations;
 
-    /** {@code null-ok;} the annotated methods, if any */
-    private ArrayList<MethodAnnotationStruct> methodAnnotations;
+  /** {@code null-ok;} the annotated methods, if any */
+  private ArrayList<MethodAnnotationStruct> methodAnnotations;
 
-    /** {@code null-ok;} the annotated parameters, if any */
-    private ArrayList<ParameterAnnotationStruct> parameterAnnotations;
+  /** {@code null-ok;} the annotated parameters, if any */
+  private ArrayList<ParameterAnnotationStruct> parameterAnnotations;
 
-    /**
-     * Constructs an empty instance.
-     */
-    public AnnotationsDirectoryItem() {
-        super(ALIGNMENT, -1);
+  /**
+   * Constructs an empty instance.
+   */
+  public AnnotationsDirectoryItem() {
+    super(ALIGNMENT, -1);
 
-        classAnnotations = null;
-        fieldAnnotations = null;
-        methodAnnotations = null;
-        parameterAnnotations = null;
+    classAnnotations = null;
+    fieldAnnotations = null;
+    methodAnnotations = null;
+    parameterAnnotations = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_ANNOTATIONS_DIRECTORY_ITEM;
+  }
+
+  /**
+   * Returns whether this item is empty (has no contents).
+   *
+   * @return {@code true} if this item is empty, or {@code false}
+   * if not
+   */
+  public boolean isEmpty() {
+    return (classAnnotations == null) && (fieldAnnotations == null) && (methodAnnotations == null)
+        && (parameterAnnotations == null);
+  }
+
+  /**
+   * Returns whether this item is a candidate for interning. The only
+   * interning candidates are ones that <i>only</i> have a non-null
+   * set of class annotations, with no other lists.
+   *
+   * @return {@code true} if this is an interning candidate, or
+   * {@code false} if not
+   */
+  public boolean isInternable() {
+    return (classAnnotations != null) && (fieldAnnotations == null) && (methodAnnotations == null)
+        && (parameterAnnotations == null);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    if (classAnnotations == null) {
+      return 0;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_ANNOTATIONS_DIRECTORY_ITEM;
+    return classAnnotations.hashCode();
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * <p><b>Note:</b>: This throws an exception if this item is not
+   * internable.</p>
+   *
+   * @see #isInternable
+   */
+  @Override
+  public int compareTo0(OffsettedItem other) {
+    if (!isInternable()) {
+      throw new UnsupportedOperationException("uninternable instance");
     }
 
-    /**
-     * Returns whether this item is empty (has no contents).
-     *
-     * @return {@code true} if this item is empty, or {@code false}
-     * if not
-     */
-    public boolean isEmpty() {
-        return (classAnnotations == null) &&
-            (fieldAnnotations == null) &&
-            (methodAnnotations == null) &&
-            (parameterAnnotations == null);
+    AnnotationsDirectoryItem otherDirectory = (AnnotationsDirectoryItem) other;
+    return classAnnotations.compareTo(otherDirectory.classAnnotations);
+  }
+
+  /**
+   * Sets the direct annotations on this instance. These are annotations
+   * made on the class, per se, as opposed to on one of its members.
+   * It is only valid to call this method at most once per instance.
+   *
+   * @param annotations {@code non-null;} annotations to set for this class
+   */
+  public void setClassAnnotations(Annotations annotations) {
+    if (annotations == null) {
+      throw new NullPointerException("annotations == null");
     }
 
-    /**
-     * Returns whether this item is a candidate for interning. The only
-     * interning candidates are ones that <i>only</i> have a non-null
-     * set of class annotations, with no other lists.
-     *
-     * @return {@code true} if this is an interning candidate, or
-     * {@code false} if not
-     */
-    public boolean isInternable() {
-        return (classAnnotations != null) &&
-            (fieldAnnotations == null) &&
-            (methodAnnotations == null) &&
-            (parameterAnnotations == null);
+    if (classAnnotations != null) {
+      throw new UnsupportedOperationException("class annotations already set");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        if (classAnnotations == null) {
-            return 0;
-        }
+    classAnnotations = new AnnotationSetItem(annotations);
+  }
 
-        return classAnnotations.hashCode();
+  /**
+   * Adds a field annotations item to this instance.
+   *
+   * @param field {@code non-null;} field in question
+   * @param annotations {@code non-null;} associated annotations to add
+   */
+  public void addFieldAnnotations(CstFieldRef field, Annotations annotations) {
+    if (fieldAnnotations == null) {
+      fieldAnnotations = new ArrayList<FieldAnnotationStruct>();
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * <p><b>Note:</b>: This throws an exception if this item is not
-     * internable.</p>
-     *
-     * @see #isInternable
-     */
-    @Override
-    public int compareTo0(OffsettedItem other) {
-        if (! isInternable()) {
-            throw new UnsupportedOperationException("uninternable instance");
-        }
+    fieldAnnotations.add(new FieldAnnotationStruct(field, new AnnotationSetItem(annotations)));
+  }
 
-        AnnotationsDirectoryItem otherDirectory =
-            (AnnotationsDirectoryItem) other;
-        return classAnnotations.compareTo(otherDirectory.classAnnotations);
+  /**
+   * Adds a method annotations item to this instance.
+   *
+   * @param method {@code non-null;} method in question
+   * @param annotations {@code non-null;} associated annotations to add
+   */
+  public void addMethodAnnotations(CstMethodRef method, Annotations annotations) {
+    if (methodAnnotations == null) {
+      methodAnnotations = new ArrayList<MethodAnnotationStruct>();
     }
 
-    /**
-     * Sets the direct annotations on this instance. These are annotations
-     * made on the class, per se, as opposed to on one of its members.
-     * It is only valid to call this method at most once per instance.
-     *
-     * @param annotations {@code non-null;} annotations to set for this class
-     */
-    public void setClassAnnotations(Annotations annotations) {
-        if (annotations == null) {
-            throw new NullPointerException("annotations == null");
-        }
+    methodAnnotations.add(new MethodAnnotationStruct(method, new AnnotationSetItem(annotations)));
+  }
 
-        if (classAnnotations != null) {
-            throw new UnsupportedOperationException(
-                    "class annotations already set");
-        }
-
-        classAnnotations = new AnnotationSetItem(annotations);
+  /**
+   * Adds a parameter annotations item to this instance.
+   *
+   * @param method {@code non-null;} method in question
+   * @param list {@code non-null;} associated list of annotation sets to add
+   */
+  public void addParameterAnnotations(CstMethodRef method, AnnotationsList list) {
+    if (parameterAnnotations == null) {
+      parameterAnnotations = new ArrayList<ParameterAnnotationStruct>();
     }
 
-    /**
-     * Adds a field annotations item to this instance.
-     *
-     * @param field {@code non-null;} field in question
-     * @param annotations {@code non-null;} associated annotations to add
-     */
-    public void addFieldAnnotations(CstFieldRef field,
-            Annotations annotations) {
-        if (fieldAnnotations == null) {
-            fieldAnnotations = new ArrayList<FieldAnnotationStruct>();
-        }
+    parameterAnnotations.add(new ParameterAnnotationStruct(method, list));
+  }
 
-        fieldAnnotations.add(new FieldAnnotationStruct(field,
-                        new AnnotationSetItem(annotations)));
+  /**
+   * Gets the method annotations for a given method, if any. This is
+   * meant for use by debugging / dumping code.
+   *
+   * @param method {@code non-null;} the method
+   * @return {@code null-ok;} the method annotations, if any
+   */
+  public Annotations getMethodAnnotations(CstMethodRef method) {
+    if (methodAnnotations == null) {
+      return null;
     }
 
-    /**
-     * Adds a method annotations item to this instance.
-     *
-     * @param method {@code non-null;} method in question
-     * @param annotations {@code non-null;} associated annotations to add
-     */
-    public void addMethodAnnotations(CstMethodRef method,
-            Annotations annotations) {
-        if (methodAnnotations == null) {
-            methodAnnotations = new ArrayList<MethodAnnotationStruct>();
-        }
-
-        methodAnnotations.add(new MethodAnnotationStruct(method,
-                        new AnnotationSetItem(annotations)));
+    for (MethodAnnotationStruct item : methodAnnotations) {
+      if (item.getMethod().equals(method)) {
+        return item.getAnnotations();
+      }
     }
 
-    /**
-     * Adds a parameter annotations item to this instance.
-     *
-     * @param method {@code non-null;} method in question
-     * @param list {@code non-null;} associated list of annotation sets to add
-     */
-    public void addParameterAnnotations(CstMethodRef method,
-            AnnotationsList list) {
-        if (parameterAnnotations == null) {
-            parameterAnnotations = new ArrayList<ParameterAnnotationStruct>();
-        }
+    return null;
+  }
 
-        parameterAnnotations.add(new ParameterAnnotationStruct(method, list));
+  /**
+   * Gets the parameter annotations for a given method, if any. This is
+   * meant for use by debugging / dumping code.
+   *
+   * @param method {@code non-null;} the method
+   * @return {@code null-ok;} the parameter annotations, if any
+   */
+  public AnnotationsList getParameterAnnotations(CstMethodRef method) {
+    if (parameterAnnotations == null) {
+      return null;
     }
 
-    /**
-     * Gets the method annotations for a given method, if any. This is
-     * meant for use by debugging / dumping code.
-     *
-     * @param method {@code non-null;} the method
-     * @return {@code null-ok;} the method annotations, if any
-     */
-    public Annotations getMethodAnnotations(CstMethodRef method) {
-        if (methodAnnotations == null) {
-            return null;
-        }
-
-        for (MethodAnnotationStruct item : methodAnnotations) {
-            if (item.getMethod().equals(method)) {
-                return item.getAnnotations();
-            }
-        }
-
-        return null;
+    for (ParameterAnnotationStruct item : parameterAnnotations) {
+      if (item.getMethod().equals(method)) {
+        return item.getAnnotationsList();
+      }
     }
 
-    /**
-     * Gets the parameter annotations for a given method, if any. This is
-     * meant for use by debugging / dumping code.
-     *
-     * @param method {@code non-null;} the method
-     * @return {@code null-ok;} the parameter annotations, if any
-     */
-    public AnnotationsList getParameterAnnotations(CstMethodRef method) {
-        if (parameterAnnotations == null) {
-            return null;
-        }
+    return null;
+  }
 
-        for (ParameterAnnotationStruct item : parameterAnnotations) {
-            if (item.getMethod().equals(method)) {
-                return item.getAnnotationsList();
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    MixedItemSection wordData = file.getWordData();
 
-        return null;
+    if (classAnnotations != null) {
+      classAnnotations = wordData.intern(classAnnotations);
     }
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        MixedItemSection wordData = file.getWordData();
-
-        if (classAnnotations != null) {
-            classAnnotations = wordData.intern(classAnnotations);
-        }
-
-        if (fieldAnnotations != null) {
-            for (FieldAnnotationStruct item : fieldAnnotations) {
-                item.addContents(file);
-            }
-        }
-
-        if (methodAnnotations != null) {
-            for (MethodAnnotationStruct item : methodAnnotations) {
-                item.addContents(file);
-            }
-        }
-
-        if (parameterAnnotations != null) {
-            for (ParameterAnnotationStruct item : parameterAnnotations) {
-                item.addContents(file);
-            }
-        }
+    if (fieldAnnotations != null) {
+      for (FieldAnnotationStruct item : fieldAnnotations) {
+        item.addContents(file);
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        throw new RuntimeException("unsupported");
+    if (methodAnnotations != null) {
+      for (MethodAnnotationStruct item : methodAnnotations) {
+        item.addContents(file);
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // We just need to set the write size here.
+    if (parameterAnnotations != null) {
+      for (ParameterAnnotationStruct item : parameterAnnotations) {
+        item.addContents(file);
+      }
+    }
+  }
 
-        int elementCount = listSize(fieldAnnotations)
-            + listSize(methodAnnotations) + listSize(parameterAnnotations);
-        setWriteSize(HEADER_SIZE + (elementCount * ELEMENT_SIZE));
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    throw new RuntimeException("unsupported");
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // We just need to set the write size here.
+
+    int elementCount =
+        listSize(fieldAnnotations) + listSize(methodAnnotations) + listSize(parameterAnnotations);
+    setWriteSize(HEADER_SIZE + (elementCount * ELEMENT_SIZE));
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    int classOff = OffsettedItem.getAbsoluteOffsetOr0(classAnnotations);
+    int fieldsSize = listSize(fieldAnnotations);
+    int methodsSize = listSize(methodAnnotations);
+    int parametersSize = listSize(parameterAnnotations);
+
+    if (annotates) {
+      out.annotate(0, offsetString() + " annotations directory");
+      out.annotate(4, "  class_annotations_off: " + Hex.u4(classOff));
+      out.annotate(4, "  fields_size:           " + Hex.u4(fieldsSize));
+      out.annotate(4, "  methods_size:          " + Hex.u4(methodsSize));
+      out.annotate(4, "  parameters_size:       " + Hex.u4(parametersSize));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        int classOff = OffsettedItem.getAbsoluteOffsetOr0(classAnnotations);
-        int fieldsSize = listSize(fieldAnnotations);
-        int methodsSize = listSize(methodAnnotations);
-        int parametersSize = listSize(parameterAnnotations);
+    out.writeInt(classOff);
+    out.writeInt(fieldsSize);
+    out.writeInt(methodsSize);
+    out.writeInt(parametersSize);
 
-        if (annotates) {
-            out.annotate(0, offsetString() + " annotations directory");
-            out.annotate(4, "  class_annotations_off: " + Hex.u4(classOff));
-            out.annotate(4, "  fields_size:           " +
-                    Hex.u4(fieldsSize));
-            out.annotate(4, "  methods_size:          " +
-                    Hex.u4(methodsSize));
-            out.annotate(4, "  parameters_size:       " +
-                    Hex.u4(parametersSize));
-        }
-
-        out.writeInt(classOff);
-        out.writeInt(fieldsSize);
-        out.writeInt(methodsSize);
-        out.writeInt(parametersSize);
-
-        if (fieldsSize != 0) {
-            Collections.sort(fieldAnnotations);
-            if (annotates) {
-                out.annotate(0, "  fields:");
-            }
-            for (FieldAnnotationStruct item : fieldAnnotations) {
-                item.writeTo(file, out);
-            }
-        }
-
-        if (methodsSize != 0) {
-            Collections.sort(methodAnnotations);
-            if (annotates) {
-                out.annotate(0, "  methods:");
-            }
-            for (MethodAnnotationStruct item : methodAnnotations) {
-                item.writeTo(file, out);
-            }
-        }
-
-        if (parametersSize != 0) {
-            Collections.sort(parameterAnnotations);
-            if (annotates) {
-                out.annotate(0, "  parameters:");
-            }
-            for (ParameterAnnotationStruct item : parameterAnnotations) {
-                item.writeTo(file, out);
-            }
-        }
+    if (fieldsSize != 0) {
+      Collections.sort(fieldAnnotations);
+      if (annotates) {
+        out.annotate(0, "  fields:");
+      }
+      for (FieldAnnotationStruct item : fieldAnnotations) {
+        item.writeTo(file, out);
+      }
     }
 
-    /**
-     * Gets the list size of the given list, or {@code 0} if given
-     * {@code null}.
-     *
-     * @param list {@code null-ok;} the list in question
-     * @return {@code >= 0;} its size
-     */
-    private static int listSize(ArrayList<?> list) {
-        if (list == null) {
-            return 0;
-        }
-
-        return list.size();
+    if (methodsSize != 0) {
+      Collections.sort(methodAnnotations);
+      if (annotates) {
+        out.annotate(0, "  methods:");
+      }
+      for (MethodAnnotationStruct item : methodAnnotations) {
+        item.writeTo(file, out);
+      }
     }
 
-    /**
-     * Prints out the contents of this instance, in a debugging-friendly
-     * way. This is meant to be called from {@link ClassDefItem#debugPrint}.
-     *
-     * @param out {@code non-null;} where to output to
-     */
-    /*package*/ void debugPrint(PrintWriter out) {
-        if (classAnnotations != null) {
-            out.println("  class annotations: " + classAnnotations);
-        }
-
-        if (fieldAnnotations != null) {
-            out.println("  field annotations:");
-            for (FieldAnnotationStruct item : fieldAnnotations) {
-                out.println("    " + item.toHuman());
-            }
-        }
-
-        if (methodAnnotations != null) {
-            out.println("  method annotations:");
-            for (MethodAnnotationStruct item : methodAnnotations) {
-                out.println("    " + item.toHuman());
-            }
-        }
-
-        if (parameterAnnotations != null) {
-            out.println("  parameter annotations:");
-            for (ParameterAnnotationStruct item : parameterAnnotations) {
-                out.println("    " + item.toHuman());
-            }
-        }
+    if (parametersSize != 0) {
+      Collections.sort(parameterAnnotations);
+      if (annotates) {
+        out.annotate(0, "  parameters:");
+      }
+      for (ParameterAnnotationStruct item : parameterAnnotations) {
+        item.writeTo(file, out);
+      }
     }
+  }
+
+  /**
+   * Gets the list size of the given list, or {@code 0} if given
+   * {@code null}.
+   *
+   * @param list {@code null-ok;} the list in question
+   * @return {@code >= 0;} its size
+   */
+  private static int listSize(ArrayList<?> list) {
+    if (list == null) {
+      return 0;
+    }
+
+    return list.size();
+  }
+
+  /**
+   * Prints out the contents of this instance, in a debugging-friendly
+   * way. This is meant to be called from {@link ClassDefItem#debugPrint}.
+   *
+   * @param out {@code non-null;} where to output to
+   */
+  /*package*/void debugPrint(PrintWriter out) {
+    if (classAnnotations != null) {
+      out.println("  class annotations: " + classAnnotations);
+    }
+
+    if (fieldAnnotations != null) {
+      out.println("  field annotations:");
+      for (FieldAnnotationStruct item : fieldAnnotations) {
+        out.println("    " + item.toHuman());
+      }
+    }
+
+    if (methodAnnotations != null) {
+      out.println("  method annotations:");
+      for (MethodAnnotationStruct item : methodAnnotations) {
+        out.println("    " + item.toHuman());
+      }
+    }
+
+    if (parameterAnnotations != null) {
+      out.println("  parameter annotations:");
+      for (ParameterAnnotationStruct item : parameterAnnotations) {
+        out.println("    " + item.toHuman());
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/CatchStructs.java b/dx/src/com/android/jack/dx/dex/file/CatchStructs.java
index 686ef82..3426fac 100644
--- a/dx/src/com/android/jack/dx/dex/file/CatchStructs.java
+++ b/dx/src/com/android/jack/dx/dex/file/CatchStructs.java
@@ -34,282 +34,284 @@
  * {@code catch_handler_item[]}.
  */
 public final class CatchStructs {
-    /**
-     * the size of a {@code try_item}: a {@code uint}
-     * and two {@code ushort}s
-     */
-    public static final int TRY_ITEM_WRITE_SIZE = 4 + (2 * 2);
+  /**
+   * the size of a {@code try_item}: a {@code uint}
+   * and two {@code ushort}s
+   */
+  public static final int TRY_ITEM_WRITE_SIZE = 4 + (2 * 2);
 
-    /** {@code non-null;} code that contains the catches */
-    private final DalvCode code;
+  /** {@code non-null;} code that contains the catches */
+  private final DalvCode code;
 
-    /**
-     * {@code null-ok;} the underlying table; set in
-     * {@link #finishProcessingIfNecessary}
-     */
-    private CatchTable table;
+  /**
+   * {@code null-ok;} the underlying table; set in
+   * {@link #finishProcessingIfNecessary}
+   */
+  private CatchTable table;
 
-    /**
-     * {@code null-ok;} the encoded handler list, if calculated; set in
-     * {@link #encode}
-     */
-    private byte[] encodedHandlers;
+  /**
+   * {@code null-ok;} the encoded handler list, if calculated; set in
+   * {@link #encode}
+   */
+  private byte[] encodedHandlers;
 
-    /**
-     * length of the handlers header (encoded size), if known; used for
-     * annotation
-     */
-    private int encodedHandlerHeaderSize;
+  /**
+   * length of the handlers header (encoded size), if known; used for
+   * annotation
+   */
+  private int encodedHandlerHeaderSize;
 
-    /**
-     * {@code null-ok;} map from handler lists to byte offsets, if calculated; set in
-     * {@link #encode}
-     */
-    private TreeMap<CatchHandlerList, Integer> handlerOffsets;
+  /**
+   * {@code null-ok;} map from handler lists to byte offsets, if calculated; set in
+   * {@link #encode}
+   */
+  private TreeMap<CatchHandlerList, Integer> handlerOffsets;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param code {@code non-null;} code that contains the catches
+  /**
+   * Constructs an instance.
+   *
+   * @param code {@code non-null;} code that contains the catches
+   */
+  public CatchStructs(DalvCode code) {
+    this.code = code;
+    this.table = null;
+    this.encodedHandlers = null;
+    this.encodedHandlerHeaderSize = 0;
+    this.handlerOffsets = null;
+  }
+
+  /**
+   * Finish processing the catches, if necessary.
+   */
+  private void finishProcessingIfNecessary() {
+    if (table == null) {
+      table = code.getCatches();
+    }
+  }
+
+  /**
+   * Gets the size of the tries list, in entries.
+   *
+   * @return {@code >= 0;} the tries list size
+   */
+  public int triesSize() {
+    finishProcessingIfNecessary();
+    return table.size();
+  }
+
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} prefix to attach to each line of output
+   */
+  public void debugPrint(PrintWriter out, String prefix) {
+    annotateEntries(prefix, out, null);
+  }
+
+  /**
+   * Encodes the handler lists.
+   *
+   * @param file {@code non-null;} file this instance is part of
+   */
+  public void encode(DexFile file) {
+    finishProcessingIfNecessary();
+
+    TypeIdsSection typeIds = file.getTypeIds();
+    int size = table.size();
+
+    handlerOffsets = new TreeMap<CatchHandlerList, Integer>();
+
+    /*
+     * First add a map entry for each unique list. The tree structure
+     * will ensure they are sorted when we reiterate later.
      */
-    public CatchStructs(DalvCode code) {
-        this.code = code;
-        this.table = null;
-        this.encodedHandlers = null;
-        this.encodedHandlerHeaderSize = 0;
-        this.handlerOffsets = null;
+    for (int i = 0; i < size; i++) {
+      handlerOffsets.put(table.get(i).getHandlers(), null);
     }
 
-    /**
-     * Finish processing the catches, if necessary.
-     */
-    private void finishProcessingIfNecessary() {
-        if (table == null) {
-            table = code.getCatches();
-        }
+    if (handlerOffsets.size() > 65535) {
+      throw new UnsupportedOperationException("too many catch handlers");
     }
 
-    /**
-     * Gets the size of the tries list, in entries.
-     *
-     * @return {@code >= 0;} the tries list size
-     */
-    public int triesSize() {
-        finishProcessingIfNecessary();
-        return table.size();
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
+
+    // Write out the handlers "header" consisting of its size in entries.
+    encodedHandlerHeaderSize = out.writeUleb128(handlerOffsets.size());
+
+    // Now write the lists out in order, noting the offset of each.
+    for (Map.Entry<CatchHandlerList, Integer> mapping : handlerOffsets.entrySet()) {
+      CatchHandlerList list = mapping.getKey();
+      int listSize = list.size();
+      boolean catchesAll = list.catchesAll();
+
+      // Set the offset before we do any writing.
+      mapping.setValue(out.getCursor());
+
+      if (catchesAll) {
+        // A size <= 0 means that the list ends with a catch-all.
+        out.writeSleb128(-(listSize - 1));
+        listSize--;
+      } else {
+        out.writeSleb128(listSize);
+      }
+
+      for (int i = 0; i < listSize; i++) {
+        CatchHandlerList.Entry entry = list.get(i);
+        out.writeUleb128(typeIds.indexOf(entry.getExceptionType()));
+        out.writeUleb128(entry.getHandler());
+      }
+
+      if (catchesAll) {
+        out.writeUleb128(list.get(listSize).getHandler());
+      }
     }
 
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} prefix to attach to each line of output
-     */
-    public void debugPrint(PrintWriter out, String prefix) {
-        annotateEntries(prefix, out, null);
+    encodedHandlers = out.toByteArray();
+  }
+
+  /**
+   * Gets the write size of this instance, in bytes.
+   *
+   * @return {@code >= 0;} the write size
+   */
+  public int writeSize() {
+    return (triesSize() * TRY_ITEM_WRITE_SIZE) + encodedHandlers.length;
+  }
+
+  /**
+   * Writes this instance to the given stream.
+   *
+   * @param file {@code non-null;} file this instance is part of
+   * @param out {@code non-null;} where to write to
+   */
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    finishProcessingIfNecessary();
+
+    if (out.annotates()) {
+      annotateEntries("  ", null, out);
     }
 
-    /**
-     * Encodes the handler lists.
-     *
-     * @param file {@code non-null;} file this instance is part of
-     */
-    public void encode(DexFile file) {
-        finishProcessingIfNecessary();
+    int tableSize = table.size();
+    for (int i = 0; i < tableSize; i++) {
+      CatchTable.Entry one = table.get(i);
+      int start = one.getStart();
+      int end = one.getEnd();
+      int insnCount = end - start;
 
-        TypeIdsSection typeIds = file.getTypeIds();
-        int size = table.size();
+      if (insnCount >= 65536) {
+        throw new UnsupportedOperationException(
+            "bogus exception range: " + Hex.u4(start) + ".." + Hex.u4(end));
+      }
 
-        handlerOffsets = new TreeMap<CatchHandlerList, Integer>();
-
-        /*
-         * First add a map entry for each unique list. The tree structure
-         * will ensure they are sorted when we reiterate later.
-         */
-        for (int i = 0; i < size; i++) {
-            handlerOffsets.put(table.get(i).getHandlers(), null);
-        }
-
-        if (handlerOffsets.size() > 65535) {
-            throw new UnsupportedOperationException(
-                    "too many catch handlers");
-        }
-
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
-
-        // Write out the handlers "header" consisting of its size in entries.
-        encodedHandlerHeaderSize =
-            out.writeUleb128(handlerOffsets.size());
-
-        // Now write the lists out in order, noting the offset of each.
-        for (Map.Entry<CatchHandlerList, Integer> mapping :
-                 handlerOffsets.entrySet()) {
-            CatchHandlerList list = mapping.getKey();
-            int listSize = list.size();
-            boolean catchesAll = list.catchesAll();
-
-            // Set the offset before we do any writing.
-            mapping.setValue(out.getCursor());
-
-            if (catchesAll) {
-                // A size <= 0 means that the list ends with a catch-all.
-                out.writeSleb128(-(listSize - 1));
-                listSize--;
-            } else {
-                out.writeSleb128(listSize);
-            }
-
-            for (int i = 0; i < listSize; i++) {
-                CatchHandlerList.Entry entry = list.get(i);
-                out.writeUleb128(
-                        typeIds.indexOf(entry.getExceptionType()));
-                out.writeUleb128(entry.getHandler());
-            }
-
-            if (catchesAll) {
-                out.writeUleb128(list.get(listSize).getHandler());
-            }
-        }
-
-        encodedHandlers = out.toByteArray();
+      out.writeInt(start);
+      out.writeShort(insnCount);
+      out.writeShort(handlerOffsets.get(one.getHandlers()));
     }
 
-    /**
-     * Gets the write size of this instance, in bytes.
-     *
-     * @return {@code >= 0;} the write size
-     */
-    public int writeSize() {
-        return (triesSize() * TRY_ITEM_WRITE_SIZE) +
-                + encodedHandlers.length;
+    out.write(encodedHandlers);
+  }
+
+  /**
+   * Helper method to annotate or simply print the exception handlers.
+   * Only one of {@code printTo} or {@code annotateTo} should
+   * be non-null.
+   *
+   * @param prefix {@code non-null;} prefix for each line
+   * @param printTo {@code null-ok;} where to print to
+   * @param annotateTo {@code null-ok;} where to consume bytes and annotate to
+   */
+  private void annotateEntries(String prefix, PrintWriter printTo, AnnotatedOutput annotateTo) {
+    finishProcessingIfNecessary();
+
+    boolean consume = (annotateTo != null);
+    int amt1 = consume ? 6 : 0;
+    int amt2 = consume ? 2 : 0;
+    int size = table.size();
+    String subPrefix = prefix + "  ";
+
+    if (consume) {
+      annotateTo.annotate(0, prefix + "tries:");
+    } else {
+      printTo.println(prefix + "tries:");
     }
 
-    /**
-     * Writes this instance to the given stream.
-     *
-     * @param file {@code non-null;} file this instance is part of
-     * @param out {@code non-null;} where to write to
-     */
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        finishProcessingIfNecessary();
+    for (int i = 0; i < size; i++) {
+      CatchTable.Entry entry = table.get(i);
+      CatchHandlerList handlers = entry.getHandlers();
+      String s1 =
+          subPrefix + "try " + Hex.u2or4(entry.getStart()) + ".." + Hex.u2or4(entry.getEnd());
+      String s2 = handlers.toHuman(subPrefix, "");
 
-        if (out.annotates()) {
-            annotateEntries("  ", null, out);
-        }
-
-        int tableSize = table.size();
-        for (int i = 0; i < tableSize; i++) {
-            CatchTable.Entry one = table.get(i);
-            int start = one.getStart();
-            int end = one.getEnd();
-            int insnCount = end - start;
-
-            if (insnCount >= 65536) {
-                throw new UnsupportedOperationException(
-                        "bogus exception range: " + Hex.u4(start) + ".." +
-                        Hex.u4(end));
-            }
-
-            out.writeInt(start);
-            out.writeShort(insnCount);
-            out.writeShort(handlerOffsets.get(one.getHandlers()));
-        }
-
-        out.write(encodedHandlers);
+      if (consume) {
+        annotateTo.annotate(amt1, s1);
+        annotateTo.annotate(amt2, s2);
+      } else {
+        printTo.println(s1);
+        printTo.println(s2);
+      }
     }
 
-    /**
-     * Helper method to annotate or simply print the exception handlers.
-     * Only one of {@code printTo} or {@code annotateTo} should
-     * be non-null.
-     *
-     * @param prefix {@code non-null;} prefix for each line
-     * @param printTo {@code null-ok;} where to print to
-     * @param annotateTo {@code null-ok;} where to consume bytes and annotate to
-     */
-    private void annotateEntries(String prefix, PrintWriter printTo,
-            AnnotatedOutput annotateTo) {
-        finishProcessingIfNecessary();
-
-        boolean consume = (annotateTo != null);
-        int amt1 = consume ? 6 : 0;
-        int amt2 = consume ? 2 : 0;
-        int size = table.size();
-        String subPrefix = prefix + "  ";
-
-        if (consume) {
-            annotateTo.annotate(0, prefix + "tries:");
-        } else {
-            printTo.println(prefix + "tries:");
-        }
-
-        for (int i = 0; i < size; i++) {
-            CatchTable.Entry entry = table.get(i);
-            CatchHandlerList handlers = entry.getHandlers();
-            String s1 = subPrefix + "try " + Hex.u2or4(entry.getStart())
-                + ".." + Hex.u2or4(entry.getEnd());
-            String s2 = handlers.toHuman(subPrefix, "");
-
-            if (consume) {
-                annotateTo.annotate(amt1, s1);
-                annotateTo.annotate(amt2, s2);
-            } else {
-                printTo.println(s1);
-                printTo.println(s2);
-            }
-        }
-
-        if (! consume) {
-            // Only emit the handler lists if we are consuming bytes.
-            return;
-        }
-
-        annotateTo.annotate(0, prefix + "handlers:");
-        annotateTo.annotate(encodedHandlerHeaderSize,
-                subPrefix + "size: " + Hex.u2(handlerOffsets.size()));
-
-        int lastOffset = 0;
-        CatchHandlerList lastList = null;
-
-        for (Map.Entry<CatchHandlerList, Integer> mapping :
-                 handlerOffsets.entrySet()) {
-            CatchHandlerList list = mapping.getKey();
-            int offset = mapping.getValue();
-
-            if (lastList != null) {
-                annotateAndConsumeHandlers(lastList, lastOffset,
-                        offset - lastOffset, subPrefix, printTo, annotateTo);
-            }
-
-            lastList = list;
-            lastOffset = offset;
-        }
-
-        annotateAndConsumeHandlers(lastList, lastOffset,
-                encodedHandlers.length - lastOffset,
-                subPrefix, printTo, annotateTo);
+    if (!consume) {
+      // Only emit the handler lists if we are consuming bytes.
+      return;
     }
 
-    /**
-     * Helper for {@link #annotateEntries} to annotate a catch handler list
-     * while consuming it.
-     *
-     * @param handlers {@code non-null;} handlers to annotate
-     * @param offset {@code >= 0;} the offset of this handler
-     * @param size {@code >= 1;} the number of bytes the handlers consume
-     * @param prefix {@code non-null;} prefix for each line
-     * @param printTo {@code null-ok;} where to print to
-     * @param annotateTo {@code non-null;} where to annotate to
-     */
-    private static void annotateAndConsumeHandlers(CatchHandlerList handlers,
-            int offset, int size, String prefix, PrintWriter printTo,
-            AnnotatedOutput annotateTo) {
-        String s = handlers.toHuman(prefix, Hex.u2(offset) + ": ");
+    annotateTo.annotate(0, prefix + "handlers:");
+    annotateTo.annotate(encodedHandlerHeaderSize,
+        subPrefix + "size: " + Hex.u2(handlerOffsets.size()));
 
-        if (printTo != null) {
-            printTo.println(s);
-        }
+    int lastOffset = 0;
+    CatchHandlerList lastList = null;
 
-        annotateTo.annotate(size, s);
+    for (Map.Entry<CatchHandlerList, Integer> mapping : handlerOffsets.entrySet()) {
+      CatchHandlerList list = mapping.getKey();
+      int offset = mapping.getValue();
+
+      if (lastList != null) {
+        annotateAndConsumeHandlers(lastList,
+            lastOffset,
+            offset - lastOffset,
+            subPrefix,
+            printTo,
+            annotateTo);
+      }
+
+      lastList = list;
+      lastOffset = offset;
     }
+
+    annotateAndConsumeHandlers(lastList,
+        lastOffset,
+        encodedHandlers.length - lastOffset,
+        subPrefix,
+        printTo,
+        annotateTo);
+  }
+
+  /**
+   * Helper for {@link #annotateEntries} to annotate a catch handler list
+   * while consuming it.
+   *
+   * @param handlers {@code non-null;} handlers to annotate
+   * @param offset {@code >= 0;} the offset of this handler
+   * @param size {@code >= 1;} the number of bytes the handlers consume
+   * @param prefix {@code non-null;} prefix for each line
+   * @param printTo {@code null-ok;} where to print to
+   * @param annotateTo {@code non-null;} where to annotate to
+   */
+  private static void annotateAndConsumeHandlers(CatchHandlerList handlers,
+      int offset,
+      int size,
+      String prefix,
+      PrintWriter printTo,
+      AnnotatedOutput annotateTo) {
+    String s = handlers.toHuman(prefix, Hex.u2(offset) + ": ");
+
+    if (printTo != null) {
+      printTo.println(s);
+    }
+
+    annotateTo.annotate(size, s);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ClassDataItem.java b/dx/src/com/android/jack/dx/dex/file/ClassDataItem.java
index 8ca353c..7e9ccce 100644
--- a/dx/src/com/android/jack/dx/dex/file/ClassDataItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/ClassDataItem.java
@@ -38,389 +38,385 @@
  * {@code dex} file, as opposed to a random-access form.
  */
 public final class ClassDataItem extends OffsettedItem {
-    /** {@code non-null;} what class this data is for, just for listing generation */
-    private final CstType thisClass;
+  /** {@code non-null;} what class this data is for, just for listing generation */
+  private final CstType thisClass;
 
-    /** {@code non-null;} list of static fields */
-    private final ArrayList<EncodedField> staticFields;
+  /** {@code non-null;} list of static fields */
+  private final ArrayList<EncodedField> staticFields;
 
-    /** {@code non-null;} list of initial values for static fields */
-    private final HashMap<EncodedField, Constant> staticValues;
+  /** {@code non-null;} list of initial values for static fields */
+  private final HashMap<EncodedField, Constant> staticValues;
 
-    /** {@code non-null;} list of instance fields */
-    private final ArrayList<EncodedField> instanceFields;
+  /** {@code non-null;} list of instance fields */
+  private final ArrayList<EncodedField> instanceFields;
 
-    /** {@code non-null;} list of direct methods */
-    private final ArrayList<EncodedMethod> directMethods;
+  /** {@code non-null;} list of direct methods */
+  private final ArrayList<EncodedMethod> directMethods;
 
-    /** {@code non-null;} list of virtual methods */
-    private final ArrayList<EncodedMethod> virtualMethods;
+  /** {@code non-null;} list of virtual methods */
+  private final ArrayList<EncodedMethod> virtualMethods;
 
-    /** {@code null-ok;} static initializer list; set in {@link #addContents} */
-    private CstArray staticValuesConstant;
+  /** {@code null-ok;} static initializer list; set in {@link #addContents} */
+  private CstArray staticValuesConstant;
 
-    /**
-     * {@code null-ok;} encoded form, ready for writing to a file; set during
-     * {@link #place0}
+  /**
+   * {@code null-ok;} encoded form, ready for writing to a file; set during
+   * {@link #place0}
+   */
+  private byte[] encodedForm;
+
+  /**
+   * Constructs an instance. Its sets of members are initially
+   * empty.
+   *
+   * @param thisClass {@code non-null;} what class this data is for, just
+   * for listing generation
+   */
+  public ClassDataItem(CstType thisClass) {
+    super(1, -1);
+
+    if (thisClass == null) {
+      throw new NullPointerException("thisClass == null");
+    }
+
+    this.thisClass = thisClass;
+    this.staticFields = new ArrayList<EncodedField>(20);
+    this.staticValues = new HashMap<EncodedField, Constant>(40);
+    this.instanceFields = new ArrayList<EncodedField>(20);
+    this.directMethods = new ArrayList<EncodedMethod>(20);
+    this.virtualMethods = new ArrayList<EncodedMethod>(20);
+    this.staticValuesConstant = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_CLASS_DATA_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return toString();
+  }
+
+  /**
+   * Returns whether this instance is empty.
+   *
+   * @return {@code true} if this instance is empty or
+   * {@code false} if at least one element has been added to it
+   */
+  public boolean isEmpty() {
+    return staticFields.isEmpty() && instanceFields.isEmpty() && directMethods.isEmpty()
+        && virtualMethods.isEmpty();
+  }
+
+  /**
+   * Adds a static field.
+   *
+   * @param field {@code non-null;} the field to add
+   * @param value {@code null-ok;} initial value for the field, if any
+   */
+  public void addStaticField(EncodedField field, Constant value) {
+    if (field == null) {
+      throw new NullPointerException("field == null");
+    }
+
+    if (staticValuesConstant != null) {
+      throw new UnsupportedOperationException("static fields already sorted");
+    }
+
+    staticFields.add(field);
+    staticValues.put(field, value);
+  }
+
+  /**
+   * Adds an instance field.
+   *
+   * @param field {@code non-null;} the field to add
+   */
+  public void addInstanceField(EncodedField field) {
+    if (field == null) {
+      throw new NullPointerException("field == null");
+    }
+
+    instanceFields.add(field);
+  }
+
+  /**
+   * Adds a direct ({@code static} and/or {@code private}) method.
+   *
+   * @param method {@code non-null;} the method to add
+   */
+  public void addDirectMethod(EncodedMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
+    }
+
+    directMethods.add(method);
+  }
+
+  /**
+   * Adds a virtual method.
+   *
+   * @param method {@code non-null;} the method to add
+   */
+  public void addVirtualMethod(EncodedMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
+    }
+
+    virtualMethods.add(method);
+  }
+
+  /**
+   * Gets all the methods in this class. The returned list is not linked
+   * in any way to the underlying lists contained in this instance, but
+   * the objects contained in the list are shared.
+   *
+   * @return {@code non-null;} list of all methods
+   */
+  public ArrayList<EncodedMethod> getMethods() {
+    int sz = directMethods.size() + virtualMethods.size();
+    ArrayList<EncodedMethod> result = new ArrayList<EncodedMethod>(sz);
+
+    result.addAll(directMethods);
+    result.addAll(virtualMethods);
+
+    return result;
+  }
+
+
+  /**
+   * Prints out the contents of this instance, in a debugging-friendly
+   * way.
+   *
+   * @param out {@code non-null;} where to output to
+   * @param verbose whether to be verbose with the output
+   */
+  public void debugPrint(Writer out, boolean verbose) {
+    PrintWriter pw = Writers.printWriterFor(out);
+
+    int sz = staticFields.size();
+    for (int i = 0; i < sz; i++) {
+      pw.println("  sfields[" + i + "]: " + staticFields.get(i));
+    }
+
+    sz = instanceFields.size();
+    for (int i = 0; i < sz; i++) {
+      pw.println("  ifields[" + i + "]: " + instanceFields.get(i));
+    }
+
+    sz = directMethods.size();
+    for (int i = 0; i < sz; i++) {
+      pw.println("  dmeths[" + i + "]:");
+      directMethods.get(i).debugPrint(pw, verbose);
+    }
+
+    sz = virtualMethods.size();
+    for (int i = 0; i < sz; i++) {
+      pw.println("  vmeths[" + i + "]:");
+      virtualMethods.get(i).debugPrint(pw, verbose);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    if (!staticFields.isEmpty()) {
+      getStaticValuesConstant(); // Force the fields to be sorted.
+      for (EncodedField field : staticFields) {
+        field.addContents(file);
+      }
+    }
+
+    if (!instanceFields.isEmpty()) {
+      Collections.sort(instanceFields);
+      for (EncodedField field : instanceFields) {
+        field.addContents(file);
+      }
+    }
+
+    if (!directMethods.isEmpty()) {
+      Collections.sort(directMethods);
+      for (EncodedMethod method : directMethods) {
+        method.addContents(file);
+      }
+    }
+
+    if (!virtualMethods.isEmpty()) {
+      Collections.sort(virtualMethods);
+      for (EncodedMethod method : virtualMethods) {
+        method.addContents(file);
+      }
+    }
+  }
+
+  /**
+   * Gets a {@link CstArray} corresponding to {@link #staticValues} if
+   * it contains any non-zero non-{@code null} values.
+   *
+   * @return {@code null-ok;} the corresponding constant or {@code null} if
+   * there are no values to encode
+   */
+  public CstArray getStaticValuesConstant() {
+    if ((staticValuesConstant == null) && (staticFields.size() != 0)) {
+      staticValuesConstant = makeStaticValuesConstant();
+    }
+
+    return staticValuesConstant;
+  }
+
+  /**
+   * Gets a {@link CstArray} corresponding to {@link #staticValues} if
+   * it contains any non-zero non-{@code null} values.
+   *
+   * @return {@code null-ok;} the corresponding constant or {@code null} if
+   * there are no values to encode
+   */
+  private CstArray makeStaticValuesConstant() {
+    // First sort the statics into their final order.
+    Collections.sort(staticFields);
+
+    /*
+     * Get the size of staticValues minus any trailing zeros/nulls (both
+     * nulls per se as well as instances of CstKnownNull).
      */
-    private byte[] encodedForm;
 
-    /**
-     * Constructs an instance. Its sets of members are initially
-     * empty.
-     *
-     * @param thisClass {@code non-null;} what class this data is for, just
-     * for listing generation
-     */
-    public ClassDataItem(CstType thisClass) {
-        super(1, -1);
-
-        if (thisClass == null) {
-            throw new NullPointerException("thisClass == null");
+int size = staticFields.size();
+    while (size > 0) {
+      EncodedField field = staticFields.get(size - 1);
+      Constant cst = staticValues.get(field);
+      if (cst instanceof CstLiteralBits) {
+        // Note: CstKnownNull extends CstLiteralBits.
+        if (((CstLiteralBits) cst).getLongBits() != 0) {
+          break;
         }
-
-        this.thisClass = thisClass;
-        this.staticFields = new ArrayList<EncodedField>(20);
-        this.staticValues = new HashMap<EncodedField, Constant>(40);
-        this.instanceFields = new ArrayList<EncodedField>(20);
-        this.directMethods = new ArrayList<EncodedMethod>(20);
-        this.virtualMethods = new ArrayList<EncodedMethod>(20);
-        this.staticValuesConstant = null;
+      } else if (cst != null) {
+        break;
+      }
+      size--;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_CLASS_DATA_ITEM;
+    if (size == 0) {
+      return null;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return toString();
+    // There is something worth encoding, so build up a result.
+
+    CstArray.List list = new CstArray.List(size);
+    for (int i = 0; i < size; i++) {
+      EncodedField field = staticFields.get(i);
+      Constant cst = staticValues.get(field);
+      if (cst == null) {
+        cst = Zeroes.zeroFor(field.getRef().getType());
+      }
+      list.set(i, cst);
+    }
+    list.setImmutable();
+
+    return new CstArray(list);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // Encode the data and note the size.
+
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
+
+    encodeOutput(addedTo.getFile(), out);
+    encodedForm = out.toByteArray();
+    setWriteSize(encodedForm.length);
+  }
+
+  /**
+   * Writes out the encoded form of this instance.
+   *
+   * @param file {@code non-null;} file this instance is part of
+   * @param out {@code non-null;} where to write to
+   */
+  private void encodeOutput(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+
+    if (annotates) {
+      out.annotate(0, offsetString() + " class data for " + thisClass.toHuman());
     }
 
-    /**
-     * Returns whether this instance is empty.
-     *
-     * @return {@code true} if this instance is empty or
-     * {@code false} if at least one element has been added to it
-     */
-    public boolean isEmpty() {
-        return staticFields.isEmpty() && instanceFields.isEmpty()
-            && directMethods.isEmpty() && virtualMethods.isEmpty();
+    encodeSize(file, out, "static_fields", staticFields.size());
+    encodeSize(file, out, "instance_fields", instanceFields.size());
+    encodeSize(file, out, "direct_methods", directMethods.size());
+    encodeSize(file, out, "virtual_methods", virtualMethods.size());
+
+    encodeList(file, out, "static_fields", staticFields);
+    encodeList(file, out, "instance_fields", instanceFields);
+    encodeList(file, out, "direct_methods", directMethods);
+    encodeList(file, out, "virtual_methods", virtualMethods);
+
+    if (annotates) {
+      out.endAnnotation();
+    }
+  }
+
+  /**
+   * Helper for {@link #encodeOutput}, which writes out the given
+   * size value, annotating it as well (if annotations are enabled).
+   *
+   * @param file {@code non-null;} file this instance is part of
+   * @param out {@code non-null;} where to write to
+   * @param label {@code non-null;} the label for the purposes of annotation
+   * @param size {@code >= 0;} the size to write
+   */
+  private static void encodeSize(DexFile file, AnnotatedOutput out, String label, int size) {
+    if (out.annotates()) {
+      out.annotate(String.format("  %-21s %08x", label + "_size:", size));
     }
 
-    /**
-     * Adds a static field.
-     *
-     * @param field {@code non-null;} the field to add
-     * @param value {@code null-ok;} initial value for the field, if any
-     */
-    public void addStaticField(EncodedField field, Constant value) {
-        if (field == null) {
-            throw new NullPointerException("field == null");
-        }
+    out.writeUleb128(size);
+  }
 
-        if (staticValuesConstant != null) {
-            throw new UnsupportedOperationException(
-                    "static fields already sorted");
-        }
+  /**
+   * Helper for {@link #encodeOutput}, which writes out the given
+   * list. It also annotates the items (if any and if annotations
+   * are enabled).
+   *
+   * @param file {@code non-null;} file this instance is part of
+   * @param out {@code non-null;} where to write to
+   * @param label {@code non-null;} the label for the purposes of annotation
+   * @param list {@code non-null;} the list in question
+   */
+  private static void encodeList(DexFile file, AnnotatedOutput out, String label,
+      ArrayList<? extends EncodedMember> list) {
+    int size = list.size();
+    int lastIndex = 0;
 
-        staticFields.add(field);
-        staticValues.put(field, value);
+    if (size == 0) {
+      return;
     }
 
-    /**
-     * Adds an instance field.
-     *
-     * @param field {@code non-null;} the field to add
-     */
-    public void addInstanceField(EncodedField field) {
-        if (field == null) {
-            throw new NullPointerException("field == null");
-        }
-
-        instanceFields.add(field);
+    if (out.annotates()) {
+      out.annotate(0, "  " + label + ":");
     }
 
-    /**
-     * Adds a direct ({@code static} and/or {@code private}) method.
-     *
-     * @param method {@code non-null;} the method to add
-     */
-    public void addDirectMethod(EncodedMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        directMethods.add(method);
+    for (int i = 0; i < size; i++) {
+      lastIndex = list.get(i).encode(file, out, lastIndex, i);
     }
+  }
 
-    /**
-     * Adds a virtual method.
-     *
-     * @param method {@code non-null;} the method to add
-     */
-    public void addVirtualMethod(EncodedMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
 
-        virtualMethods.add(method);
+    if (annotates) {
+      /*
+       * The output is to be annotated, so redo the work previously
+       * done by place0(), except this time annotations will actually
+       * get emitted.
+       */
+      encodeOutput(file, out);
+    } else {
+      out.write(encodedForm);
     }
-
-    /**
-     * Gets all the methods in this class. The returned list is not linked
-     * in any way to the underlying lists contained in this instance, but
-     * the objects contained in the list are shared.
-     *
-     * @return {@code non-null;} list of all methods
-     */
-    public ArrayList<EncodedMethod> getMethods() {
-        int sz = directMethods.size() + virtualMethods.size();
-        ArrayList<EncodedMethod> result = new ArrayList<EncodedMethod>(sz);
-
-        result.addAll(directMethods);
-        result.addAll(virtualMethods);
-
-        return result;
-    }
-
-
-    /**
-     * Prints out the contents of this instance, in a debugging-friendly
-     * way.
-     *
-     * @param out {@code non-null;} where to output to
-     * @param verbose whether to be verbose with the output
-     */
-    public void debugPrint(Writer out, boolean verbose) {
-        PrintWriter pw = Writers.printWriterFor(out);
-
-        int sz = staticFields.size();
-        for (int i = 0; i < sz; i++) {
-            pw.println("  sfields[" + i + "]: " + staticFields.get(i));
-        }
-
-        sz = instanceFields.size();
-        for (int i = 0; i < sz; i++) {
-            pw.println("  ifields[" + i + "]: " + instanceFields.get(i));
-        }
-
-        sz = directMethods.size();
-        for (int i = 0; i < sz; i++) {
-            pw.println("  dmeths[" + i + "]:");
-            directMethods.get(i).debugPrint(pw, verbose);
-        }
-
-        sz = virtualMethods.size();
-        for (int i = 0; i < sz; i++) {
-            pw.println("  vmeths[" + i + "]:");
-            virtualMethods.get(i).debugPrint(pw, verbose);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        if (!staticFields.isEmpty()) {
-            getStaticValuesConstant(); // Force the fields to be sorted.
-            for (EncodedField field : staticFields) {
-                field.addContents(file);
-            }
-        }
-
-        if (!instanceFields.isEmpty()) {
-            Collections.sort(instanceFields);
-            for (EncodedField field : instanceFields) {
-                field.addContents(file);
-            }
-        }
-
-        if (!directMethods.isEmpty()) {
-            Collections.sort(directMethods);
-            for (EncodedMethod method : directMethods) {
-                method.addContents(file);
-            }
-        }
-
-        if (!virtualMethods.isEmpty()) {
-            Collections.sort(virtualMethods);
-            for (EncodedMethod method : virtualMethods) {
-                method.addContents(file);
-            }
-        }
-    }
-
-    /**
-     * Gets a {@link CstArray} corresponding to {@link #staticValues} if
-     * it contains any non-zero non-{@code null} values.
-     *
-     * @return {@code null-ok;} the corresponding constant or {@code null} if
-     * there are no values to encode
-     */
-    public CstArray getStaticValuesConstant() {
-        if ((staticValuesConstant == null) && (staticFields.size() != 0)) {
-            staticValuesConstant = makeStaticValuesConstant();
-        }
-
-        return staticValuesConstant;
-    }
-
-    /**
-     * Gets a {@link CstArray} corresponding to {@link #staticValues} if
-     * it contains any non-zero non-{@code null} values.
-     *
-     * @return {@code null-ok;} the corresponding constant or {@code null} if
-     * there are no values to encode
-     */
-    private CstArray makeStaticValuesConstant() {
-        // First sort the statics into their final order.
-        Collections.sort(staticFields);
-
-        /*
-         * Get the size of staticValues minus any trailing zeros/nulls (both
-         * nulls per se as well as instances of CstKnownNull).
-         */
-
-        int size = staticFields.size();
-        while (size > 0) {
-            EncodedField field = staticFields.get(size - 1);
-            Constant cst = staticValues.get(field);
-            if (cst instanceof CstLiteralBits) {
-                // Note: CstKnownNull extends CstLiteralBits.
-                if (((CstLiteralBits) cst).getLongBits() != 0) {
-                    break;
-                }
-            } else if (cst != null) {
-                break;
-            }
-            size--;
-        }
-
-        if (size == 0) {
-            return null;
-        }
-
-        // There is something worth encoding, so build up a result.
-
-        CstArray.List list = new CstArray.List(size);
-        for (int i = 0; i < size; i++) {
-            EncodedField field = staticFields.get(i);
-            Constant cst = staticValues.get(field);
-            if (cst == null) {
-                cst = Zeroes.zeroFor(field.getRef().getType());
-            }
-            list.set(i, cst);
-        }
-        list.setImmutable();
-
-        return new CstArray(list);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // Encode the data and note the size.
-
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
-
-        encodeOutput(addedTo.getFile(), out);
-        encodedForm = out.toByteArray();
-        setWriteSize(encodedForm.length);
-    }
-
-    /**
-     * Writes out the encoded form of this instance.
-     *
-     * @param file {@code non-null;} file this instance is part of
-     * @param out {@code non-null;} where to write to
-     */
-    private void encodeOutput(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-
-        if (annotates) {
-            out.annotate(0, offsetString() + " class data for " +
-                    thisClass.toHuman());
-        }
-
-        encodeSize(file, out, "static_fields", staticFields.size());
-        encodeSize(file, out, "instance_fields", instanceFields.size());
-        encodeSize(file, out, "direct_methods", directMethods.size());
-        encodeSize(file, out, "virtual_methods", virtualMethods.size());
-
-        encodeList(file, out, "static_fields", staticFields);
-        encodeList(file, out, "instance_fields", instanceFields);
-        encodeList(file, out, "direct_methods", directMethods);
-        encodeList(file, out, "virtual_methods", virtualMethods);
-
-        if (annotates) {
-            out.endAnnotation();
-        }
-    }
-
-    /**
-     * Helper for {@link #encodeOutput}, which writes out the given
-     * size value, annotating it as well (if annotations are enabled).
-     *
-     * @param file {@code non-null;} file this instance is part of
-     * @param out {@code non-null;} where to write to
-     * @param label {@code non-null;} the label for the purposes of annotation
-     * @param size {@code >= 0;} the size to write
-     */
-    private static void encodeSize(DexFile file, AnnotatedOutput out,
-            String label, int size) {
-        if (out.annotates()) {
-            out.annotate(String.format("  %-21s %08x", label + "_size:",
-                            size));
-        }
-
-        out.writeUleb128(size);
-    }
-
-    /**
-     * Helper for {@link #encodeOutput}, which writes out the given
-     * list. It also annotates the items (if any and if annotations
-     * are enabled).
-     *
-     * @param file {@code non-null;} file this instance is part of
-     * @param out {@code non-null;} where to write to
-     * @param label {@code non-null;} the label for the purposes of annotation
-     * @param list {@code non-null;} the list in question
-     */
-    private static void encodeList(DexFile file, AnnotatedOutput out,
-            String label, ArrayList<? extends EncodedMember> list) {
-        int size = list.size();
-        int lastIndex = 0;
-
-        if (size == 0) {
-            return;
-        }
-
-        if (out.annotates()) {
-            out.annotate(0, "  " + label + ":");
-        }
-
-        for (int i = 0; i < size; i++) {
-            lastIndex = list.get(i).encode(file, out, lastIndex, i);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-
-        if (annotates) {
-            /*
-             * The output is to be annotated, so redo the work previously
-             * done by place0(), except this time annotations will actually
-             * get emitted.
-             */
-            encodeOutput(file, out);
-        } else {
-            out.write(encodedForm);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ClassDefItem.java b/dx/src/com/android/jack/dx/dex/file/ClassDefItem.java
index 7f485a6..e845fab 100644
--- a/dx/src/com/android/jack/dx/dex/file/ClassDefItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/ClassDefItem.java
@@ -43,366 +43,351 @@
  */
 public final class ClassDefItem extends IndexedItem {
 
-    /** {@code non-null;} type constant for this class */
-    private final CstType thisClass;
+  /** {@code non-null;} type constant for this class */
+  private final CstType thisClass;
 
-    /** access flags */
-    private final int accessFlags;
+  /** access flags */
+  private final int accessFlags;
 
-    /**
-     * {@code null-ok;} superclass or {@code null} if this class is a/the
-     * root class
+  /**
+   * {@code null-ok;} superclass or {@code null} if this class is a/the
+   * root class
+   */
+  private final CstType superclass;
+
+  /** {@code null-ok;} list of implemented interfaces */
+  private TypeListItem interfaces;
+
+  /** {@code null-ok;} source file name or {@code null} if unknown */
+  private final CstString sourceFile;
+
+  /** {@code non-null;} associated class data object */
+  private final ClassDataItem classData;
+
+  /**
+   * {@code null-ok;} item wrapper for the static values, initialized
+   * in {@link #addContents}
+   */
+  private EncodedArrayItem staticValuesItem;
+
+  /** {@code non-null;} annotations directory */
+  private AnnotationsDirectoryItem annotationsDirectory;
+
+  /**
+   * Constructs an instance. Its sets of members and annotations are
+   * initially empty.
+   *
+   * @param thisClass {@code non-null;} type constant for this class
+   * @param accessFlags access flags
+   * @param superclass {@code null-ok;} superclass or {@code null} if
+   * this class is a/the root class
+   * @param interfaces {@code non-null;} list of implemented interfaces
+   * @param sourceFile {@code null-ok;} source file name or
+   * {@code null} if unknown
+   */
+  public ClassDefItem(CstType thisClass, int accessFlags, CstType superclass, TypeList interfaces,
+      CstString sourceFile) {
+    if (thisClass == null) {
+      throw new NullPointerException("thisClass == null");
+    }
+
+    /*
+     * TODO(dx team): Maybe check accessFlags and superclass, at
+     * least for easily-checked stuff?
      */
-    private final CstType superclass;
 
-    /** {@code null-ok;} list of implemented interfaces */
-    private TypeListItem interfaces;
+if (interfaces == null) {
+      throw new NullPointerException("interfaces == null");
+    }
 
-    /** {@code null-ok;} source file name or {@code null} if unknown */
-    private final CstString sourceFile;
+    this.thisClass = thisClass;
+    this.accessFlags = accessFlags;
+    this.superclass = superclass;
+    this.interfaces = (interfaces.size() == 0) ? null : new TypeListItem(interfaces);
+    this.sourceFile = sourceFile;
+    this.classData = new ClassDataItem(thisClass);
+    this.staticValuesItem = null;
+    this.annotationsDirectory = new AnnotationsDirectoryItem();
+  }
 
-    /** {@code non-null;} associated class data object */
-    private final ClassDataItem classData;
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_CLASS_DEF_ITEM;
+  }
 
-    /**
-     * {@code null-ok;} item wrapper for the static values, initialized
-     * in {@link #addContents}
-     */
-    private EncodedArrayItem staticValuesItem;
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.CLASS_DEF_ITEM;
+  }
 
-    /** {@code non-null;} annotations directory */
-    private AnnotationsDirectoryItem annotationsDirectory;
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    MixedItemSection byteData = file.getByteData();
+    MixedItemSection wordData = file.getWordData();
+    MixedItemSection typeLists = file.getTypeLists();
+    StringIdsSection stringIds = file.getStringIds();
 
-    /**
-     * Constructs an instance. Its sets of members and annotations are
-     * initially empty.
-     *
-     * @param thisClass {@code non-null;} type constant for this class
-     * @param accessFlags access flags
-     * @param superclass {@code null-ok;} superclass or {@code null} if
-     * this class is a/the root class
-     * @param interfaces {@code non-null;} list of implemented interfaces
-     * @param sourceFile {@code null-ok;} source file name or
-     * {@code null} if unknown
-     */
-    public ClassDefItem(CstType thisClass, int accessFlags,
-            CstType superclass, TypeList interfaces, CstString sourceFile) {
-        if (thisClass == null) {
-            throw new NullPointerException("thisClass == null");
+    typeIds.intern(thisClass);
+
+    if (!classData.isEmpty()) {
+      MixedItemSection classDataSection = file.getClassData();
+      classDataSection.add(classData);
+
+      CstArray staticValues = classData.getStaticValuesConstant();
+      if (staticValues != null) {
+        staticValuesItem = byteData.intern(new EncodedArrayItem(staticValues));
+      }
+    }
+
+    if (superclass != null) {
+      typeIds.intern(superclass);
+    }
+
+    if (interfaces != null) {
+      interfaces = typeLists.intern(interfaces);
+    }
+
+    if (sourceFile != null) {
+      stringIds.intern(sourceFile);
+    }
+
+    if (!annotationsDirectory.isEmpty()) {
+      if (annotationsDirectory.isInternable()) {
+        annotationsDirectory = wordData.intern(annotationsDirectory);
+      } else {
+        wordData.add(annotationsDirectory);
+      }
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    TypeIdsSection typeIds = file.getTypeIds();
+    int classIdx = typeIds.indexOf(thisClass);
+    int superIdx = (superclass == null) ? -1 : typeIds.indexOf(superclass);
+    int interOff = OffsettedItem.getAbsoluteOffsetOr0(interfaces);
+    int annoOff = annotationsDirectory.isEmpty() ? 0 : annotationsDirectory.getAbsoluteOffset();
+    int sourceFileIdx = (sourceFile == null) ? -1 : file.getStringIds().indexOf(sourceFile);
+    int dataOff = classData.isEmpty() ? 0 : classData.getAbsoluteOffset();
+    int staticValuesOff = OffsettedItem.getAbsoluteOffsetOr0(staticValuesItem);
+
+    if (annotates) {
+      out.annotate(0, indexString() + ' ' + thisClass.toHuman());
+      out.annotate(4, "  class_idx:           " + Hex.u4(classIdx));
+      out.annotate(4, "  access_flags:        " + AccessFlags.classString(accessFlags));
+      out.annotate(4, "  superclass_idx:      " + Hex.u4(superIdx) + " // "
+          + ((superclass == null) ? "<none>" : superclass.toHuman()));
+      out.annotate(4, "  interfaces_off:      " + Hex.u4(interOff));
+      if (interOff != 0) {
+        TypeList list = interfaces.getList();
+        int sz = list.size();
+        for (int i = 0; i < sz; i++) {
+          out.annotate(0, "    " + list.getType(i).toHuman());
         }
-
-        /*
-         * TODO: Maybe check accessFlags and superclass, at
-         * least for easily-checked stuff?
-         */
-
-        if (interfaces == null) {
-            throw new NullPointerException("interfaces == null");
-        }
-
-        this.thisClass = thisClass;
-        this.accessFlags = accessFlags;
-        this.superclass = superclass;
-        this.interfaces =
-            (interfaces.size() == 0) ? null :  new TypeListItem(interfaces);
-        this.sourceFile = sourceFile;
-        this.classData = new ClassDataItem(thisClass);
-        this.staticValuesItem = null;
-        this.annotationsDirectory = new AnnotationsDirectoryItem();
+      }
+      out.annotate(4, "  source_file_idx:     " + Hex.u4(sourceFileIdx) + " // "
+          + ((sourceFile == null) ? "<none>" : sourceFile.toHuman()));
+      out.annotate(4, "  annotations_off:     " + Hex.u4(annoOff));
+      out.annotate(4, "  class_data_off:      " + Hex.u4(dataOff));
+      out.annotate(4, "  static_values_off:   " + Hex.u4(staticValuesOff));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_CLASS_DEF_ITEM;
+    out.writeInt(classIdx);
+    out.writeInt(accessFlags);
+    out.writeInt(superIdx);
+    out.writeInt(interOff);
+    out.writeInt(sourceFileIdx);
+    out.writeInt(annoOff);
+    out.writeInt(dataOff);
+    out.writeInt(staticValuesOff);
+  }
+
+  /**
+   * Gets the constant corresponding to this class.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public CstType getThisClass() {
+    return thisClass;
+  }
+
+  /**
+   * Gets the access flags.
+   *
+   * @return the access flags
+   */
+  public int getAccessFlags() {
+    return accessFlags;
+  }
+
+  /**
+   * Gets the superclass.
+   *
+   * @return {@code null-ok;} the superclass or {@code null} if
+   * this class is a/the root class
+   */
+  public CstType getSuperclass() {
+    return superclass;
+  }
+
+  /**
+   * Gets the list of interfaces implemented.
+   *
+   * @return {@code non-null;} the interfaces list
+   */
+  public TypeList getInterfaces() {
+    if (interfaces == null) {
+      return StdTypeList.EMPTY;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.CLASS_DEF_ITEM;
-    }
+    return interfaces.getList();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        MixedItemSection byteData = file.getByteData();
-        MixedItemSection wordData = file.getWordData();
-        MixedItemSection typeLists = file.getTypeLists();
-        StringIdsSection stringIds = file.getStringIds();
+  /**
+   * Gets the source file name.
+   *
+   * @return {@code null-ok;} the source file name or {@code null} if unknown
+   */
+  public CstString getSourceFile() {
+    return sourceFile;
+  }
 
-        typeIds.intern(thisClass);
+  /**
+   * Adds a static field.
+   *
+   * @param field {@code non-null;} the field to add
+   * @param value {@code null-ok;} initial value for the field, if any
+   */
+  public void addStaticField(EncodedField field, Constant value) {
+    classData.addStaticField(field, value);
+  }
 
-        if (!classData.isEmpty()) {
-            MixedItemSection classDataSection = file.getClassData();
-            classDataSection.add(classData);
+  /**
+   * Adds an instance field.
+   *
+   * @param field {@code non-null;} the field to add
+   */
+  public void addInstanceField(EncodedField field) {
+    classData.addInstanceField(field);
+  }
 
-            CstArray staticValues = classData.getStaticValuesConstant();
-            if (staticValues != null) {
-                staticValuesItem =
-                    byteData.intern(new EncodedArrayItem(staticValues));
-            }
-        }
+  /**
+   * Adds a direct ({@code static} and/or {@code private}) method.
+   *
+   * @param method {@code non-null;} the method to add
+   */
+  public void addDirectMethod(EncodedMethod method) {
+    classData.addDirectMethod(method);
+  }
 
-        if (superclass != null) {
-            typeIds.intern(superclass);
-        }
+  /**
+   * Adds a virtual method.
+   *
+   * @param method {@code non-null;} the method to add
+   */
+  public void addVirtualMethod(EncodedMethod method) {
+    classData.addVirtualMethod(method);
+  }
 
-        if (interfaces != null) {
-            interfaces = typeLists.intern(interfaces);
-        }
+  /**
+   * Gets all the methods in this class. The returned list is not linked
+   * in any way to the underlying lists contained in this instance, but
+   * the objects contained in the list are shared.
+   *
+   * @return {@code non-null;} list of all methods
+   */
+  public ArrayList<EncodedMethod> getMethods() {
+    return classData.getMethods();
+  }
 
-        if (sourceFile != null) {
-            stringIds.intern(sourceFile);
-        }
+  /**
+   * Sets the direct annotations on this class. These are annotations
+   * made on the class, per se, as opposed to on one of its members.
+   * It is only valid to call this method at most once per instance.
+   *
+   * @param annotations {@code non-null;} annotations to set for this class
+   */
+  public void setClassAnnotations(Annotations annotations) {
+    annotationsDirectory.setClassAnnotations(annotations);
+  }
 
-        if (! annotationsDirectory.isEmpty()) {
-            if (annotationsDirectory.isInternable()) {
-                annotationsDirectory = wordData.intern(annotationsDirectory);
-            } else {
-                wordData.add(annotationsDirectory);
-            }
-        }
-    }
+  /**
+   * Adds a field annotations item to this class.
+   *
+   * @param field {@code non-null;} field in question
+   * @param annotations {@code non-null;} associated annotations to add
+   */
+  public void addFieldAnnotations(CstFieldRef field, Annotations annotations) {
+    annotationsDirectory.addFieldAnnotations(field, annotations);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        TypeIdsSection typeIds = file.getTypeIds();
-        int classIdx = typeIds.indexOf(thisClass);
-        int superIdx = (superclass == null) ? -1 :
-            typeIds.indexOf(superclass);
-        int interOff = OffsettedItem.getAbsoluteOffsetOr0(interfaces);
-        int annoOff = annotationsDirectory.isEmpty() ? 0 :
-            annotationsDirectory.getAbsoluteOffset();
-        int sourceFileIdx = (sourceFile == null) ? -1 :
-            file.getStringIds().indexOf(sourceFile);
-        int dataOff = classData.isEmpty()? 0 : classData.getAbsoluteOffset();
-        int staticValuesOff =
-            OffsettedItem.getAbsoluteOffsetOr0(staticValuesItem);
+  /**
+   * Adds a method annotations item to this class.
+   *
+   * @param method {@code non-null;} method in question
+   * @param annotations {@code non-null;} associated annotations to add
+   */
+  public void addMethodAnnotations(CstMethodRef method, Annotations annotations) {
+    annotationsDirectory.addMethodAnnotations(method, annotations);
+  }
 
-        if (annotates) {
-            out.annotate(0, indexString() + ' ' + thisClass.toHuman());
-            out.annotate(4, "  class_idx:           " + Hex.u4(classIdx));
-            out.annotate(4, "  access_flags:        " +
-                         AccessFlags.classString(accessFlags));
-            out.annotate(4, "  superclass_idx:      " + Hex.u4(superIdx) +
-                         " // " + ((superclass == null) ? "<none>" :
-                          superclass.toHuman()));
-            out.annotate(4, "  interfaces_off:      " + Hex.u4(interOff));
-            if (interOff != 0) {
-                TypeList list = interfaces.getList();
-                int sz = list.size();
-                for (int i = 0; i < sz; i++) {
-                    out.annotate(0, "    " + list.getType(i).toHuman());
-                }
-            }
-            out.annotate(4, "  source_file_idx:     " + Hex.u4(sourceFileIdx) +
-                         " // " + ((sourceFile == null) ? "<none>" :
-                          sourceFile.toHuman()));
-            out.annotate(4, "  annotations_off:     " + Hex.u4(annoOff));
-            out.annotate(4, "  class_data_off:      " + Hex.u4(dataOff));
-            out.annotate(4, "  static_values_off:   " +
-                    Hex.u4(staticValuesOff));
-        }
+  /**
+   * Adds a parameter annotations item to this class.
+   *
+   * @param method {@code non-null;} method in question
+   * @param list {@code non-null;} associated list of annotation sets to add
+   */
+  public void addParameterAnnotations(CstMethodRef method, AnnotationsList list) {
+    annotationsDirectory.addParameterAnnotations(method, list);
+  }
 
-        out.writeInt(classIdx);
-        out.writeInt(accessFlags);
-        out.writeInt(superIdx);
-        out.writeInt(interOff);
-        out.writeInt(sourceFileIdx);
-        out.writeInt(annoOff);
-        out.writeInt(dataOff);
-        out.writeInt(staticValuesOff);
-    }
+  /**
+   * Gets the method annotations for a given method, if any. This is
+   * meant for use by debugging / dumping code.
+   *
+   * @param method {@code non-null;} the method
+   * @return {@code null-ok;} the method annotations, if any
+   */
+  public Annotations getMethodAnnotations(CstMethodRef method) {
+    return annotationsDirectory.getMethodAnnotations(method);
+  }
 
-    /**
-     * Gets the constant corresponding to this class.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public CstType getThisClass() {
-        return thisClass;
-    }
+  /**
+   * Gets the parameter annotations for a given method, if any. This is
+   * meant for use by debugging / dumping code.
+   *
+   * @param method {@code non-null;} the method
+   * @return {@code null-ok;} the parameter annotations, if any
+   */
+  public AnnotationsList getParameterAnnotations(CstMethodRef method) {
+    return annotationsDirectory.getParameterAnnotations(method);
+  }
 
-    /**
-     * Gets the access flags.
-     *
-     * @return the access flags
-     */
-    public int getAccessFlags() {
-        return accessFlags;
-    }
+  /**
+   * Prints out the contents of this instance, in a debugging-friendly
+   * way.
+   *
+   * @param out {@code non-null;} where to output to
+   * @param verbose whether to be verbose with the output
+   */
+  public void debugPrint(Writer out, boolean verbose) {
+    PrintWriter pw = Writers.printWriterFor(out);
 
-    /**
-     * Gets the superclass.
-     *
-     * @return {@code null-ok;} the superclass or {@code null} if
-     * this class is a/the root class
-     */
-    public CstType getSuperclass() {
-        return superclass;
-    }
+    pw.println(getClass().getName() + " {");
+    pw.println("  accessFlags: " + Hex.u2(accessFlags));
+    pw.println("  superclass: " + superclass);
+    pw.println("  interfaces: " + ((interfaces == null) ? "<none>" : interfaces));
+    pw.println("  sourceFile: " + ((sourceFile == null) ? "<none>" : sourceFile.toQuoted()));
 
-    /**
-     * Gets the list of interfaces implemented.
-     *
-     * @return {@code non-null;} the interfaces list
-     */
-    public TypeList getInterfaces() {
-        if (interfaces == null) {
-            return StdTypeList.EMPTY;
-        }
+    classData.debugPrint(out, verbose);
+    annotationsDirectory.debugPrint(pw);
 
-        return interfaces.getList();
-    }
-
-    /**
-     * Gets the source file name.
-     *
-     * @return {@code null-ok;} the source file name or {@code null} if unknown
-     */
-    public CstString getSourceFile() {
-        return sourceFile;
-    }
-
-    /**
-     * Adds a static field.
-     *
-     * @param field {@code non-null;} the field to add
-     * @param value {@code null-ok;} initial value for the field, if any
-     */
-    public void addStaticField(EncodedField field, Constant value) {
-        classData.addStaticField(field, value);
-    }
-
-    /**
-     * Adds an instance field.
-     *
-     * @param field {@code non-null;} the field to add
-     */
-    public void addInstanceField(EncodedField field) {
-        classData.addInstanceField(field);
-    }
-
-    /**
-     * Adds a direct ({@code static} and/or {@code private}) method.
-     *
-     * @param method {@code non-null;} the method to add
-     */
-    public void addDirectMethod(EncodedMethod method) {
-        classData.addDirectMethod(method);
-    }
-
-    /**
-     * Adds a virtual method.
-     *
-     * @param method {@code non-null;} the method to add
-     */
-    public void addVirtualMethod(EncodedMethod method) {
-        classData.addVirtualMethod(method);
-    }
-
-    /**
-     * Gets all the methods in this class. The returned list is not linked
-     * in any way to the underlying lists contained in this instance, but
-     * the objects contained in the list are shared.
-     *
-     * @return {@code non-null;} list of all methods
-     */
-    public ArrayList<EncodedMethod> getMethods() {
-        return classData.getMethods();
-    }
-
-    /**
-     * Sets the direct annotations on this class. These are annotations
-     * made on the class, per se, as opposed to on one of its members.
-     * It is only valid to call this method at most once per instance.
-     *
-     * @param annotations {@code non-null;} annotations to set for this class
-     */
-    public void setClassAnnotations(Annotations annotations) {
-        annotationsDirectory.setClassAnnotations(annotations);
-    }
-
-    /**
-     * Adds a field annotations item to this class.
-     *
-     * @param field {@code non-null;} field in question
-     * @param annotations {@code non-null;} associated annotations to add
-     */
-    public void addFieldAnnotations(CstFieldRef field,
-            Annotations annotations) {
-        annotationsDirectory.addFieldAnnotations(field, annotations);
-    }
-
-    /**
-     * Adds a method annotations item to this class.
-     *
-     * @param method {@code non-null;} method in question
-     * @param annotations {@code non-null;} associated annotations to add
-     */
-    public void addMethodAnnotations(CstMethodRef method,
-            Annotations annotations) {
-        annotationsDirectory.addMethodAnnotations(method, annotations);
-    }
-
-    /**
-     * Adds a parameter annotations item to this class.
-     *
-     * @param method {@code non-null;} method in question
-     * @param list {@code non-null;} associated list of annotation sets to add
-     */
-    public void addParameterAnnotations(CstMethodRef method,
-            AnnotationsList list) {
-        annotationsDirectory.addParameterAnnotations(method, list);
-    }
-
-    /**
-     * Gets the method annotations for a given method, if any. This is
-     * meant for use by debugging / dumping code.
-     *
-     * @param method {@code non-null;} the method
-     * @return {@code null-ok;} the method annotations, if any
-     */
-    public Annotations getMethodAnnotations(CstMethodRef method) {
-        return annotationsDirectory.getMethodAnnotations(method);
-    }
-
-    /**
-     * Gets the parameter annotations for a given method, if any. This is
-     * meant for use by debugging / dumping code.
-     *
-     * @param method {@code non-null;} the method
-     * @return {@code null-ok;} the parameter annotations, if any
-     */
-    public AnnotationsList getParameterAnnotations(CstMethodRef method) {
-        return annotationsDirectory.getParameterAnnotations(method);
-    }
-
-    /**
-     * Prints out the contents of this instance, in a debugging-friendly
-     * way.
-     *
-     * @param out {@code non-null;} where to output to
-     * @param verbose whether to be verbose with the output
-     */
-    public void debugPrint(Writer out, boolean verbose) {
-        PrintWriter pw = Writers.printWriterFor(out);
-
-        pw.println(getClass().getName() + " {");
-        pw.println("  accessFlags: " + Hex.u2(accessFlags));
-        pw.println("  superclass: " + superclass);
-        pw.println("  interfaces: " +
-                ((interfaces == null) ? "<none>" : interfaces));
-        pw.println("  sourceFile: " +
-                ((sourceFile == null) ? "<none>" : sourceFile.toQuoted()));
-
-        classData.debugPrint(out, verbose);
-        annotationsDirectory.debugPrint(pw);
-
-        pw.println("}");
-    }
+    pw.println("}");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ClassDefsSection.java b/dx/src/com/android/jack/dx/dex/file/ClassDefsSection.java
index 512ffc1..0c66c50 100644
--- a/dx/src/com/android/jack/dx/dex/file/ClassDefsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/ClassDefsSection.java
@@ -31,157 +31,157 @@
  * Class definitions list section of a {@code .dex} file.
  */
 public final class ClassDefsSection extends UniformItemSection {
-    /**
-     * {@code non-null;} map from type constants for classes to {@link
-     * ClassDefItem} instances that define those classes
+  /**
+   * {@code non-null;} map from type constants for classes to {@link
+   * ClassDefItem} instances that define those classes
+   */
+  private final TreeMap<Type, ClassDefItem> classDefs;
+
+  /** {@code null-ok;} ordered list of classes; set in {@link #orderItems} */
+  private ArrayList<ClassDefItem> orderedDefs;
+
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public ClassDefsSection(DexFile file) {
+    super("class_defs", file, 4);
+
+    classDefs = new TreeMap<Type, ClassDefItem>();
+    orderedDefs = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    if (orderedDefs != null) {
+      return orderedDefs;
+    }
+
+    return classDefs.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
+    }
+
+    throwIfNotPrepared();
+
+    Type type = ((CstType) cst).getClassType();
+    IndexedItem result = classDefs.get(type);
+
+    if (result == null) {
+      throw new IllegalArgumentException("not found");
+    }
+
+    return result;
+  }
+
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
+
+    int sz = classDefs.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
+
+    if (out.annotates()) {
+      out.annotate(4, "class_defs_size: " + Hex.u4(sz));
+      out.annotate(4, "class_defs_off:  " + Hex.u4(offset));
+    }
+
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
+
+  /**
+   * Adds an element to this instance. It is illegal to attempt to add more
+   * than one class with the same name.
+   *
+   * @param clazz {@code non-null;} the class def to add
+   */
+  public void add(ClassDefItem clazz) {
+    Type type;
+
+    try {
+      type = clazz.getThisClass().getClassType();
+    } catch (NullPointerException ex) {
+      // Elucidate the exception.
+      throw new NullPointerException("clazz == null");
+    }
+
+    throwIfPrepared();
+
+    if (classDefs.get(type) != null) {
+      throw new IllegalArgumentException("already added: " + type);
+    }
+
+    classDefs.put(type, clazz);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    int sz = classDefs.size();
+    int idx = 0;
+
+    orderedDefs = new ArrayList<ClassDefItem>(sz);
+
+    /*
+     * Iterate over all the classes, recursively assigning an
+     * index to each, implicitly skipping the ones that have
+     * already been assigned by the time this (top-level)
+     * iteration reaches them.
      */
-    private final TreeMap<Type, ClassDefItem> classDefs;
+    for (Type type : classDefs.keySet()) {
+      idx = orderItems0(type, idx, sz - idx);
+    }
+  }
 
-    /** {@code null-ok;} ordered list of classes; set in {@link #orderItems} */
-    private ArrayList<ClassDefItem> orderedDefs;
+  /**
+   * Helper for {@link #orderItems}, which recursively assigns indices
+   * to classes.
+   *
+   * @param type {@code null-ok;} type ref to assign, if any
+   * @param idx {@code >= 0;} the next index to assign
+   * @param maxDepth maximum recursion depth; if negative, this will
+   * throw an exception indicating class definition circularity
+   * @return {@code >= 0;} the next index to assign
+   */
+  private int orderItems0(Type type, int idx, int maxDepth) {
+    ClassDefItem c = classDefs.get(type);
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public ClassDefsSection(DexFile file) {
-        super("class_defs", file, 4);
-
-        classDefs = new TreeMap<Type, ClassDefItem>();
-        orderedDefs = null;
+    if ((c == null) || (c.hasIndex())) {
+      return idx;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        if (orderedDefs != null) {
-            return orderedDefs;
-        }
-
-        return classDefs.values();
+    if (maxDepth < 0) {
+      throw new RuntimeException("class circularity with " + type);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
+    maxDepth--;
 
-        throwIfNotPrepared();
-
-        Type type = ((CstType) cst).getClassType();
-        IndexedItem result = classDefs.get(type);
-
-        if (result == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return result;
+    CstType superclassCst = c.getSuperclass();
+    if (superclassCst != null) {
+      Type superclass = superclassCst.getClassType();
+      idx = orderItems0(superclass, idx, maxDepth);
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
-
-        int sz = classDefs.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
-
-        if (out.annotates()) {
-            out.annotate(4, "class_defs_size: " + Hex.u4(sz));
-            out.annotate(4, "class_defs_off:  " + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+    TypeList interfaces = c.getInterfaces();
+    int sz = interfaces.size();
+    for (int i = 0; i < sz; i++) {
+      idx = orderItems0(interfaces.getType(i), idx, maxDepth);
     }
 
-    /**
-     * Adds an element to this instance. It is illegal to attempt to add more
-     * than one class with the same name.
-     *
-     * @param clazz {@code non-null;} the class def to add
-     */
-    public void add(ClassDefItem clazz) {
-        Type type;
-
-        try {
-            type = clazz.getThisClass().getClassType();
-        } catch (NullPointerException ex) {
-            // Elucidate the exception.
-            throw new NullPointerException("clazz == null");
-        }
-
-        throwIfPrepared();
-
-        if (classDefs.get(type) != null) {
-            throw new IllegalArgumentException("already added: " + type);
-        }
-
-        classDefs.put(type, clazz);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        int sz = classDefs.size();
-        int idx = 0;
-
-        orderedDefs = new ArrayList<ClassDefItem>(sz);
-
-        /*
-         * Iterate over all the classes, recursively assigning an
-         * index to each, implicitly skipping the ones that have
-         * already been assigned by the time this (top-level)
-         * iteration reaches them.
-         */
-        for (Type type : classDefs.keySet()) {
-            idx = orderItems0(type, idx, sz - idx);
-        }
-    }
-
-    /**
-     * Helper for {@link #orderItems}, which recursively assigns indices
-     * to classes.
-     *
-     * @param type {@code null-ok;} type ref to assign, if any
-     * @param idx {@code >= 0;} the next index to assign
-     * @param maxDepth maximum recursion depth; if negative, this will
-     * throw an exception indicating class definition circularity
-     * @return {@code >= 0;} the next index to assign
-     */
-    private int orderItems0(Type type, int idx, int maxDepth) {
-        ClassDefItem c = classDefs.get(type);
-
-        if ((c == null) || (c.hasIndex())) {
-            return idx;
-        }
-
-        if (maxDepth < 0) {
-            throw new RuntimeException("class circularity with " + type);
-        }
-
-        maxDepth--;
-
-        CstType superclassCst = c.getSuperclass();
-        if (superclassCst != null) {
-            Type superclass = superclassCst.getClassType();
-            idx = orderItems0(superclass, idx, maxDepth);
-        }
-
-        TypeList interfaces = c.getInterfaces();
-        int sz = interfaces.size();
-        for (int i = 0; i < sz; i++) {
-            idx = orderItems0(interfaces.getType(i), idx, maxDepth);
-        }
-
-        c.setIndex(idx);
-        orderedDefs.add(c);
-        return idx + 1;
-    }
+    c.setIndex(idx);
+    orderedDefs.add(c);
+    return idx + 1;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/CodeItem.java b/dx/src/com/android/jack/dx/dex/file/CodeItem.java
index 15cb5a8..2dbaed9 100644
--- a/dx/src/com/android/jack/dx/dex/file/CodeItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/CodeItem.java
@@ -35,290 +35,288 @@
  */
 public final class CodeItem extends OffsettedItem implements Code {
 
-    /** {@code non-null;} method that this code implements */
-    private final CstMethodRef ref;
+  /** {@code non-null;} method that this code implements */
+  private final CstMethodRef ref;
 
-    /** {@code non-null;} the bytecode instructions and associated data */
-    private final DalvCode code;
+  /** {@code non-null;} the bytecode instructions and associated data */
+  private final DalvCode code;
 
-    /** {@code null-ok;} the catches, if needed; set in {@link #addContents} */
-    private CatchStructs catches;
+  /** {@code null-ok;} the catches, if needed; set in {@link #addContents} */
+  private CatchStructs catches;
 
-    /** whether this instance is for a {@code static} method */
-    private final boolean isStatic;
+  /** whether this instance is for a {@code static} method */
+  private final boolean isStatic;
 
-    /**
-     * {@code non-null;} list of possibly-thrown exceptions; just used in
-     * generating debugging output (listings)
+  /**
+   * {@code non-null;} list of possibly-thrown exceptions; just used in
+   * generating debugging output (listings)
+   */
+  private final TypeList throwsList;
+
+  /**
+   * {@code null-ok;} the debug info or {@code null} if there is none;
+   * set in {@link #addContents}
+   */
+  private DebugInfoItem debugInfo;
+
+  /**
+   * Constructs an instance.
+   *
+   * @param ref {@code non-null;} method that this code implements
+   * @param code {@code non-null;} the underlying code
+   * @param isStatic whether this instance is for a {@code static}
+   * method
+   * @param throwsList {@code non-null;} list of possibly-thrown exceptions,
+   * just used in generating debugging output (listings)
+   */
+  public CodeItem(CstMethodRef ref, DalvCode code, boolean isStatic, TypeList throwsList) {
+    super(ALIGNMENT, -1);
+
+    if (ref == null) {
+      throw new NullPointerException("ref == null");
+    }
+
+    if (code == null) {
+      throw new NullPointerException("code == null");
+    }
+
+    if (throwsList == null) {
+      throw new NullPointerException("throwsList == null");
+    }
+
+    this.ref = ref;
+    this.code = code;
+    this.isStatic = isStatic;
+    this.throwsList = throwsList;
+    this.catches = null;
+    this.debugInfo = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_CODE_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    MixedItemSection byteData = file.getByteData();
+    TypeIdsSection typeIds = file.getTypeIds();
+
+    if (code.hasPositions() || code.hasLocals()) {
+      debugInfo = new DebugInfoItem(code, isStatic, ref);
+      byteData.add(debugInfo);
+    }
+
+    if (code.hasAnyCatches()) {
+      for (Type type : code.getCatchTypes()) {
+        typeIds.intern(type);
+      }
+      catches = new CatchStructs(code);
+    }
+
+    for (Constant c : code.getInsnConstants()) {
+      file.internIfAppropriate(c);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "CodeItem{" + toHuman() + "}";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return ref.toHuman();
+  }
+
+  /**
+   * Gets the reference to the method this instance implements.
+   *
+   * @return {@code non-null;} the method reference
+   */
+  public CstMethodRef getRef() {
+    return ref;
+  }
+
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} per-line prefix to use
+   * @param verbose whether to be verbose with the output
+   */
+  @Override
+  public void debugPrint(PrintWriter out, String prefix, boolean verbose) {
+    out.println(ref.toHuman() + ":");
+
+    DalvInsnList insns = code.getInsns();
+    out.println("regs: " + Hex.u2(getRegistersSize()) + "; ins: " + Hex.u2(getInsSize())
+        + "; outs: " + Hex.u2(getOutsSize()));
+
+    insns.debugPrint(out, prefix, verbose);
+
+    String prefix2 = prefix + "  ";
+
+    if (catches != null) {
+      out.print(prefix);
+      out.println("catches");
+      catches.debugPrint(out, prefix2);
+    }
+
+    if (debugInfo != null) {
+      out.print(prefix);
+      out.println("debug info");
+      debugInfo.debugPrint(out, prefix2);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    final DexFile file = addedTo.getFile();
+    int catchesSize;
+
+    /*
+     * In order to get the catches and insns, all the code's
+     * constants need to be assigned indices.
      */
-    private final TypeList throwsList;
+    code.assignIndices(new DalvCode.AssignIndicesCallback() {
+      @Override
+      public int getIndex(Constant cst) {
+        IndexedItem item = file.findItemOrNull(cst);
+        if (item == null) {
+          return -1;
+        }
+        return item.getIndex();
+      }
+    });
 
-    /**
-     * {@code null-ok;} the debug info or {@code null} if there is none;
-     * set in {@link #addContents}
+    if (catches != null) {
+      catches.encode(file);
+      catchesSize = catches.writeSize();
+    } else {
+      catchesSize = 0;
+    }
+
+    /*
+     * The write size includes the header, two bytes per code
+     * unit, post-code padding if necessary, and however much
+     * space the catches need.
      */
-    private DebugInfoItem debugInfo;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ref {@code non-null;} method that this code implements
-     * @param code {@code non-null;} the underlying code
-     * @param isStatic whether this instance is for a {@code static}
-     * method
-     * @param throwsList {@code non-null;} list of possibly-thrown exceptions,
-     * just used in generating debugging output (listings)
-     */
-    public CodeItem(CstMethodRef ref, DalvCode code, boolean isStatic,
-            TypeList throwsList) {
-        super(ALIGNMENT, -1);
-
-        if (ref == null) {
-            throw new NullPointerException("ref == null");
-        }
-
-        if (code == null) {
-            throw new NullPointerException("code == null");
-        }
-
-        if (throwsList == null) {
-            throw new NullPointerException("throwsList == null");
-        }
-
-        this.ref = ref;
-        this.code = code;
-        this.isStatic = isStatic;
-        this.throwsList = throwsList;
-        this.catches = null;
-        this.debugInfo = null;
+int insnsSize = code.getInsns().codeSize();
+    if ((insnsSize & 1) != 0) {
+      insnsSize++;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_CODE_ITEM;
+    setWriteSize(HEADER_SIZE + (insnsSize * 2) + catchesSize);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    int regSz = getRegistersSize();
+    int outsSz = getOutsSize();
+    int insSz = getInsSize();
+    int insnsSz = code.getInsns().codeSize();
+    boolean needPadding = (insnsSz & 1) != 0;
+    int triesSz = (catches == null) ? 0 : catches.triesSize();
+    int debugOff = (debugInfo == null) ? 0 : debugInfo.getAbsoluteOffset();
+
+    if (annotates) {
+      out.annotate(0, offsetString() + ' ' + ref.toHuman());
+      out.annotate(2, "  registers_size: " + Hex.u2(regSz));
+      out.annotate(2, "  ins_size:       " + Hex.u2(insSz));
+      out.annotate(2, "  outs_size:      " + Hex.u2(outsSz));
+      out.annotate(2, "  tries_size:     " + Hex.u2(triesSz));
+      out.annotate(4, "  debug_off:      " + Hex.u4(debugOff));
+      out.annotate(4, "  insns_size:     " + Hex.u4(insnsSz));
+
+      // This isn't represented directly here, but it is useful to see.
+      int size = throwsList.size();
+      if (size != 0) {
+        out.annotate(0, "  throws " + StdTypeList.toHuman(throwsList));
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        MixedItemSection byteData = file.getByteData();
-        TypeIdsSection typeIds = file.getTypeIds();
+    out.writeShort(regSz);
+    out.writeShort(insSz);
+    out.writeShort(outsSz);
+    out.writeShort(triesSz);
+    out.writeInt(debugOff);
+    out.writeInt(insnsSz);
 
-        if (code.hasPositions() || code.hasLocals()) {
-            debugInfo = new DebugInfoItem(code, isStatic, ref);
-            byteData.add(debugInfo);
-        }
+    writeCodes(file, out);
 
-        if (code.hasAnyCatches()) {
-            for (Type type : code.getCatchTypes()) {
-                typeIds.intern(type);
-            }
-            catches = new CatchStructs(code);
-        }
-
-        for (Constant c : code.getInsnConstants()) {
-            file.internIfAppropriate(c);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return "CodeItem{" + toHuman() + "}";
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return ref.toHuman();
-    }
-
-    /**
-     * Gets the reference to the method this instance implements.
-     *
-     * @return {@code non-null;} the method reference
-     */
-    public CstMethodRef getRef() {
-        return ref;
-    }
-
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} per-line prefix to use
-     * @param verbose whether to be verbose with the output
-     */
-    @Override
-    public void debugPrint(PrintWriter out, String prefix, boolean verbose) {
-        out.println(ref.toHuman() + ":");
-
-        DalvInsnList insns = code.getInsns();
-        out.println("regs: " + Hex.u2(getRegistersSize()) +
-                "; ins: " + Hex.u2(getInsSize()) + "; outs: " +
-                Hex.u2(getOutsSize()));
-
-        insns.debugPrint(out, prefix, verbose);
-
-        String prefix2 = prefix + "  ";
-
-        if (catches != null) {
-            out.print(prefix);
-            out.println("catches");
-            catches.debugPrint(out, prefix2);
-        }
-
-        if (debugInfo != null) {
-            out.print(prefix);
-            out.println("debug info");
-            debugInfo.debugPrint(out, prefix2);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        final DexFile file = addedTo.getFile();
-        int catchesSize;
-
-        /*
-         * In order to get the catches and insns, all the code's
-         * constants need to be assigned indices.
-         */
-        code.assignIndices(new DalvCode.AssignIndicesCallback() {
-                @Override
-                public int getIndex(Constant cst) {
-                    IndexedItem item = file.findItemOrNull(cst);
-                    if (item == null) {
-                        return -1;
-                    }
-                    return item.getIndex();
-                }
-            });
-
-        if (catches != null) {
-            catches.encode(file);
-            catchesSize = catches.writeSize();
-        } else {
-            catchesSize = 0;
-        }
-
-        /*
-         * The write size includes the header, two bytes per code
-         * unit, post-code padding if necessary, and however much
-         * space the catches need.
-         */
-
-        int insnsSize = code.getInsns().codeSize();
-        if ((insnsSize & 1) != 0) {
-            insnsSize++;
-        }
-
-        setWriteSize(HEADER_SIZE + (insnsSize * 2) + catchesSize);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        int regSz = getRegistersSize();
-        int outsSz = getOutsSize();
-        int insSz = getInsSize();
-        int insnsSz = code.getInsns().codeSize();
-        boolean needPadding = (insnsSz & 1) != 0;
-        int triesSz = (catches == null) ? 0 : catches.triesSize();
-        int debugOff = (debugInfo == null) ? 0 : debugInfo.getAbsoluteOffset();
-
+    if (catches != null) {
+      if (needPadding) {
         if (annotates) {
-            out.annotate(0, offsetString() + ' ' + ref.toHuman());
-            out.annotate(2, "  registers_size: " + Hex.u2(regSz));
-            out.annotate(2, "  ins_size:       " + Hex.u2(insSz));
-            out.annotate(2, "  outs_size:      " + Hex.u2(outsSz));
-            out.annotate(2, "  tries_size:     " + Hex.u2(triesSz));
-            out.annotate(4, "  debug_off:      " + Hex.u4(debugOff));
-            out.annotate(4, "  insns_size:     " + Hex.u4(insnsSz));
-
-            // This isn't represented directly here, but it is useful to see.
-            int size = throwsList.size();
-            if (size != 0) {
-                out.annotate(0, "  throws " + StdTypeList.toHuman(throwsList));
-            }
+          out.annotate(2, "  padding: 0");
         }
+        out.writeShort(0);
+      }
 
-        out.writeShort(regSz);
-        out.writeShort(insSz);
-        out.writeShort(outsSz);
-        out.writeShort(triesSz);
-        out.writeInt(debugOff);
-        out.writeInt(insnsSz);
-
-        writeCodes(file, out);
-
-        if (catches != null) {
-            if (needPadding) {
-                if (annotates) {
-                    out.annotate(2, "  padding: 0");
-                }
-                out.writeShort(0);
-            }
-
-            catches.writeTo(file, out);
-        }
-
-        if (annotates) {
-            /*
-             * These are pointed at in the code header (above), but it's less
-             * distracting to expand on them at the bottom of the code.
-             */
-            if (debugInfo != null) {
-                out.annotate(0, "  debug info");
-                debugInfo.annotateTo(file, out, "    ");
-            }
-        }
+      catches.writeTo(file, out);
     }
 
-    /**
-     * Helper for {@link #writeTo0} which writes out the actual bytecode.
-     *
-     * @param file {@code non-null;} file we are part of
-     * @param out {@code non-null;} where to write to
-     */
-    private void writeCodes(DexFile file, AnnotatedOutput out) {
-        DalvInsnList insns = code.getInsns();
-
-        try {
-            insns.writeTo(out);
-        } catch (RuntimeException ex) {
-            throw ExceptionWithContext.withContext(ex, "...while writing " +
-                    "instructions for " + ref.toHuman());
-        }
+    if (annotates) {
+      /*
+       * These are pointed at in the code header (above), but it's less
+       * distracting to expand on them at the bottom of the code.
+       */
+      if (debugInfo != null) {
+        out.annotate(0, "  debug info");
+        debugInfo.annotateTo(file, out, "    ");
+      }
     }
+  }
 
-    /**
-     * Get the in registers count.
-     *
-     * @return the count
-     */
-    private int getInsSize() {
-        return ref.getParameterWordCount(isStatic);
-    }
+  /**
+   * Helper for {@link #writeTo0} which writes out the actual bytecode.
+   *
+   * @param file {@code non-null;} file we are part of
+   * @param out {@code non-null;} where to write to
+   */
+  private void writeCodes(DexFile file, AnnotatedOutput out) {
+    DalvInsnList insns = code.getInsns();
 
-    /**
-     * Get the out registers count.
-     *
-     * @return the count
-     */
-    private int getOutsSize() {
-        return code.getInsns().getOutsSize();
+    try {
+      insns.writeTo(out);
+    } catch (RuntimeException ex) {
+      throw ExceptionWithContext.withContext(ex,
+          "...while writing " + "instructions for " + ref.toHuman());
     }
+  }
 
-    /**
-     * Get the total registers count.
-     *
-     * @return the count
-     */
-    private int getRegistersSize() {
-        return code.getInsns().getRegistersSize();
-    }
+  /**
+   * Get the in registers count.
+   *
+   * @return the count
+   */
+  private int getInsSize() {
+    return ref.getParameterWordCount(isStatic);
+  }
+
+  /**
+   * Get the out registers count.
+   *
+   * @return the count
+   */
+  private int getOutsSize() {
+    return code.getInsns().getOutsSize();
+  }
+
+  /**
+   * Get the total registers count.
+   *
+   * @return the count
+   */
+  private int getRegistersSize() {
+    return code.getInsns().getRegistersSize();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/DebugInfoConstants.java b/dx/src/com/android/jack/dx/dex/file/DebugInfoConstants.java
index 63d8a34..1e2d520 100644
--- a/dx/src/com/android/jack/dx/dex/file/DebugInfoConstants.java
+++ b/dx/src/com/android/jack/dx/dex/file/DebugInfoConstants.java
@@ -21,134 +21,134 @@
  */
 public interface DebugInfoConstants {
 
-    /*
-     * normal opcodes
-     */
+  /*
+   * normal opcodes
+   */
 
-    /**
-     * Terminates a debug info sequence for a method.<p>
-     * Args: none
-     *
-     */
-    static final int DBG_END_SEQUENCE = 0x00;
+  /**
+   * Terminates a debug info sequence for a method.<p>
+   * Args: none
+   *
+   */
+  static final int DBG_END_SEQUENCE = 0x00;
 
-    /**
-     * Advances the program counter/address register without emitting
-     * a positions entry.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; amount to advance pc by
-     * </ol>
-     */
-    static final int DBG_ADVANCE_PC = 0x01;
+  /**
+   * Advances the program counter/address register without emitting
+   * a positions entry.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; amount to advance pc by
+   * </ol>
+   */
+  static final int DBG_ADVANCE_PC = 0x01;
 
-    /**
-     * Advances the line register without emitting
-     * a positions entry.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Signed LEB128 &mdash; amount to change line register by.
-     * </ol>
-     */
-    static final int DBG_ADVANCE_LINE = 0x02;
+  /**
+   * Advances the line register without emitting
+   * a positions entry.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Signed LEB128 &mdash; amount to change line register by.
+   * </ol>
+   */
+  static final int DBG_ADVANCE_LINE = 0x02;
 
-    /**
-     * Introduces a local variable at the current address.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; register that will contain local.
-     * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of local name.
-     * <li>Unsigned LEB128 &mdash; type index (shifted by 1) of type.
-     * </ol>
-     */
-    static final int DBG_START_LOCAL = 0x03;
+  /**
+   * Introduces a local variable at the current address.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; register that will contain local.
+   * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of local name.
+   * <li>Unsigned LEB128 &mdash; type index (shifted by 1) of type.
+   * </ol>
+   */
+  static final int DBG_START_LOCAL = 0x03;
 
-    /**
-     * Introduces a local variable at the current address with a type
-     * signature specified.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; register that will contain local.
-     * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of local name.
-     * <li>Unsigned LEB128 &mdash; type index (shifted by 1) of type.
-     * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of
-     * type signature.
-     * </ol>
-     */
-    static final int DBG_START_LOCAL_EXTENDED = 0x04;
+  /**
+   * Introduces a local variable at the current address with a type
+   * signature specified.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; register that will contain local.
+   * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of local name.
+   * <li>Unsigned LEB128 &mdash; type index (shifted by 1) of type.
+   * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of
+   * type signature.
+   * </ol>
+   */
+  static final int DBG_START_LOCAL_EXTENDED = 0x04;
 
-    /**
-     * Marks a currently-live local variable as out of scope at the
-     * current address.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; register that contained local
-     * </ol>
-     */
-    static final int DBG_END_LOCAL = 0x05;
+  /**
+   * Marks a currently-live local variable as out of scope at the
+   * current address.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; register that contained local
+   * </ol>
+   */
+  static final int DBG_END_LOCAL = 0x05;
 
-    /**
-     * Re-introduces a local variable at the current address. The name
-     * and type are the same as the last local that was live in the specified
-     * register.<p>
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; register to re-start.
-     * </ol>
-     */
-    static final int DBG_RESTART_LOCAL = 0x06;
+  /**
+   * Re-introduces a local variable at the current address. The name
+   * and type are the same as the last local that was live in the specified
+   * register.<p>
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; register to re-start.
+   * </ol>
+   */
+  static final int DBG_RESTART_LOCAL = 0x06;
 
 
-    /**
-     * Sets the "prologue_end" state machine register, indicating that the
-     * next position entry that is added should be considered the end of
-     * a method prologue (an appropriate place for a method breakpoint).<p>
-     *
-     * The prologue_end register is cleared by any special
-     * ({@code >= OPCODE_BASE}) opcode.
-     */
-    static final int DBG_SET_PROLOGUE_END = 0x07;
+  /**
+   * Sets the "prologue_end" state machine register, indicating that the
+   * next position entry that is added should be considered the end of
+   * a method prologue (an appropriate place for a method breakpoint).<p>
+   *
+   * The prologue_end register is cleared by any special
+   * ({@code >= OPCODE_BASE}) opcode.
+   */
+  static final int DBG_SET_PROLOGUE_END = 0x07;
 
-    /**
-     * Sets the "epilogue_begin" state machine register, indicating that the
-     * next position entry that is added should be considered the beginning of
-     * a method epilogue (an appropriate place to suspend execution before
-     * method exit).<p>
-     *
-     * The epilogue_begin register is cleared by any special
-     * ({@code >= OPCODE_BASE}) opcode.
-     */
-    static final int DBG_SET_EPILOGUE_BEGIN = 0x08;
+  /**
+   * Sets the "epilogue_begin" state machine register, indicating that the
+   * next position entry that is added should be considered the beginning of
+   * a method epilogue (an appropriate place to suspend execution before
+   * method exit).<p>
+   *
+   * The epilogue_begin register is cleared by any special
+   * ({@code >= OPCODE_BASE}) opcode.
+   */
+  static final int DBG_SET_EPILOGUE_BEGIN = 0x08;
 
-    /**
-     * Sets the current file that that line numbers refer to. All subsequent
-     * line number entries make reference to this source file name, instead
-     * of the default name specified in code_item.
-     *
-     * Args:
-     * <ol>
-     * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of source
-     * file name.
-     * </ol>
-     */
-    static final int DBG_SET_FILE = 0x09;
+  /**
+   * Sets the current file that that line numbers refer to. All subsequent
+   * line number entries make reference to this source file name, instead
+   * of the default name specified in code_item.
+   *
+   * Args:
+   * <ol>
+   * <li>Unsigned LEB128 &mdash; string index (shifted by 1) of source
+   * file name.
+   * </ol>
+   */
+  static final int DBG_SET_FILE = 0x09;
 
-    /* IF YOU ADD A NEW OPCODE, increase OPCODE_BASE */
+  /* IF YOU ADD A NEW OPCODE, increase OPCODE_BASE */
 
-    /*
-     * "special opcode" configuration, essentially what's found in
-     * the line number program header in DWARFv3, Section 6.2.4
-     */
+  /*
+   * "special opcode" configuration, essentially what's found in
+   * the line number program header in DWARFv3, Section 6.2.4
+   */
 
-    /** the smallest value a special opcode can take */
-    static final int DBG_FIRST_SPECIAL = 0x0a;
-    static final int DBG_LINE_BASE = -4;
-    static final int DBG_LINE_RANGE = 15;
-    // MIN_INSN_LENGTH is always 1
+  /** the smallest value a special opcode can take */
+  static final int DBG_FIRST_SPECIAL = 0x0a;
+  static final int DBG_LINE_BASE = -4;
+  static final int DBG_LINE_RANGE = 15;
+  // MIN_INSN_LENGTH is always 1
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/DebugInfoDecoder.java b/dx/src/com/android/jack/dx/dex/file/DebugInfoDecoder.java
index 98ebc08..acd7939 100644
--- a/dx/src/com/android/jack/dx/dex/file/DebugInfoDecoder.java
+++ b/dx/src/com/android/jack/dx/dex/file/DebugInfoDecoder.java
@@ -16,6 +16,20 @@
 
 package com.android.jack.dx.dex.file;
 
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_ADVANCE_LINE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_ADVANCE_PC;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_END_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_END_SEQUENCE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_FIRST_SPECIAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_LINE_BASE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_LINE_RANGE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_RESTART_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_SET_EPILOGUE_BEGIN;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_SET_FILE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_SET_PROLOGUE_END;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL_EXTENDED;
+
 import com.android.jack.dx.dex.code.DalvCode;
 import com.android.jack.dx.dex.code.DalvInsnList;
 import com.android.jack.dx.dex.code.LocalList;
@@ -35,563 +49,560 @@
 import java.util.ArrayList;
 import java.util.List;
 
-import static com.android.jack.dx.dex.file.DebugInfoConstants.*;
-
 /**
  * A decoder for the dex debug info state machine format.
  * This code exists mostly as a reference implementation and test for
  * for the {@code DebugInfoEncoder}
  */
 public class DebugInfoDecoder {
-    /** encoded debug info */
-    private final ByteInput encoded;
+  /** encoded debug info */
+  private final ByteInput encoded;
 
-    /** positions decoded */
-    private final ArrayList<PositionEntry> positions;
+  /** positions decoded */
+  private final ArrayList<PositionEntry> positions;
 
-    /** locals decoded */
-    private final ArrayList<LocalEntry> locals;
+  /** locals decoded */
+  private final ArrayList<LocalEntry> locals;
 
-    /** indexed by register, the last local variable live in a reg */
-    private final LocalEntry[] lastEntryForReg;
+  /** indexed by register, the last local variable live in a reg */
+  private final LocalEntry[] lastEntryForReg;
 
-    /** method descriptor of method this debug info is for */
-    private final Prototype desc;
+  /** method descriptor of method this debug info is for */
+  private final Prototype desc;
 
-    /** true if method is static */
-    private final boolean isStatic;
+  /** true if method is static */
+  private final boolean isStatic;
 
-    /**
-     * register size, in register units, of the register space
-     * used by this method
-     */
-    private final int regSize;
+  /**
+   * register size, in register units, of the register space
+   * used by this method
+   */
+  private final int regSize;
 
-    /** current decoding state: line number */
-    private int line = 1;
+  /** current decoding state: line number */
+  private int line = 1;
 
-    /** current decoding state: bytecode address */
-    private int address = 0;
+  /** current decoding state: bytecode address */
+  private int address = 0;
 
-    /** string index of the string "this" */
-    private final int thisStringIdx;
+  /** string index of the string "this" */
+  private final int thisStringIdx;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param encoded encoded debug info
-     * @param regSize register size, in register units, of the register space
-     * used by this method
-     * @param isStatic true if method is static
-     * @param ref method descriptor of method this debug info is for
-     * @param file dex file this debug info will be stored in
-     */
-    DebugInfoDecoder(byte[] encoded, int regSize,
-            boolean isStatic, CstMethodRef ref, DexFile file) {
-      this(new ByteArrayByteInput(encoded), regSize, isStatic, ref.getPrototype(),
-              extractThisIdx(file));
+  /**
+   * Constructs an instance.
+   *
+   * @param encoded encoded debug info
+   * @param regSize register size, in register units, of the register space
+   * used by this method
+   * @param isStatic true if method is static
+   * @param ref method descriptor of method this debug info is for
+   * @param file dex file this debug info will be stored in
+   */
+  DebugInfoDecoder(byte[] encoded, int regSize, boolean isStatic, CstMethodRef ref, DexFile file) {
+    this(new ByteArrayByteInput(encoded), regSize, isStatic, ref.getPrototype(), extractThisIdx(
+        file));
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param encoded encoded debug info
+   * @param regSize register size, in register units, of the register space
+   * used by this method
+   * @param isStatic true if method is static
+   * @param desc method descriptor of method this debug info is for
+   * @param thisIdx string index of the string "this" or -1 if the string does not exists in the
+   * dex.
+   */
+  public DebugInfoDecoder(ByteInput encoded, int regSize, boolean isStatic, Prototype desc,
+      int thisIdx) {
+    if (encoded == null) {
+      throw new NullPointerException("encoded == null");
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param encoded encoded debug info
-     * @param regSize register size, in register units, of the register space
-     * used by this method
-     * @param isStatic true if method is static
-     * @param desc method descriptor of method this debug info is for
-     * @param thisIdx string index of the string "this" or -1 if the string does not exists in the
-     * dex.
-     */
-    public DebugInfoDecoder(ByteInput encoded, int regSize,
-          boolean isStatic, Prototype desc, int thisIdx) {
-        if (encoded == null) {
-            throw new NullPointerException("encoded == null");
-        }
+    this.encoded = encoded;
+    this.isStatic = isStatic;
+    this.desc = desc;
+    this.regSize = regSize;
 
-        this.encoded = encoded;
-        this.isStatic = isStatic;
-        this.desc = desc;
-        this.regSize = regSize;
+    positions = new ArrayList<PositionEntry>();
+    locals = new ArrayList<LocalEntry>();
+    lastEntryForReg = new LocalEntry[regSize];
 
-        positions = new ArrayList<PositionEntry>();
-        locals = new ArrayList<LocalEntry>();
-        lastEntryForReg = new LocalEntry[regSize];
+    thisStringIdx = thisIdx;
+  }
 
-        thisStringIdx = thisIdx;
+  /**
+   * An entry in the resulting postions table
+   */
+  public static class PositionEntry {
+    /** bytecode address */
+    public int address;
+
+    /** line number */
+    public int line;
+
+    public PositionEntry(int address, int line) {
+      this.address = address;
+      this.line = line;
+    }
+  }
+
+  /**
+   * An entry in the resulting locals table
+   */
+  public static class LocalEntry {
+    /** address of event */
+    public int address;
+
+    /** {@code true} iff it's a local start */
+    public boolean isStart;
+
+    /** register number */
+    public int reg;
+
+    /** index of name in strings table */
+    public int nameIndex;
+
+    /** index of type in types table */
+    public int typeIndex;
+
+    /** index of type signature in strings table */
+    public int signatureIndex;
+
+    public LocalEntry(int address,
+        boolean isStart,
+        int reg,
+        int nameIndex,
+        int typeIndex,
+        int signatureIndex) {
+      this.address = address;
+      this.isStart = isStart;
+      this.reg = reg;
+      this.nameIndex = nameIndex;
+      this.typeIndex = typeIndex;
+      this.signatureIndex = signatureIndex;
     }
 
-    /**
-     * An entry in the resulting postions table
-     */
-    static public class PositionEntry {
-        /** bytecode address */
-        public int address;
+    @Override
+    public String toString() {
+      return String.format("[%x %s v%d %04x %04x %04x]",
+          address,
+          isStart ? "start" : "end",
+          reg,
+          nameIndex,
+          typeIndex,
+          signatureIndex);
+    }
+  }
 
-        /** line number */
-        public int line;
+  /**
+   * Gets the decoded positions list.
+   * Valid after calling {@code decode}.
+   *
+   * @return positions list in ascending address order.
+   */
+  public List<PositionEntry> getPositionList() {
+    return positions;
+  }
 
-        public PositionEntry(int address, int line) {
-            this.address = address;
-            this.line = line;
-        }
+  /**
+   * Gets the decoded locals list, in ascending start-address order.
+   * Valid after calling {@code decode}.
+   *
+   * @return locals list in ascending address order.
+   */
+  public List<LocalEntry> getLocals() {
+    return locals;
+  }
+
+  /**
+   * Decodes the debug info sequence.
+   */
+  public void decode() {
+    try {
+      decode0();
+    } catch (Exception ex) {
+      throw ExceptionWithContext.withContext(ex, "...while decoding debug info");
+    }
+  }
+
+  /**
+   * Reads a string index. String indicies are offset by 1, and a 0 value
+   * in the stream (-1 as returned by this method) means "null"
+   *
+   * @return index into file's string ids table, -1 means null
+   * @throws IOException
+   */
+  private int readStringIndex(ByteInput bs) throws IOException {
+    int offsetIndex = Leb128Utils.readUnsignedLeb128(bs);
+
+    return offsetIndex - 1;
+  }
+
+  /**
+   * Gets the register that begins the method's parameter range (including
+   * the 'this' parameter for non-static methods). The range continues until
+   * {@code regSize}
+   *
+   * @return register as noted above.
+   */
+  private int getParamBase() {
+    return regSize - desc.getParameterTypes().getWordCount() - (isStatic ? 0 : 1);
+  }
+
+  private void decode0() throws IOException {
+    line = Leb128Utils.readUnsignedLeb128(encoded);
+    int szParams = Leb128Utils.readUnsignedLeb128(encoded);
+    StdTypeList params = desc.getParameterTypes();
+    int curReg = getParamBase();
+
+    if (szParams != params.size()) {
+      throw new RuntimeException("Mismatch between parameters_size and prototype");
     }
 
-    /**
-     * An entry in the resulting locals table
-     */
-    static public class LocalEntry {
-        /** address of event */
-        public int address;
-
-        /** {@code true} iff it's a local start */
-        public boolean isStart;
-
-        /** register number */
-        public int reg;
-
-        /** index of name in strings table */
-        public int nameIndex;
-
-        /** index of type in types table */
-        public int typeIndex;
-
-        /** index of type signature in strings table */
-        public int signatureIndex;
-
-        public LocalEntry(int address, boolean isStart, int reg, int nameIndex,
-                int typeIndex, int signatureIndex) {
-            this.address        = address;
-            this.isStart        = isStart;
-            this.reg            = reg;
-            this.nameIndex      = nameIndex;
-            this.typeIndex      = typeIndex;
-            this.signatureIndex = signatureIndex;
-        }
-
-        public String toString() {
-            return String.format("[%x %s v%d %04x %04x %04x]",
-                    address, isStart ? "start" : "end", reg,
-                    nameIndex, typeIndex, signatureIndex);
-        }
+    if (!isStatic) {
+      // Start off with implicit 'this' entry
+      LocalEntry thisEntry =
+          new LocalEntry(0, true, curReg, thisStringIdx, ClassDef.NO_INDEX, ClassDef.NO_INDEX);
+      locals.add(thisEntry);
+      lastEntryForReg[curReg] = thisEntry;
+      curReg++;
     }
 
-    /**
-     * Gets the decoded positions list.
-     * Valid after calling {@code decode}.
-     *
-     * @return positions list in ascending address order.
-     */
-    public List<PositionEntry> getPositionList() {
-        return positions;
-    }
+    for (int i = 0; i < szParams; i++) {
+      Type paramType = params.getType(i);
+      LocalEntry le;
 
-    /**
-     * Gets the decoded locals list, in ascending start-address order.
-     * Valid after calling {@code decode}.
-     *
-     * @return locals list in ascending address order.
-     */
-    public List<LocalEntry> getLocals() {
-        return locals;
-    }
+      int nameIdx = readStringIndex(encoded);
 
-    /**
-     * Decodes the debug info sequence.
-     */
-    public void decode() {
-        try {
-            decode0();
-        } catch (Exception ex) {
-            throw ExceptionWithContext.withContext(ex,
-                    "...while decoding debug info");
-        }
-    }
-
-    /**
-     * Reads a string index. String indicies are offset by 1, and a 0 value
-     * in the stream (-1 as returned by this method) means "null"
-     *
-     * @return index into file's string ids table, -1 means null
-     * @throws IOException
-     */
-    private int readStringIndex(ByteInput bs) throws IOException {
-        int offsetIndex = Leb128Utils.readUnsignedLeb128(bs);
-
-        return offsetIndex - 1;
-    }
-
-    /**
-     * Gets the register that begins the method's parameter range (including
-     * the 'this' parameter for non-static methods). The range continues until
-     * {@code regSize}
-     *
-     * @return register as noted above.
-     */
-    private int getParamBase() {
-        return regSize
-                - desc.getParameterTypes().getWordCount() - (isStatic? 0 : 1);
-    }
-
-    private void decode0() throws IOException {
-        line = Leb128Utils.readUnsignedLeb128(encoded);
-        int szParams = Leb128Utils.readUnsignedLeb128(encoded);
-        StdTypeList params = desc.getParameterTypes();
-        int curReg = getParamBase();
-
-        if (szParams != params.size()) {
-            throw new RuntimeException(
-                    "Mismatch between parameters_size and prototype");
-        }
-
-        if (!isStatic) {
-            // Start off with implicit 'this' entry
-            LocalEntry thisEntry =
-                new LocalEntry(0, true, curReg, thisStringIdx, ClassDef.NO_INDEX,
-                    ClassDef.NO_INDEX);
-            locals.add(thisEntry);
-            lastEntryForReg[curReg] = thisEntry;
-            curReg++;
-        }
-
-        for (int i = 0; i < szParams; i++) {
-            Type paramType = params.getType(i);
-            LocalEntry le;
-
-            int nameIdx = readStringIndex(encoded);
-
-            if (nameIdx == -1) {
-                /*
-                 * Unnamed parameter; often but not always filled in by an
-                 * extended start op after the prologue
-                 */
-                le = new LocalEntry(0, true, curReg, ClassDef.NO_INDEX, ClassDef.NO_INDEX,
-                    ClassDef.NO_INDEX);
-            } else {
-                // TODO: Final 0 should be idx of paramType.getDescriptor().
-                le = new LocalEntry(0, true, curReg, nameIdx, ClassDef.NO_INDEX, ClassDef.NO_INDEX);
-            }
-
-            locals.add(le);
-            lastEntryForReg[curReg] = le;
-            curReg += paramType.getCategory();
-        }
-
-        for (;;) {
-            int opcode = encoded.readByte() & 0xff;
-
-            switch (opcode) {
-                case DBG_START_LOCAL: {
-                    int reg = Leb128Utils.readUnsignedLeb128(encoded);
-                    int nameIdx = readStringIndex(encoded);
-                    int typeIdx = readStringIndex(encoded);
-                    LocalEntry le = new LocalEntry(
-                            address, true, reg, nameIdx, typeIdx, ClassDef.NO_INDEX);
-
-                    locals.add(le);
-                    lastEntryForReg[reg] = le;
-                }
-                break;
-
-                case DBG_START_LOCAL_EXTENDED: {
-                    int reg = Leb128Utils.readUnsignedLeb128(encoded);
-                    int nameIdx = readStringIndex(encoded);
-                    int typeIdx = readStringIndex(encoded);
-                    int sigIdx = readStringIndex(encoded);
-                    LocalEntry le = new LocalEntry(
-                            address, true, reg, nameIdx, typeIdx, sigIdx);
-
-                    locals.add(le);
-                    lastEntryForReg[reg] = le;
-                }
-                break;
-
-                case DBG_RESTART_LOCAL: {
-                    int reg = Leb128Utils.readUnsignedLeb128(encoded);
-                    LocalEntry prevle;
-                    LocalEntry le;
-
-                    try {
-                        prevle = lastEntryForReg[reg];
-
-                        if (prevle.isStart) {
-                            throw new RuntimeException("nonsensical "
-                                    + "RESTART_LOCAL on live register v"
-                                    + reg);
-                        }
-
-                        le = new LocalEntry(address, true, reg,
-                                prevle.nameIndex, prevle.typeIndex, prevle.signatureIndex);
-                    } catch (NullPointerException ex) {
-                        throw new RuntimeException(
-                                "Encountered RESTART_LOCAL on new v" + reg);
-                    }
-
-                    locals.add(le);
-                    lastEntryForReg[reg] = le;
-                }
-                break;
-
-                case DBG_END_LOCAL: {
-                    int reg = Leb128Utils.readUnsignedLeb128(encoded);
-                    LocalEntry prevle;
-                    LocalEntry le;
-
-                    try {
-                        prevle = lastEntryForReg[reg];
-
-                        if (!prevle.isStart) {
-                            throw new RuntimeException("nonsensical "
-                                    + "END_LOCAL on dead register v" + reg);
-                        }
-
-                        le = new LocalEntry(address, false, reg,
-                                prevle.nameIndex, prevle.typeIndex,
-                                prevle.signatureIndex);
-                    } catch (NullPointerException ex) {
-                        throw new RuntimeException(
-                                "Encountered END_LOCAL on new v" + reg);
-                    }
-
-                    locals.add(le);
-                    lastEntryForReg[reg] = le;
-                }
-                break;
-
-                case DBG_END_SEQUENCE:
-                    // all done
-                return;
-
-                case DBG_ADVANCE_PC:
-                    address += Leb128Utils.readUnsignedLeb128(encoded);
-                break;
-
-                case DBG_ADVANCE_LINE:
-                    line += Leb128Utils.readSignedLeb128(encoded);
-                break;
-
-                case DBG_SET_PROLOGUE_END:
-                    //TODO do something with this.
-                break;
-
-                case DBG_SET_EPILOGUE_BEGIN:
-                    //TODO do something with this.
-                break;
-
-                case DBG_SET_FILE:
-                    //TODO do something with this.
-                break;
-
-                default:
-                    if (opcode < DBG_FIRST_SPECIAL) {
-                        throw new RuntimeException(
-                                "Invalid extended opcode encountered "
-                                        + opcode);
-                    }
-
-                    int adjopcode = opcode - DBG_FIRST_SPECIAL;
-
-                    address += adjopcode / DBG_LINE_RANGE;
-                    line += DBG_LINE_BASE + (adjopcode % DBG_LINE_RANGE);
-
-                    positions.add(new PositionEntry(address, line));
-                break;
-
-            }
-        }
-    }
-
-    /**
-     * Validates an encoded debug info stream against data used to encode it,
-     * throwing an exception if they do not match. Used to validate the
-     * encoder.
-     *
-     * @param info encoded debug info
-     * @param file {@code non-null;} file to refer to during decoding
-     * @param ref {@code non-null;} method whose info is being decoded
-     * @param code {@code non-null;} original code object that was encoded
-     * @param isStatic whether the method is static
-     */
-    public static void validateEncode(byte[] info, DexFile file,
-            CstMethodRef ref, DalvCode code, boolean isStatic) {
-        PositionList pl = code.getPositions();
-        LocalList ll = code.getLocals();
-        DalvInsnList insns = code.getInsns();
-        int countRegisters = insns.getRegistersSize();
-
-        try {
-            validateEncode0(info, countRegisters,
-                    isStatic, ref, file, pl, ll);
-        } catch (RuntimeException ex) {
-            System.err.println("instructions:");
-            insns.debugPrint(System.err, "  ", true);
-            System.err.println("local list:");
-            ll.debugPrint(System.err, "  ");
-            throw ExceptionWithContext.withContext(ex,
-                    "while processing " + ref.toHuman());
-        }
-    }
-
-    private static void validateEncode0(byte[] info,
-            int countRegisters, boolean isStatic, CstMethodRef ref,
-            DexFile file, PositionList pl, LocalList ll) {
-        DebugInfoDecoder decoder
-                = new DebugInfoDecoder(info, countRegisters,
-                    isStatic, ref, file);
-
-        decoder.decode();
-
+      if (nameIdx == -1) {
         /*
-         * Go through the decoded position entries, matching up
-         * with original entries.
+         * Unnamed parameter; often but not always filled in by an
+         * extended start op after the prologue
          */
+        le = new LocalEntry(0,
+            true,
+            curReg,
+            ClassDef.NO_INDEX,
+            ClassDef.NO_INDEX,
+            ClassDef.NO_INDEX);
+      } else {
+        // TODO(dx team): Final 0 should be idx of paramType.getDescriptor().
+        le = new LocalEntry(0, true, curReg, nameIdx, ClassDef.NO_INDEX, ClassDef.NO_INDEX);
+      }
 
-        List<PositionEntry> decodedEntries = decoder.getPositionList();
-
-        if (decodedEntries.size() != pl.size()) {
-            throw new RuntimeException(
-                    "Decoded positions table not same size was "
-                    + decodedEntries.size() + " expected " + pl.size());
-        }
-
-        for (PositionEntry entry : decodedEntries) {
-            boolean found = false;
-            for (int i = pl.size() - 1; i >= 0; i--) {
-                PositionList.Entry ple = pl.get(i);
-
-                if (entry.line == ple.getPosition().getLine()
-                        && entry.address == ple.getAddress()) {
-                    found = true;
-                    break;
-                }
-            }
-
-            if (!found) {
-                throw new RuntimeException ("Could not match position entry: "
-                        + entry.address + ", " + entry.line);
-            }
-        }
-
-        /*
-         * Go through the original local list, in order, matching up
-         * with decoded entries.
-         */
-
-        List<LocalEntry> decodedLocals = decoder.getLocals();
-        int thisStringIdx = decoder.thisStringIdx;
-        int decodedSz = decodedLocals.size();
-        int paramBase = decoder.getParamBase();
-
-        /*
-         * Preflight to fill in any parameters that were skipped in
-         * the prologue (including an implied "this") but then
-         * identified by full signature.
-         */
-        for (int i = 0; i < decodedSz; i++) {
-            LocalEntry entry = decodedLocals.get(i);
-            int idx = entry.nameIndex;
-
-            if ((idx < 0) || (idx == thisStringIdx)) {
-                for (int j = i + 1; j < decodedSz; j++) {
-                    LocalEntry e2 = decodedLocals.get(j);
-                    if (e2.address != 0) {
-                        break;
-                    }
-                    if ((entry.reg == e2.reg) && e2.isStart) {
-                        decodedLocals.set(i, e2);
-                        decodedLocals.remove(j);
-                        decodedSz--;
-                        break;
-                    }
-                }
-            }
-        }
-
-        int origSz = ll.size();
-        int decodeAt = 0;
-        boolean problem = false;
-
-        for (int i = 0; i < origSz; i++) {
-            LocalList.Entry origEntry = ll.get(i);
-
-            if (origEntry.getDisposition()
-                    == LocalList.Disposition.END_REPLACED) {
-                /*
-                 * The encoded list doesn't represent replacements, so
-                 * ignore them for the sake of comparison.
-                 */
-                continue;
-            }
-
-            LocalEntry decodedEntry;
-
-            do {
-                decodedEntry = decodedLocals.get(decodeAt);
-                if (decodedEntry.nameIndex >= 0) {
-                    break;
-                }
-                /*
-                 * A negative name index means this is an anonymous
-                 * parameter, and we shouldn't expect to see it in the
-                 * original list. So, skip it.
-                 */
-                decodeAt++;
-            } while (decodeAt < decodedSz);
-
-            int decodedAddress = decodedEntry.address;
-
-            if (decodedEntry.reg != origEntry.getRegister()) {
-                System.err.println("local register mismatch at orig " + i +
-                        " / decoded " + decodeAt);
-                problem = true;
-                break;
-            }
-
-            if (decodedEntry.isStart != origEntry.isStart()) {
-                System.err.println("local start/end mismatch at orig " + i +
-                        " / decoded " + decodeAt);
-                problem = true;
-                break;
-            }
-
-            /*
-             * The secondary check here accounts for the fact that a
-             * parameter might not be marked as starting at 0 in the
-             * original list.
-             */
-            if ((decodedAddress != origEntry.getAddress())
-                    && !((decodedAddress == 0)
-                            && (decodedEntry.reg >= paramBase))) {
-                System.err.println("local address mismatch at orig " + i +
-                        " / decoded " + decodeAt);
-                problem = true;
-                break;
-            }
-
-            decodeAt++;
-        }
-
-        if (problem) {
-            System.err.println("decoded locals:");
-            for (LocalEntry e : decodedLocals) {
-                System.err.println("  " + e);
-            }
-            throw new RuntimeException("local table problem");
-        }
+      locals.add(le);
+      lastEntryForReg[curReg] = le;
+      curReg += paramType.getCategory();
     }
 
-    private static int extractThisIdx(DexFile file) {
-        int idx = -1;
+    for (;;) {
+      int opcode = encoded.readByte() & 0xff;
 
-        try {
-            idx = file.getStringIds().indexOf(new CstString("this"));
-        } catch (IllegalArgumentException ex) {
-            /*
-             * Silently tolerate not finding "this". It just means that
-             * no method has local variable info that looks like
-             * a standard instance method.
-             */
+      switch (opcode) {
+        case DBG_START_LOCAL: {
+          int reg = Leb128Utils.readUnsignedLeb128(encoded);
+          int nameIdx = readStringIndex(encoded);
+          int typeIdx = readStringIndex(encoded);
+          LocalEntry le = new LocalEntry(address, true, reg, nameIdx, typeIdx, ClassDef.NO_INDEX);
+
+          locals.add(le);
+          lastEntryForReg[reg] = le;
         }
-        return idx;
+          break;
+
+        case DBG_START_LOCAL_EXTENDED: {
+          int reg = Leb128Utils.readUnsignedLeb128(encoded);
+          int nameIdx = readStringIndex(encoded);
+          int typeIdx = readStringIndex(encoded);
+          int sigIdx = readStringIndex(encoded);
+          LocalEntry le = new LocalEntry(address, true, reg, nameIdx, typeIdx, sigIdx);
+
+          locals.add(le);
+          lastEntryForReg[reg] = le;
+        }
+          break;
+
+        case DBG_RESTART_LOCAL: {
+          int reg = Leb128Utils.readUnsignedLeb128(encoded);
+          LocalEntry prevle;
+          LocalEntry le;
+
+          try {
+            prevle = lastEntryForReg[reg];
+
+            if (prevle.isStart) {
+              throw new RuntimeException("nonsensical " + "RESTART_LOCAL on live register v" + reg);
+            }
+
+            le = new LocalEntry(address,
+                true,
+                reg,
+                prevle.nameIndex,
+                prevle.typeIndex,
+                prevle.signatureIndex);
+          } catch (NullPointerException ex) {
+            throw new RuntimeException("Encountered RESTART_LOCAL on new v" + reg);
+          }
+
+          locals.add(le);
+          lastEntryForReg[reg] = le;
+        }
+          break;
+
+        case DBG_END_LOCAL: {
+          int reg = Leb128Utils.readUnsignedLeb128(encoded);
+          LocalEntry prevle;
+          LocalEntry le;
+
+          try {
+            prevle = lastEntryForReg[reg];
+
+            if (!prevle.isStart) {
+              throw new RuntimeException("nonsensical " + "END_LOCAL on dead register v" + reg);
+            }
+
+            le = new LocalEntry(address,
+                false,
+                reg,
+                prevle.nameIndex,
+                prevle.typeIndex,
+                prevle.signatureIndex);
+          } catch (NullPointerException ex) {
+            throw new RuntimeException("Encountered END_LOCAL on new v" + reg);
+          }
+
+          locals.add(le);
+          lastEntryForReg[reg] = le;
+        }
+          break;
+
+        case DBG_END_SEQUENCE:
+          // all done
+          return;
+
+        case DBG_ADVANCE_PC:
+          address += Leb128Utils.readUnsignedLeb128(encoded);
+          break;
+
+        case DBG_ADVANCE_LINE:
+          line += Leb128Utils.readSignedLeb128(encoded);
+          break;
+
+        case DBG_SET_PROLOGUE_END:
+          //TODO(dx team) do something with this.
+          break;
+
+        case DBG_SET_EPILOGUE_BEGIN:
+          //TODO(dx team) do something with this.
+          break;
+
+        case DBG_SET_FILE:
+          //TODO(dx team) do something with this.
+          break;
+
+        default:
+          if (opcode < DBG_FIRST_SPECIAL) {
+            throw new RuntimeException("Invalid extended opcode encountered " + opcode);
+          }
+
+          int adjopcode = opcode - DBG_FIRST_SPECIAL;
+
+          address += adjopcode / DBG_LINE_RANGE;
+          line += DBG_LINE_BASE + (adjopcode % DBG_LINE_RANGE);
+
+          positions.add(new PositionEntry(address, line));
+          break;
+
+      }
     }
+  }
+
+  /**
+   * Validates an encoded debug info stream against data used to encode it,
+   * throwing an exception if they do not match. Used to validate the
+   * encoder.
+   *
+   * @param info encoded debug info
+   * @param file {@code non-null;} file to refer to during decoding
+   * @param ref {@code non-null;} method whose info is being decoded
+   * @param code {@code non-null;} original code object that was encoded
+   * @param isStatic whether the method is static
+   */
+  public static void validateEncode(byte[] info, DexFile file, CstMethodRef ref, DalvCode code,
+      boolean isStatic) {
+    PositionList pl = code.getPositions();
+    LocalList ll = code.getLocals();
+    DalvInsnList insns = code.getInsns();
+    int countRegisters = insns.getRegistersSize();
+
+    try {
+      validateEncode0(info, countRegisters, isStatic, ref, file, pl, ll);
+    } catch (RuntimeException ex) {
+      System.err.println("instructions:");
+      insns.debugPrint(System.err, "  ", true);
+      System.err.println("local list:");
+      ll.debugPrint(System.err, "  ");
+      throw ExceptionWithContext.withContext(ex, "while processing " + ref.toHuman());
+    }
+  }
+
+  private static void validateEncode0(byte[] info,
+      int countRegisters,
+      boolean isStatic,
+      CstMethodRef ref,
+      DexFile file,
+      PositionList pl,
+      LocalList ll) {
+    DebugInfoDecoder decoder = new DebugInfoDecoder(info, countRegisters, isStatic, ref, file);
+
+    decoder.decode();
+
+    /*
+     * Go through the decoded position entries, matching up
+     * with original entries.
+     */
+
+List<PositionEntry> decodedEntries = decoder.getPositionList();
+
+    if (decodedEntries.size() != pl.size()) {
+      throw new RuntimeException("Decoded positions table not same size was "
+          + decodedEntries.size() + " expected " + pl.size());
+    }
+
+    for (PositionEntry entry : decodedEntries) {
+      boolean found = false;
+      for (int i = pl.size() - 1; i >= 0; i--) {
+        PositionList.Entry ple = pl.get(i);
+
+        if (entry.line == ple.getPosition().getLine() && entry.address == ple.getAddress()) {
+          found = true;
+          break;
+        }
+      }
+
+      if (!found) {
+        throw new RuntimeException(
+            "Could not match position entry: " + entry.address + ", " + entry.line);
+      }
+    }
+
+    /*
+     * Go through the original local list, in order, matching up
+     * with decoded entries.
+     */
+
+List<LocalEntry> decodedLocals = decoder.getLocals();
+    int thisStringIdx = decoder.thisStringIdx;
+    int decodedSz = decodedLocals.size();
+    int paramBase = decoder.getParamBase();
+
+    /*
+     * Preflight to fill in any parameters that were skipped in
+     * the prologue (including an implied "this") but then
+     * identified by full signature.
+     */
+    for (int i = 0; i < decodedSz; i++) {
+      LocalEntry entry = decodedLocals.get(i);
+      int idx = entry.nameIndex;
+
+      if ((idx < 0) || (idx == thisStringIdx)) {
+        for (int j = i + 1; j < decodedSz; j++) {
+          LocalEntry e2 = decodedLocals.get(j);
+          if (e2.address != 0) {
+            break;
+          }
+          if ((entry.reg == e2.reg) && e2.isStart) {
+            decodedLocals.set(i, e2);
+            decodedLocals.remove(j);
+            decodedSz--;
+            break;
+          }
+        }
+      }
+    }
+
+    int origSz = ll.size();
+    int decodeAt = 0;
+    boolean problem = false;
+
+    for (int i = 0; i < origSz; i++) {
+      LocalList.Entry origEntry = ll.get(i);
+
+      if (origEntry.getDisposition() == LocalList.Disposition.END_REPLACED) {
+        /*
+         * The encoded list doesn't represent replacements, so
+         * ignore them for the sake of comparison.
+         */
+        continue;
+      }
+
+      LocalEntry decodedEntry;
+
+      do {
+        decodedEntry = decodedLocals.get(decodeAt);
+        if (decodedEntry.nameIndex >= 0) {
+          break;
+        }
+        /*
+         * A negative name index means this is an anonymous
+         * parameter, and we shouldn't expect to see it in the
+         * original list. So, skip it.
+         */
+        decodeAt++;
+      } while (decodeAt < decodedSz);
+
+      int decodedAddress = decodedEntry.address;
+
+      if (decodedEntry.reg != origEntry.getRegister()) {
+        System.err.println("local register mismatch at orig " + i + " / decoded " + decodeAt);
+        problem = true;
+        break;
+      }
+
+      if (decodedEntry.isStart != origEntry.isStart()) {
+        System.err.println("local start/end mismatch at orig " + i + " / decoded " + decodeAt);
+        problem = true;
+        break;
+      }
+
+      /*
+       * The secondary check here accounts for the fact that a
+       * parameter might not be marked as starting at 0 in the
+       * original list.
+       */
+      if ((decodedAddress != origEntry.getAddress())
+          && !((decodedAddress == 0) && (decodedEntry.reg >= paramBase))) {
+        System.err.println("local address mismatch at orig " + i + " / decoded " + decodeAt);
+        problem = true;
+        break;
+      }
+
+      decodeAt++;
+    }
+
+    if (problem) {
+      System.err.println("decoded locals:");
+      for (LocalEntry e : decodedLocals) {
+        System.err.println("  " + e);
+      }
+      throw new RuntimeException("local table problem");
+    }
+  }
+
+  private static int extractThisIdx(DexFile file) {
+    int idx = -1;
+
+    try {
+      idx = file.getStringIds().indexOf(new CstString("this"));
+    } catch (IllegalArgumentException ex) {
+      /*
+       * Silently tolerate not finding "this". It just means that
+       * no method has local variable info that looks like
+       * a standard instance method.
+       */
+    }
+    return idx;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/DebugInfoEncoder.java b/dx/src/com/android/jack/dx/dex/file/DebugInfoEncoder.java
index 026d0c0..725200d 100644
--- a/dx/src/com/android/jack/dx/dex/file/DebugInfoEncoder.java
+++ b/dx/src/com/android/jack/dx/dex/file/DebugInfoEncoder.java
@@ -16,6 +16,18 @@
 
 package com.android.jack.dx.dex.file;
 
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_ADVANCE_LINE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_ADVANCE_PC;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_END_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_END_SEQUENCE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_FIRST_SPECIAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_LINE_BASE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_LINE_RANGE;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_RESTART_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_SET_PROLOGUE_END;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL;
+import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL_EXTENDED;
+
 import com.android.jack.dx.dex.code.LocalList;
 import com.android.jack.dx.dex.code.PositionList;
 import com.android.jack.dx.rop.code.RegisterSpec;
@@ -33,11 +45,9 @@
 import java.io.IOException;
 import java.io.PrintWriter;
 import java.util.ArrayList;
+import java.util.BitSet;
 import java.util.Collections;
 import java.util.Comparator;
-import java.util.BitSet;
-
-import static com.android.jack.dx.dex.file.DebugInfoConstants.*;
 
 /**
  * An encoder for the dex debug info state machine format. The format
@@ -53,868 +63,842 @@
  * </ol>
  */
 public final class DebugInfoEncoder {
-    private static final boolean DEBUG = false;
+  private static final boolean DEBUG = false;
 
-    /** {@code null-ok;} positions (line numbers) to encode */
-    private final PositionList positions;
+  /** {@code null-ok;} positions (line numbers) to encode */
+  private final PositionList positions;
 
-    /** {@code null-ok;} local variables to encode */
-    private final LocalList locals;
+  /** {@code null-ok;} local variables to encode */
+  private final LocalList locals;
 
-    private final ByteArrayAnnotatedOutput output;
-    private final DexFile file;
-    private final int codeSize;
-    private final int regSize;
+  private final ByteArrayAnnotatedOutput output;
+  private final DexFile file;
+  private final int codeSize;
+  private final int regSize;
 
-    private final Prototype desc;
-    private final boolean isStatic;
+  private final Prototype desc;
+  private final boolean isStatic;
 
-    /** current encoding state: bytecode address */
-    private int address = 0;
+  /** current encoding state: bytecode address */
+  private int address = 0;
 
-    /** current encoding state: line number */
-    private int line = 1;
+  /** current encoding state: line number */
+  private int line = 1;
 
-    /**
-     * if non-null: the output to write annotations to. No normal
-     * output is written to this.
-     */
-    private AnnotatedOutput annotateTo;
+  /**
+   * if non-null: the output to write annotations to. No normal
+   * output is written to this.
+   */
+  private AnnotatedOutput annotateTo;
 
-    /** if non-null: another possible output for annotations */
-    private PrintWriter debugPrint;
+  /** if non-null: another possible output for annotations */
+  private PrintWriter debugPrint;
 
-    /** if non-null: the prefix for each annotation or debugPrint line */
-    private String prefix;
+  /** if non-null: the prefix for each annotation or debugPrint line */
+  private String prefix;
 
-    /** true if output should be consumed during annotation */
-    private boolean shouldConsume;
+  /** true if output should be consumed during annotation */
+  private boolean shouldConsume;
 
-    /** indexed by register; last local alive in register */
-    private final LocalList.Entry[] lastEntryForReg;
+  /** indexed by register; last local alive in register */
+  private final LocalList.Entry[] lastEntryForReg;
 
-    /**
-     * Creates an instance.
-     *
-     * @param positions {@code null-ok;} positions (line numbers) to encode
-     * @param locals {@code null-ok;} local variables to encode
-     * @param file {@code null-ok;} may only be {@code null} if simply using
-     * this class to do a debug print
-     * @param codeSize
-     * @param regSize
-     * @param isStatic
-     * @param ref
-     */
-    public DebugInfoEncoder(PositionList positions, LocalList locals,
-            DexFile file, int codeSize, int regSize,
-            boolean isStatic, CstMethodRef ref) {
-        this.positions = positions;
-        this.locals = locals;
-        this.file = file;
-        this.desc = ref.getPrototype();
-        this.isStatic = isStatic;
-        this.codeSize = codeSize;
-        this.regSize = regSize;
+  /**
+   * Creates an instance.
+   *
+   * @param positions {@code null-ok;} positions (line numbers) to encode
+   * @param locals {@code null-ok;} local variables to encode
+   * @param file {@code null-ok;} may only be {@code null} if simply using
+   * this class to do a debug print
+   * @param codeSize
+   * @param regSize
+   * @param isStatic
+   * @param ref
+   */
+  public DebugInfoEncoder(PositionList positions,
+      LocalList locals,
+      DexFile file,
+      int codeSize,
+      int regSize,
+      boolean isStatic,
+      CstMethodRef ref) {
+    this.positions = positions;
+    this.locals = locals;
+    this.file = file;
+    this.desc = ref.getPrototype();
+    this.isStatic = isStatic;
+    this.codeSize = codeSize;
+    this.regSize = regSize;
 
-        output = new ByteArrayAnnotatedOutput();
-        lastEntryForReg = new LocalList.Entry[regSize];
+    output = new ByteArrayAnnotatedOutput();
+    lastEntryForReg = new LocalList.Entry[regSize];
+  }
+
+  /**
+   * Annotates or writes a message to the {@code debugPrint} writer
+   * if applicable.
+   *
+   * @param length the number of bytes associated with this message
+   * @param message the message itself
+   */
+  private void annotate(int length, String message) {
+    if (prefix != null) {
+      message = prefix + message;
     }
 
-    /**
-     * Annotates or writes a message to the {@code debugPrint} writer
-     * if applicable.
-     *
-     * @param length the number of bytes associated with this message
-     * @param message the message itself
-     */
-    private void annotate(int length, String message) {
-        if (prefix != null) {
-            message = prefix + message;
-        }
-
-        if (annotateTo != null) {
-            annotateTo.annotate(shouldConsume ? length : 0, message);
-        }
-
-        if (debugPrint != null) {
-            debugPrint.println(message);
-        }
+    if (annotateTo != null) {
+      annotateTo.annotate(shouldConsume ? length : 0, message);
     }
 
-    /**
-     * Converts this (PositionList, LocalList) pair into a state machine
-     * sequence.
-     *
-     * @return {@code non-null;} encoded byte sequence without padding and
-     * terminated with a {@code 0x00} byte
-     */
-    public byte[] convert() {
-        try {
-            byte[] ret;
-            ret = convert0();
+    if (debugPrint != null) {
+      debugPrint.println(message);
+    }
+  }
 
-            if (DEBUG) {
-                for (int i = 0 ; i < ret.length; i++) {
-                    System.err.printf("byte %02x\n", (0xff & ret[i]));
-                }
-            }
+  /**
+   * Converts this (PositionList, LocalList) pair into a state machine
+   * sequence.
+   *
+   * @return {@code non-null;} encoded byte sequence without padding and
+   * terminated with a {@code 0x00} byte
+   */
+  public byte[] convert() {
+    try {
+      byte[] ret;
+      ret = convert0();
 
-            return ret;
-        } catch (IOException ex) {
-            throw ExceptionWithContext
-                    .withContext(ex, "...while encoding debug info");
+      if (DEBUG) {
+        for (int i = 0; i < ret.length; i++) {
+          System.err.printf("byte %02x\n", (0xff & ret[i]));
         }
+      }
+
+      return ret;
+    } catch (IOException ex) {
+      throw ExceptionWithContext.withContext(ex, "...while encoding debug info");
+    }
+  }
+
+  /**
+   * Converts and produces annotations on a stream. Does not write
+   * actual bits to the {@code AnnotatedOutput}.
+   *
+   * @param prefix {@code null-ok;} prefix to attach to each line of output
+   * @param debugPrint {@code null-ok;} if specified, an alternate output for
+   * annotations
+   * @param out {@code null-ok;} if specified, where annotations should go
+   * @param consume whether to claim to have consumed output for
+   * {@code out}
+   * @return {@code non-null;} encoded output
+   */
+  public byte[] convertAndAnnotate(String prefix, PrintWriter debugPrint, AnnotatedOutput out,
+      boolean consume) {
+    this.prefix = prefix;
+    this.debugPrint = debugPrint;
+    annotateTo = out;
+    shouldConsume = consume;
+
+    byte[] result = convert();
+
+    return result;
+  }
+
+  private byte[] convert0() throws IOException {
+    ArrayList<PositionList.Entry> sortedPositions = buildSortedPositions();
+    ArrayList<LocalList.Entry> methodArgs = extractMethodArguments();
+
+    emitHeader(sortedPositions, methodArgs);
+
+    // TODO(dx team): Make this mark be the actual prologue end.
+    output.writeByte(DBG_SET_PROLOGUE_END);
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(1, String.format("%04x: prologue end", address));
     }
 
-    /**
-     * Converts and produces annotations on a stream. Does not write
-     * actual bits to the {@code AnnotatedOutput}.
-     *
-     * @param prefix {@code null-ok;} prefix to attach to each line of output
-     * @param debugPrint {@code null-ok;} if specified, an alternate output for
-     * annotations
-     * @param out {@code null-ok;} if specified, where annotations should go
-     * @param consume whether to claim to have consumed output for
-     * {@code out}
-     * @return {@code non-null;} encoded output
-     */
-    public byte[] convertAndAnnotate(String prefix, PrintWriter debugPrint,
-            AnnotatedOutput out, boolean consume) {
-        this.prefix = prefix;
-        this.debugPrint = debugPrint;
-        annotateTo = out;
-        shouldConsume = consume;
+    int positionsSz = sortedPositions.size();
+    int localsSz = locals.size();
 
-        byte[] result = convert();
+    // Current index in sortedPositions
+    int curPositionIdx = 0;
+    // Current index in locals
+    int curLocalIdx = 0;
 
-        return result;
+    for (;;) {
+      /*
+       * Emit any information for the current address.
+       */
+
+curLocalIdx = emitLocalsAtAddress(curLocalIdx);
+      curPositionIdx = emitPositionsAtAddress(curPositionIdx, sortedPositions);
+
+      /*
+       * Figure out what the next important address is.
+       */
+
+int nextAddrL = Integer.MAX_VALUE; // local variable
+      int nextAddrP = Integer.MAX_VALUE; // position (line number)
+
+      if (curLocalIdx < localsSz) {
+        nextAddrL = locals.get(curLocalIdx).getAddress();
+      }
+
+      if (curPositionIdx < positionsSz) {
+        nextAddrP = sortedPositions.get(curPositionIdx).getAddress();
+      }
+
+      int next = Math.min(nextAddrP, nextAddrL);
+
+      // No next important address == done.
+      if (next == Integer.MAX_VALUE) {
+        break;
+      }
+
+      /*
+       * If the only work remaining are local ends at the end of the
+       * block, stop here. Those are implied anyway.
+       */
+      if (next == codeSize && nextAddrL == Integer.MAX_VALUE && nextAddrP == Integer.MAX_VALUE) {
+        break;
+      }
+
+      if (next == nextAddrP) {
+        // Combined advance PC + position entry
+        emitPosition(sortedPositions.get(curPositionIdx++));
+      } else {
+        emitAdvancePc(next - address);
+      }
     }
 
-    private byte[] convert0() throws IOException {
-        ArrayList<PositionList.Entry> sortedPositions = buildSortedPositions();
-        ArrayList<LocalList.Entry> methodArgs = extractMethodArguments();
+    emitEndSequence();
 
-        emitHeader(sortedPositions, methodArgs);
+    return output.toByteArray();
+  }
 
-        // TODO: Make this mark be the actual prologue end.
-        output.writeByte(DBG_SET_PROLOGUE_END);
+  /**
+   * Emits all local variable activity that occurs at the current
+   * {@link #address} starting at the given index into {@code
+   * locals} and including all subsequent activity at the same
+   * address.
+   *
+   * @param curLocalIdx Current index in locals
+   * @return new value for {@code curLocalIdx}
+   * @throws IOException
+   */
+  private int emitLocalsAtAddress(int curLocalIdx) throws IOException {
+    int sz = locals.size();
 
-        if (annotateTo != null || debugPrint != null) {
-            annotate(1, String.format("%04x: prologue end",address));
-        }
+    // TODO(dx team): Don't emit ends implied by starts.
 
-        int positionsSz = sortedPositions.size();
-        int localsSz = locals.size();
+    while ((curLocalIdx < sz) && (locals.get(curLocalIdx).getAddress() == address)) {
+      LocalList.Entry entry = locals.get(curLocalIdx++);
+      int reg = entry.getRegister();
+      LocalList.Entry prevEntry = lastEntryForReg[reg];
 
-        // Current index in sortedPositions
-        int curPositionIdx = 0;
-        // Current index in locals
-        int curLocalIdx = 0;
-
-        for (;;) {
-            /*
-             * Emit any information for the current address.
-             */
-
-            curLocalIdx = emitLocalsAtAddress(curLocalIdx);
-            curPositionIdx =
-                emitPositionsAtAddress(curPositionIdx, sortedPositions);
-
-            /*
-             * Figure out what the next important address is.
-             */
-
-            int nextAddrL = Integer.MAX_VALUE; // local variable
-            int nextAddrP = Integer.MAX_VALUE; // position (line number)
-
-            if (curLocalIdx < localsSz) {
-                nextAddrL = locals.get(curLocalIdx).getAddress();
-            }
-
-            if (curPositionIdx < positionsSz) {
-                nextAddrP = sortedPositions.get(curPositionIdx).getAddress();
-            }
-
-            int next = Math.min(nextAddrP, nextAddrL);
-
-            // No next important address == done.
-            if (next == Integer.MAX_VALUE) {
-                break;
-            }
-
-            /*
-             * If the only work remaining are local ends at the end of the
-             * block, stop here. Those are implied anyway.
-             */
-            if (next == codeSize
-                    && nextAddrL == Integer.MAX_VALUE
-                    && nextAddrP == Integer.MAX_VALUE) {
-                break;
-            }
-
-            if (next == nextAddrP) {
-                // Combined advance PC + position entry
-                emitPosition(sortedPositions.get(curPositionIdx++));
-            } else {
-                emitAdvancePc(next - address);
-            }
-        }
-
-        emitEndSequence();
-
-        return output.toByteArray();
-    }
-
-    /**
-     * Emits all local variable activity that occurs at the current
-     * {@link #address} starting at the given index into {@code
-     * locals} and including all subsequent activity at the same
-     * address.
-     *
-     * @param curLocalIdx Current index in locals
-     * @return new value for {@code curLocalIdx}
-     * @throws IOException
-     */
-    private int emitLocalsAtAddress(int curLocalIdx)
-            throws IOException {
-        int sz = locals.size();
-
-        // TODO: Don't emit ends implied by starts.
-
-        while ((curLocalIdx < sz)
-                && (locals.get(curLocalIdx).getAddress() == address)) {
-            LocalList.Entry entry = locals.get(curLocalIdx++);
-            int reg = entry.getRegister();
-            LocalList.Entry prevEntry = lastEntryForReg[reg];
-
-            if (entry == prevEntry) {
-                /*
-                 * Here we ignore locals entries for parameters,
-                 * which have already been represented and placed in the
-                 * lastEntryForReg array.
-                 */
-                continue;
-            }
-
-            // At this point we have a new entry one way or another.
-            lastEntryForReg[reg] = entry;
-
-            if (entry.isStart()) {
-                if ((prevEntry != null) && entry.matches(prevEntry)) {
-                    /*
-                     * The previous local in this register has the same
-                     * name and type as the one being introduced now, so
-                     * use the more efficient "restart" form.
-                     */
-                    if (prevEntry.isStart()) {
-                        /*
-                         * We should never be handed a start when a
-                         * a matching local is already active.
-                         */
-                        throw new RuntimeException("shouldn't happen");
-                    }
-                    emitLocalRestart(entry);
-                } else {
-                    emitLocalStart(entry);
-                }
-            } else {
-                /*
-                 * Only emit a local end if it is *not* due to a direct
-                 * replacement. Direct replacements imply an end of the
-                 * previous local in the same register.
-                 *
-                 * TODO: Make sure the runtime can deal with implied
-                 * local ends from category-2 interactions, and when so,
-                 * also stop emitting local ends for those cases.
-                 */
-                if (entry.getDisposition()
-                        != LocalList.Disposition.END_REPLACED) {
-                    emitLocalEnd(entry);
-                }
-            }
-        }
-
-        return curLocalIdx;
-    }
-
-    /**
-     * Emits all positions that occur at the current {@code address}
-     *
-     * @param curPositionIdx Current index in sortedPositions
-     * @param sortedPositions positions, sorted by ascending address
-     * @return new value for {@code curPositionIdx}
-     * @throws IOException
-     */
-    private int emitPositionsAtAddress(int curPositionIdx,
-            ArrayList<PositionList.Entry> sortedPositions)
-            throws IOException {
-        int positionsSz = sortedPositions.size();
-        while ((curPositionIdx < positionsSz)
-                && (sortedPositions.get(curPositionIdx).getAddress()
-                        == address)) {
-            emitPosition(sortedPositions.get(curPositionIdx++));
-        }
-        return curPositionIdx;
-    }
-
-    /**
-     * Emits the header sequence, which consists of LEB128-encoded initial
-     * line number and string indicies for names of all non-"this" arguments.
-     *
-     * @param sortedPositions positions, sorted by ascending address
-     * @param methodArgs local list entries for method argumens arguments,
-     * in left-to-right order omitting "this"
-     * @throws IOException
-     */
-    private void emitHeader(ArrayList<PositionList.Entry> sortedPositions,
-            ArrayList<LocalList.Entry> methodArgs) throws IOException {
-        boolean annotate = (annotateTo != null) || (debugPrint != null);
-        int mark = output.getCursor();
-
-        // Start by initializing the line number register.
-        if (sortedPositions.size() > 0) {
-            PositionList.Entry entry = sortedPositions.get(0);
-            line = entry.getPosition().getLine();
-        }
-        output.writeUleb128(line);
-
-        if (annotate) {
-            annotate(output.getCursor() - mark, "line_start: " + line);
-        }
-
-        int curParam = getParamBase();
-        // paramTypes will not include 'this'
-        StdTypeList paramTypes = desc.getParameterTypes();
-        int szParamTypes = paramTypes.size();
-
+      if (entry == prevEntry) {
         /*
-         * Initialize lastEntryForReg to have an initial
-         * entry for the 'this' pointer.
+         * Here we ignore locals entries for parameters,
+         * which have already been represented and placed in the
+         * lastEntryForReg array.
          */
-        if (!isStatic) {
-            for (LocalList.Entry arg : methodArgs) {
-                if (curParam == arg.getRegister()) {
-                    lastEntryForReg[curParam] = arg;
-                    break;
-                }
-            }
-            curParam++;
+        continue;
+      }
+
+      // At this point we have a new entry one way or another.
+      lastEntryForReg[reg] = entry;
+
+      if (entry.isStart()) {
+        if ((prevEntry != null) && entry.matches(prevEntry)) {
+          /*
+           * The previous local in this register has the same
+           * name and type as the one being introduced now, so
+           * use the more efficient "restart" form.
+           */
+          if (prevEntry.isStart()) {
+            /*
+             * We should never be handed a start when a
+             * a matching local is already active.
+             */
+            throw new RuntimeException("shouldn't happen");
+          }
+          emitLocalRestart(entry);
+        } else {
+          emitLocalStart(entry);
         }
-
-        // Write out the number of parameter entries that will follow.
-        mark = output.getCursor();
-        output.writeUleb128(szParamTypes);
-
-        if (annotate) {
-            annotate(output.getCursor() - mark,
-                    String.format("parameters_size: %04x", szParamTypes));
-        }
-
+      } else {
         /*
-         * Then emit the string indicies of all the method parameters.
-         * Note that 'this', if applicable, is excluded.
+         * Only emit a local end if it is *not* due to a direct
+         * replacement. Direct replacements imply an end of the
+         * previous local in the same register.
+         *
+         * TODO(dx team): Make sure the runtime can deal with implied
+         * local ends from category-2 interactions, and when so,
+         * also stop emitting local ends for those cases.
          */
-        for (int i = 0; i < szParamTypes; i++) {
-            Type pt = paramTypes.get(i);
-            LocalList.Entry found = null;
-
-            mark = output.getCursor();
-
-            for (LocalList.Entry arg : methodArgs) {
-                if (curParam == arg.getRegister()) {
-                    found = arg;
-
-                    if (arg.getSignature() != null) {
-                        /*
-                         * Parameters with signatures will be re-emitted
-                         * in complete as LOCAL_START_EXTENDED's below.
-                         */
-                        emitStringIndex(null);
-                    } else {
-                        emitStringIndex(arg.getName());
-                    }
-                    lastEntryForReg[curParam] = arg;
-
-                    break;
-                }
-            }
-
-            if (found == null) {
-                /*
-                 * Emit a null symbol for "unnamed." This is common
-                 * for, e.g., synthesized methods and inner-class
-                 * this$0 arguments.
-                 */
-                emitStringIndex(null);
-            }
-
-            if (annotate) {
-                String parameterName
-                        = (found == null || found.getSignature() != null)
-                                ? "<unnamed>" : found.getName().toHuman();
-                annotate(output.getCursor() - mark,
-                        "parameter " + parameterName + " "
-                                + RegisterSpec.PREFIX + curParam);
-            }
-
-            curParam += pt.getCategory();
+        if (entry.getDisposition() != LocalList.Disposition.END_REPLACED) {
+          emitLocalEnd(entry);
         }
+      }
+    }
 
+    return curLocalIdx;
+  }
+
+  /**
+   * Emits all positions that occur at the current {@code address}
+   *
+   * @param curPositionIdx Current index in sortedPositions
+   * @param sortedPositions positions, sorted by ascending address
+   * @return new value for {@code curPositionIdx}
+   * @throws IOException
+   */
+  private int emitPositionsAtAddress(int curPositionIdx,
+      ArrayList<PositionList.Entry> sortedPositions) throws IOException {
+    int positionsSz = sortedPositions.size();
+    while ((curPositionIdx < positionsSz)
+        && (sortedPositions.get(curPositionIdx).getAddress() == address)) {
+      emitPosition(sortedPositions.get(curPositionIdx++));
+    }
+    return curPositionIdx;
+  }
+
+  /**
+   * Emits the header sequence, which consists of LEB128-encoded initial
+   * line number and string indicies for names of all non-"this" arguments.
+   *
+   * @param sortedPositions positions, sorted by ascending address
+   * @param methodArgs local list entries for method argumens arguments,
+   * in left-to-right order omitting "this"
+   * @throws IOException
+   */
+  private void emitHeader(ArrayList<PositionList.Entry> sortedPositions,
+      ArrayList<LocalList.Entry> methodArgs) throws IOException {
+    boolean annotate = (annotateTo != null) || (debugPrint != null);
+    int mark = output.getCursor();
+
+    // Start by initializing the line number register.
+    if (sortedPositions.size() > 0) {
+      PositionList.Entry entry = sortedPositions.get(0);
+      line = entry.getPosition().getLine();
+    }
+    output.writeUleb128(line);
+
+    if (annotate) {
+      annotate(output.getCursor() - mark, "line_start: " + line);
+    }
+
+    int curParam = getParamBase();
+    // paramTypes will not include 'this'
+    StdTypeList paramTypes = desc.getParameterTypes();
+    int szParamTypes = paramTypes.size();
+
+    /*
+     * Initialize lastEntryForReg to have an initial
+     * entry for the 'this' pointer.
+     */
+    if (!isStatic) {
+      for (LocalList.Entry arg : methodArgs) {
+        if (curParam == arg.getRegister()) {
+          lastEntryForReg[curParam] = arg;
+          break;
+        }
+      }
+      curParam++;
+    }
+
+    // Write out the number of parameter entries that will follow.
+    mark = output.getCursor();
+    output.writeUleb128(szParamTypes);
+
+    if (annotate) {
+      annotate(output.getCursor() - mark, String.format("parameters_size: %04x", szParamTypes));
+    }
+
+    /*
+     * Then emit the string indicies of all the method parameters.
+     * Note that 'this', if applicable, is excluded.
+     */
+    for (int i = 0; i < szParamTypes; i++) {
+      Type pt = paramTypes.get(i);
+      LocalList.Entry found = null;
+
+      mark = output.getCursor();
+
+      for (LocalList.Entry arg : methodArgs) {
+        if (curParam == arg.getRegister()) {
+          found = arg;
+
+          if (arg.getSignature() != null) {
+            /*
+             * Parameters with signatures will be re-emitted
+             * in complete as LOCAL_START_EXTENDED's below.
+             */
+            emitStringIndex(null);
+          } else {
+            emitStringIndex(arg.getName());
+          }
+          lastEntryForReg[curParam] = arg;
+
+          break;
+        }
+      }
+
+      if (found == null) {
         /*
-         * If anything emitted above has a type signature, emit it again as
-         * a LOCAL_RESTART_EXTENDED
+         * Emit a null symbol for "unnamed." This is common
+         * for, e.g., synthesized methods and inner-class
+         * this$0 arguments.
          */
+        emitStringIndex(null);
+      }
 
-        for (LocalList.Entry arg : lastEntryForReg) {
-            if (arg == null) {
-                continue;
-            }
+      if (annotate) {
+        String parameterName = (found == null || found.getSignature() != null) ? "<unnamed>"
+            : found.getName().toHuman();
+        annotate(output.getCursor() - mark,
+            "parameter " + parameterName + " " + RegisterSpec.PREFIX + curParam);
+      }
 
-            CstString signature = arg.getSignature();
-
-            if (signature != null) {
-                emitLocalStartExtended(arg);
-            }
-        }
+      curParam += pt.getCategory();
     }
 
-    /**
-     * Builds a list of position entries, sorted by ascending address.
-     *
-     * @return A sorted positions list
+    /*
+     * If anything emitted above has a type signature, emit it again as
+     * a LOCAL_RESTART_EXTENDED
      */
-    private ArrayList<PositionList.Entry> buildSortedPositions() {
-        int sz = (positions == null) ? 0 : positions.size();
-        ArrayList<PositionList.Entry> result = new ArrayList(sz);
 
-        for (int i = 0; i < sz; i++) {
-            result.add(positions.get(i));
-        }
+for (LocalList.Entry arg : lastEntryForReg) {
+      if (arg == null) {
+        continue;
+      }
 
-        // Sort ascending by address.
-        Collections.sort (result, new Comparator<PositionList.Entry>() {
-            public int compare (PositionList.Entry a, PositionList.Entry b) {
-                return a.getAddress() - b.getAddress();
-            }
+      CstString signature = arg.getSignature();
 
-            public boolean equals (Object obj) {
-               return obj == this;
-            }
-        });
-        return result;
+      if (signature != null) {
+        emitLocalStartExtended(arg);
+      }
+    }
+  }
+
+  /**
+   * Builds a list of position entries, sorted by ascending address.
+   *
+   * @return A sorted positions list
+   */
+  private ArrayList<PositionList.Entry> buildSortedPositions() {
+    int sz = (positions == null) ? 0 : positions.size();
+    ArrayList<PositionList.Entry> result = new ArrayList<PositionList.Entry>(sz);
+
+    for (int i = 0; i < sz; i++) {
+      result.add(positions.get(i));
     }
 
-    /**
-     * Gets the register that begins the method's parameter range (including
-     * the 'this' parameter for non-static methods). The range continues until
-     * {@code regSize}
-     *
-     * @return register as noted above
-     */
-    private int getParamBase() {
-        return regSize
-                - desc.getParameterTypes().getWordCount() - (isStatic? 0 : 1);
+    // Sort ascending by address.
+    Collections.sort(result, new Comparator<PositionList.Entry>() {
+      @Override
+      public int compare(PositionList.Entry a, PositionList.Entry b) {
+        return a.getAddress() - b.getAddress();
+      }
+
+      @Override
+      public boolean equals(Object obj) {
+        return obj == this;
+      }
+    });
+    return result;
+  }
+
+  /**
+   * Gets the register that begins the method's parameter range (including
+   * the 'this' parameter for non-static methods). The range continues until
+   * {@code regSize}
+   *
+   * @return register as noted above
+   */
+  private int getParamBase() {
+    return regSize - desc.getParameterTypes().getWordCount() - (isStatic ? 0 : 1);
+  }
+
+  /**
+   * Extracts method arguments from a locals list. These will be collected
+   * from the input list and sorted by ascending register in the
+   * returned list.
+   *
+   * @return list of non-{@code this} method argument locals,
+   * sorted by ascending register
+   */
+  private ArrayList<LocalList.Entry> extractMethodArguments() {
+    ArrayList<LocalList.Entry> result =
+        new ArrayList<LocalList.Entry>(desc.getParameterTypes().size());
+    int argBase = getParamBase();
+    BitSet seen = new BitSet(regSize - argBase);
+    int sz = locals.size();
+
+    for (int i = 0; i < sz; i++) {
+      LocalList.Entry e = locals.get(i);
+      int reg = e.getRegister();
+
+      if (reg < argBase) {
+        continue;
+      }
+
+      // only the lowest-start-address entry is included.
+      if (seen.get(reg - argBase)) {
+        continue;
+      }
+
+      seen.set(reg - argBase);
+      result.add(e);
     }
 
-    /**
-     * Extracts method arguments from a locals list. These will be collected
-     * from the input list and sorted by ascending register in the
-     * returned list.
-     *
-     * @return list of non-{@code this} method argument locals,
-     * sorted by ascending register
-     */
-    private ArrayList<LocalList.Entry> extractMethodArguments() {
-        ArrayList<LocalList.Entry> result
-                = new ArrayList(desc.getParameterTypes().size());
-        int argBase = getParamBase();
-        BitSet seen = new BitSet(regSize - argBase);
-        int sz = locals.size();
+    // Sort by ascending register.
+    Collections.sort(result, new Comparator<LocalList.Entry>() {
+      @Override
+      public int compare(LocalList.Entry a, LocalList.Entry b) {
+        return a.getRegister() - b.getRegister();
+      }
 
-        for (int i = 0; i < sz; i++) {
-            LocalList.Entry e = locals.get(i);
-            int reg = e.getRegister();
+      @Override
+      public boolean equals(Object obj) {
+        return obj == this;
+      }
+    });
 
-            if (reg < argBase) {
-                continue;
-            }
+    return result;
+  }
 
-            // only the lowest-start-address entry is included.
-            if (seen.get(reg - argBase)) {
-                continue;
-            }
+  /**
+   * Returns a string representation of this LocalList entry that is
+   * appropriate for emitting as an annotation.
+   *
+   * @param e {@code non-null;} entry
+   * @return {@code non-null;} annotation string
+   */
+  private String entryAnnotationString(LocalList.Entry e) {
+    StringBuilder sb = new StringBuilder();
 
-            seen.set(reg - argBase);
-            result.add(e);
-        }
+    sb.append(RegisterSpec.PREFIX);
+    sb.append(e.getRegister());
+    sb.append(' ');
 
-        // Sort by ascending register.
-        Collections.sort(result, new Comparator<LocalList.Entry>() {
-            public int compare(LocalList.Entry a, LocalList.Entry b) {
-                return a.getRegister() - b.getRegister();
-            }
+    CstString name = e.getName();
+    if (name == null) {
+      sb.append("null");
+    } else {
+      sb.append(name.toHuman());
+    }
+    sb.append(' ');
 
-            public boolean equals(Object obj) {
-               return obj == this;
-            }
-        });
-
-        return result;
+    CstType type = e.getType();
+    if (type == null) {
+      sb.append("null");
+    } else {
+      sb.append(type.toHuman());
     }
 
-    /**
-     * Returns a string representation of this LocalList entry that is
-     * appropriate for emitting as an annotation.
-     *
-     * @param e {@code non-null;} entry
-     * @return {@code non-null;} annotation string
-     */
-    private String entryAnnotationString(LocalList.Entry e) {
-        StringBuilder sb = new StringBuilder();
+    CstString signature = e.getSignature();
 
-        sb.append(RegisterSpec.PREFIX);
-        sb.append(e.getRegister());
-        sb.append(' ');
-
-        CstString name = e.getName();
-        if (name == null) {
-            sb.append("null");
-        } else {
-            sb.append(name.toHuman());
-        }
-        sb.append(' ');
-
-        CstType type = e.getType();
-        if (type == null) {
-            sb.append("null");
-        } else {
-            sb.append(type.toHuman());
-        }
-
-        CstString signature = e.getSignature();
-
-        if (signature != null) {
-            sb.append(' ');
-            sb.append(signature.toHuman());
-        }
-
-        return sb.toString();
+    if (signature != null) {
+      sb.append(' ');
+      sb.append(signature.toHuman());
     }
 
-    /**
-     * Emits a {@link DebugInfoConstants#DBG_RESTART_LOCAL DBG_RESTART_LOCAL}
-     * sequence.
-     *
-     * @param entry entry associated with this restart
-     * @throws IOException
-     */
-    private void emitLocalRestart(LocalList.Entry entry)
-            throws IOException {
+    return sb.toString();
+  }
 
-        int mark = output.getCursor();
+  /**
+   * Emits a {@link DebugInfoConstants#DBG_RESTART_LOCAL DBG_RESTART_LOCAL}
+   * sequence.
+   *
+   * @param entry entry associated with this restart
+   * @throws IOException
+   */
+  private void emitLocalRestart(LocalList.Entry entry) throws IOException {
 
-        output.writeByte(DBG_RESTART_LOCAL);
-        emitUnsignedLeb128(entry.getRegister());
+    int mark = output.getCursor();
 
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("%04x: +local restart %s",
-                            address, entryAnnotationString(entry)));
-        }
+    output.writeByte(DBG_RESTART_LOCAL);
+    emitUnsignedLeb128(entry.getRegister());
 
-        if (DEBUG) {
-            System.err.println("emit local restart");
-        }
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark,
+          String.format("%04x: +local restart %s", address, entryAnnotationString(entry)));
     }
 
-    /**
-     * Emits a string index as an unsigned LEB128. The actual value written
-     * is shifted by 1, so that the '0' value is reserved for "null". The
-     * null symbol is used in some cases by the parameter name list
-     * at the beginning of the sequence.
-     *
-     * @param string {@code null-ok;} string to emit
-     * @throws IOException
-     */
-    private void emitStringIndex(CstString string) throws IOException {
-        if ((string == null) || (file == null)) {
-            output.writeUleb128(0);
-        } else {
-            output.writeUleb128(
-                    1 + file.getStringIds().indexOf(string));
-        }
+    if (DEBUG) {
+      System.err.println("emit local restart");
+    }
+  }
 
-        if (DEBUG) {
-            System.err.printf("Emit string %s\n",
-                    string == null ? "<null>" : string.toQuoted());
-        }
+  /**
+   * Emits a string index as an unsigned LEB128. The actual value written
+   * is shifted by 1, so that the '0' value is reserved for "null". The
+   * null symbol is used in some cases by the parameter name list
+   * at the beginning of the sequence.
+   *
+   * @param string {@code null-ok;} string to emit
+   * @throws IOException
+   */
+  private void emitStringIndex(CstString string) throws IOException {
+    if ((string == null) || (file == null)) {
+      output.writeUleb128(0);
+    } else {
+      output.writeUleb128(1 + file.getStringIds().indexOf(string));
     }
 
-    /**
-     * Emits a type index as an unsigned LEB128. The actual value written
-     * is shifted by 1, so that the '0' value is reserved for "null".
-     *
-     * @param type {@code null-ok;} type to emit
-     * @throws IOException
-     */
-    private void emitTypeIndex(CstType type) throws IOException {
-        if ((type == null) || (file == null)) {
-            output.writeUleb128(0);
-        } else {
-            output.writeUleb128(
-                    1 + file.getTypeIds().indexOf(type));
-        }
+    if (DEBUG) {
+      System.err.printf("Emit string %s\n", string == null ? "<null>" : string.toQuoted());
+    }
+  }
 
-        if (DEBUG) {
-            System.err.printf("Emit type %s\n",
-                    type == null ? "<null>" : type.toHuman());
-        }
+  /**
+   * Emits a type index as an unsigned LEB128. The actual value written
+   * is shifted by 1, so that the '0' value is reserved for "null".
+   *
+   * @param type {@code null-ok;} type to emit
+   * @throws IOException
+   */
+  private void emitTypeIndex(CstType type) throws IOException {
+    if ((type == null) || (file == null)) {
+      output.writeUleb128(0);
+    } else {
+      output.writeUleb128(1 + file.getTypeIds().indexOf(type));
     }
 
-    /**
-     * Emits a {@link DebugInfoConstants#DBG_START_LOCAL DBG_START_LOCAL} or
-     * {@link DebugInfoConstants#DBG_START_LOCAL_EXTENDED
-     * DBG_START_LOCAL_EXTENDED} sequence.
-     *
-     * @param entry entry to emit
-     * @throws IOException
-     */
-    private void emitLocalStart(LocalList.Entry entry)
-        throws IOException {
+    if (DEBUG) {
+      System.err.printf("Emit type %s\n", type == null ? "<null>" : type.toHuman());
+    }
+  }
 
-        if (entry.getSignature() != null) {
-            emitLocalStartExtended(entry);
-            return;
-        }
+  /**
+   * Emits a {@link DebugInfoConstants#DBG_START_LOCAL DBG_START_LOCAL} or
+   * {@link DebugInfoConstants#DBG_START_LOCAL_EXTENDED
+   * DBG_START_LOCAL_EXTENDED} sequence.
+   *
+   * @param entry entry to emit
+   * @throws IOException
+   */
+  private void emitLocalStart(LocalList.Entry entry) throws IOException {
 
-        int mark = output.getCursor();
-
-        output.writeByte(DBG_START_LOCAL);
-
-        emitUnsignedLeb128(entry.getRegister());
-        emitStringIndex(entry.getName());
-        emitTypeIndex(entry.getType());
-
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("%04x: +local %s", address,
-                            entryAnnotationString(entry)));
-        }
-
-        if (DEBUG) {
-            System.err.println("emit local start");
-        }
+    if (entry.getSignature() != null) {
+      emitLocalStartExtended(entry);
+      return;
     }
 
-    /**
-     * Emits a {@link DebugInfoConstants#DBG_START_LOCAL_EXTENDED
-     * DBG_START_LOCAL_EXTENDED} sequence.
-     *
-     * @param entry entry to emit
-     * @throws IOException
-     */
-    private void emitLocalStartExtended(LocalList.Entry entry)
-        throws IOException {
+    int mark = output.getCursor();
 
-        int mark = output.getCursor();
+    output.writeByte(DBG_START_LOCAL);
 
-        output.writeByte(DBG_START_LOCAL_EXTENDED);
+    emitUnsignedLeb128(entry.getRegister());
+    emitStringIndex(entry.getName());
+    emitTypeIndex(entry.getType());
 
-        emitUnsignedLeb128(entry.getRegister());
-        emitStringIndex(entry.getName());
-        emitTypeIndex(entry.getType());
-        emitStringIndex(entry.getSignature());
-
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("%04x: +localx %s", address,
-                            entryAnnotationString(entry)));
-        }
-
-        if (DEBUG) {
-            System.err.println("emit local start");
-        }
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark,
+          String.format("%04x: +local %s", address, entryAnnotationString(entry)));
     }
 
-    /**
-     * Emits a {@link DebugInfoConstants#DBG_END_LOCAL DBG_END_LOCAL} sequence.
-     *
-     * @param entry {@code entry non-null;} entry associated with end.
-     * @throws IOException
-     */
-    private void emitLocalEnd(LocalList.Entry entry)
-            throws IOException {
+    if (DEBUG) {
+      System.err.println("emit local start");
+    }
+  }
 
-        int mark = output.getCursor();
+  /**
+   * Emits a {@link DebugInfoConstants#DBG_START_LOCAL_EXTENDED
+   * DBG_START_LOCAL_EXTENDED} sequence.
+   *
+   * @param entry entry to emit
+   * @throws IOException
+   */
+  private void emitLocalStartExtended(LocalList.Entry entry) throws IOException {
 
-        output.writeByte(DBG_END_LOCAL);
-        output.writeUleb128(entry.getRegister());
+    int mark = output.getCursor();
 
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("%04x: -local %s", address,
-                            entryAnnotationString(entry)));
-        }
+    output.writeByte(DBG_START_LOCAL_EXTENDED);
 
-        if (DEBUG) {
-            System.err.println("emit local end");
-        }
+    emitUnsignedLeb128(entry.getRegister());
+    emitStringIndex(entry.getName());
+    emitTypeIndex(entry.getType());
+    emitStringIndex(entry.getSignature());
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark,
+          String.format("%04x: +localx %s", address, entryAnnotationString(entry)));
     }
 
-    /**
-     * Emits the necessary byte sequences to emit the given position table
-     * entry. This will typically be a single special opcode, although
-     * it may also require DBG_ADVANCE_PC or DBG_ADVANCE_LINE.
-     *
-     * @param entry position entry to emit.
-     * @throws IOException
-     */
-    private void emitPosition(PositionList.Entry entry)
-            throws IOException {
+    if (DEBUG) {
+      System.err.println("emit local start");
+    }
+  }
 
-        SourcePosition pos = entry.getPosition();
-        int newLine = pos.getLine();
-        int newAddress = entry.getAddress();
+  /**
+   * Emits a {@link DebugInfoConstants#DBG_END_LOCAL DBG_END_LOCAL} sequence.
+   *
+   * @param entry {@code entry non-null;} entry associated with end.
+   * @throws IOException
+   */
+  private void emitLocalEnd(LocalList.Entry entry) throws IOException {
 
-        int opcode;
+    int mark = output.getCursor();
 
-        int deltaLines = newLine - line;
-        int deltaAddress = newAddress - address;
+    output.writeByte(DBG_END_LOCAL);
+    output.writeUleb128(entry.getRegister());
 
-        if (deltaAddress < 0) {
-            throw new RuntimeException(
-                    "Position entries must be in ascending address order");
-        }
-
-        if ((deltaLines < DBG_LINE_BASE)
-                || (deltaLines > (DBG_LINE_BASE + DBG_LINE_RANGE -1))) {
-            emitAdvanceLine(deltaLines);
-            deltaLines = 0;
-        }
-
-        opcode = computeOpcode (deltaLines, deltaAddress);
-
-        if ((opcode & ~0xff) > 0) {
-            emitAdvancePc(deltaAddress);
-            deltaAddress = 0;
-            opcode = computeOpcode (deltaLines, deltaAddress);
-
-            if ((opcode & ~0xff) > 0) {
-                emitAdvanceLine(deltaLines);
-                deltaLines = 0;
-                opcode = computeOpcode (deltaLines, deltaAddress);
-            }
-        }
-
-        output.writeByte(opcode);
-
-        line += deltaLines;
-        address += deltaAddress;
-
-        if (annotateTo != null || debugPrint != null) {
-            annotate(1,
-                    String.format("%04x: line %d", address, line));
-        }
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark,
+          String.format("%04x: -local %s", address, entryAnnotationString(entry)));
     }
 
-    /**
-     * Computes a special opcode that will encode the given position change.
-     * If the return value is > 0xff, then the request cannot be fulfilled.
-     * Essentially the same as described in "DWARF Debugging Format Version 3"
-     * section 6.2.5.1.
-     *
-     * @param deltaLines {@code >= DBG_LINE_BASE, <= DBG_LINE_BASE +
-     * DBG_LINE_RANGE;} the line change to encode
-     * @param deltaAddress {@code >= 0;} the address change to encode
-     * @return {@code <= 0xff} if in range, otherwise parameters are out
-     * of range
-     */
-    private static int computeOpcode(int deltaLines, int deltaAddress) {
-        if (deltaLines < DBG_LINE_BASE
-                || deltaLines > (DBG_LINE_BASE + DBG_LINE_RANGE -1)) {
+    if (DEBUG) {
+      System.err.println("emit local end");
+    }
+  }
 
-            throw new RuntimeException("Parameter out of range");
-        }
+  /**
+   * Emits the necessary byte sequences to emit the given position table
+   * entry. This will typically be a single special opcode, although
+   * it may also require DBG_ADVANCE_PC or DBG_ADVANCE_LINE.
+   *
+   * @param entry position entry to emit.
+   * @throws IOException
+   */
+  private void emitPosition(PositionList.Entry entry) throws IOException {
 
-        return (deltaLines - DBG_LINE_BASE)
-            + (DBG_LINE_RANGE * deltaAddress) + DBG_FIRST_SPECIAL;
+    SourcePosition pos = entry.getPosition();
+    int newLine = pos.getLine();
+    int newAddress = entry.getAddress();
+
+    int opcode;
+
+    int deltaLines = newLine - line;
+    int deltaAddress = newAddress - address;
+
+    if (deltaAddress < 0) {
+      throw new RuntimeException("Position entries must be in ascending address order");
     }
 
-    /**
-     * Emits an {@link DebugInfoConstants#DBG_ADVANCE_LINE DBG_ADVANCE_LINE}
-     * sequence.
-     *
-     * @param deltaLines amount to change line number register by
-     * @throws IOException
-     */
-    private void emitAdvanceLine(int deltaLines) throws IOException {
-        int mark = output.getCursor();
-
-        output.writeByte(DBG_ADVANCE_LINE);
-        output.writeSleb128(deltaLines);
-        line += deltaLines;
-
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("line = %d", line));
-        }
-
-        if (DEBUG) {
-            System.err.printf("Emitting advance_line for %d\n", deltaLines);
-        }
+    if ((deltaLines < DBG_LINE_BASE) || (deltaLines > (DBG_LINE_BASE + DBG_LINE_RANGE - 1))) {
+      emitAdvanceLine(deltaLines);
+      deltaLines = 0;
     }
 
-    /**
-     * Emits an  {@link DebugInfoConstants#DBG_ADVANCE_PC DBG_ADVANCE_PC}
-     * sequence.
-     *
-     * @param deltaAddress {@code >= 0;} amount to change program counter by
-     * @throws IOException
-     */
-    private void emitAdvancePc(int deltaAddress) throws IOException {
-        int mark = output.getCursor();
+    opcode = computeOpcode(deltaLines, deltaAddress);
 
-        output.writeByte(DBG_ADVANCE_PC);
-        output.writeUleb128(deltaAddress);
-        address += deltaAddress;
+    if ((opcode & ~0xff) > 0) {
+      emitAdvancePc(deltaAddress);
+      deltaAddress = 0;
+      opcode = computeOpcode(deltaLines, deltaAddress);
 
-        if (annotateTo != null || debugPrint != null) {
-            annotate(output.getCursor() - mark,
-                    String.format("%04x: advance pc", address));
-        }
-
-        if (DEBUG) {
-            System.err.printf("Emitting advance_pc for %d\n", deltaAddress);
-        }
+      if ((opcode & ~0xff) > 0) {
+        emitAdvanceLine(deltaLines);
+        deltaLines = 0;
+        opcode = computeOpcode(deltaLines, deltaAddress);
+      }
     }
 
-    /**
-     * Emits an unsigned LEB128 value.
-     *
-     * @param n {@code >= 0;} value to emit. Note that, although this can
-     * represent integers larger than Integer.MAX_VALUE, we currently don't
-     * allow that.
-     * @throws IOException
-     */
-    private void emitUnsignedLeb128(int n) throws IOException {
-        // We'll never need the top end of the unsigned range anyway.
-        if (n < 0) {
-            throw new RuntimeException(
-                    "Signed value where unsigned required: " + n);
-        }
+    output.writeByte(opcode);
 
-        output.writeUleb128(n);
+    line += deltaLines;
+    address += deltaAddress;
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(1, String.format("%04x: line %d", address, line));
+    }
+  }
+
+  /**
+   * Computes a special opcode that will encode the given position change.
+   * If the return value is > 0xff, then the request cannot be fulfilled.
+   * Essentially the same as described in "DWARF Debugging Format Version 3"
+   * section 6.2.5.1.
+   *
+   * @param deltaLines {@code >= DBG_LINE_BASE, <= DBG_LINE_BASE +
+   * DBG_LINE_RANGE;} the line change to encode
+   * @param deltaAddress {@code >= 0;} the address change to encode
+   * @return {@code <= 0xff} if in range, otherwise parameters are out
+   * of range
+   */
+  private static int computeOpcode(int deltaLines, int deltaAddress) {
+    if (deltaLines < DBG_LINE_BASE || deltaLines > (DBG_LINE_BASE + DBG_LINE_RANGE - 1)) {
+
+      throw new RuntimeException("Parameter out of range");
     }
 
-    /**
-     * Emits the {@link DebugInfoConstants#DBG_END_SEQUENCE DBG_END_SEQUENCE}
-     * bytecode.
-     */
-    private void emitEndSequence() {
-        output.writeByte(DBG_END_SEQUENCE);
+    return (deltaLines - DBG_LINE_BASE) + (DBG_LINE_RANGE * deltaAddress) + DBG_FIRST_SPECIAL;
+  }
 
-        if (annotateTo != null || debugPrint != null) {
-            annotate(1, "end sequence");
-        }
+  /**
+   * Emits an {@link DebugInfoConstants#DBG_ADVANCE_LINE DBG_ADVANCE_LINE}
+   * sequence.
+   *
+   * @param deltaLines amount to change line number register by
+   * @throws IOException
+   */
+  private void emitAdvanceLine(int deltaLines) throws IOException {
+    int mark = output.getCursor();
+
+    output.writeByte(DBG_ADVANCE_LINE);
+    output.writeSleb128(deltaLines);
+    line += deltaLines;
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark, String.format("line = %d", line));
     }
+
+    if (DEBUG) {
+      System.err.printf("Emitting advance_line for %d\n", deltaLines);
+    }
+  }
+
+  /**
+   * Emits an  {@link DebugInfoConstants#DBG_ADVANCE_PC DBG_ADVANCE_PC}
+   * sequence.
+   *
+   * @param deltaAddress {@code >= 0;} amount to change program counter by
+   * @throws IOException
+   */
+  private void emitAdvancePc(int deltaAddress) throws IOException {
+    int mark = output.getCursor();
+
+    output.writeByte(DBG_ADVANCE_PC);
+    output.writeUleb128(deltaAddress);
+    address += deltaAddress;
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(output.getCursor() - mark, String.format("%04x: advance pc", address));
+    }
+
+    if (DEBUG) {
+      System.err.printf("Emitting advance_pc for %d\n", deltaAddress);
+    }
+  }
+
+  /**
+   * Emits an unsigned LEB128 value.
+   *
+   * @param n {@code >= 0;} value to emit. Note that, although this can
+   * represent integers larger than Integer.MAX_VALUE, we currently don't
+   * allow that.
+   * @throws IOException
+   */
+  private void emitUnsignedLeb128(int n) throws IOException {
+    // We'll never need the top end of the unsigned range anyway.
+    if (n < 0) {
+      throw new RuntimeException("Signed value where unsigned required: " + n);
+    }
+
+    output.writeUleb128(n);
+  }
+
+  /**
+   * Emits the {@link DebugInfoConstants#DBG_END_SEQUENCE DBG_END_SEQUENCE}
+   * bytecode.
+   */
+  private void emitEndSequence() {
+    output.writeByte(DBG_END_SEQUENCE);
+
+    if (annotateTo != null || debugPrint != null) {
+      annotate(1, "end sequence");
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/DebugInfoItem.java b/dx/src/com/android/jack/dx/dex/file/DebugInfoItem.java
index 61db8d9..8f5ceb6 100644
--- a/dx/src/com/android/jack/dx/dex/file/DebugInfoItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/DebugInfoItem.java
@@ -26,169 +26,168 @@
 
 import java.io.PrintWriter;
 
+/**
+ * TODO(jack team)
+ */
 public class DebugInfoItem extends OffsettedItem {
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 1;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 1;
 
-    private static final boolean ENABLE_ENCODER_SELF_CHECK = false;
+  private static boolean enableEncoderSelfCheck = false;
 
-    /** {@code non-null;} the code this item represents */
-    private final DalvCode code;
+  /** {@code non-null;} the code this item represents */
+  private final DalvCode code;
 
-    private byte[] encoded;
+  private byte[] encoded;
 
-    private final boolean isStatic;
-    private final CstMethodRef ref;
+  private final boolean isStatic;
+  private final CstMethodRef ref;
 
-    public DebugInfoItem(DalvCode code, boolean isStatic, CstMethodRef ref) {
-        // We don't know the write size yet.
-        super (ALIGNMENT, -1);
+  public DebugInfoItem(DalvCode code, boolean isStatic, CstMethodRef ref) {
+    // We don't know the write size yet.
+    super(ALIGNMENT, -1);
 
-        if (code == null) {
-            throw new NullPointerException("code == null");
-        }
-
-        this.code = code;
-        this.isStatic = isStatic;
-        this.ref = ref;
+    if (code == null) {
+      throw new NullPointerException("code == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_DEBUG_INFO_ITEM;
+    this.code = code;
+    this.isStatic = isStatic;
+    this.ref = ref;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_DEBUG_INFO_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    // No contents to add.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // Encode the data and note the size.
+
+    try {
+      encoded = encode(addedTo.getFile(), null, null, null, false);
+      setWriteSize(encoded.length);
+    } catch (RuntimeException ex) {
+      throw ExceptionWithContext.withContext(ex,
+          "...while placing debug info for " + ref.toHuman());
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    throw new RuntimeException("unsupported");
+  }
+
+  /**
+   * Writes annotations for the elements of this list, as
+   * zero-length. This is meant to be used for dumping this instance
+   * directly after a code dump (with the real local list actually
+   * existing elsewhere in the output).
+   *
+   * @param file {@code non-null;} the file to use for referencing other sections
+   * @param out {@code non-null;} where to annotate to
+   * @param prefix {@code null-ok;} prefix to attach to each line of output
+   */
+  public void annotateTo(DexFile file, AnnotatedOutput out, String prefix) {
+    encode(file, prefix, null, out, false);
+  }
+
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param prefix {@code non-null;} prefix to attach to each line of output
+   */
+  public void debugPrint(PrintWriter out, String prefix) {
+    encode(null, prefix, out, null, false);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    if (out.annotates()) {
+      /*
+       * Re-run the encoder to generate the annotations,
+       * but write the bits from the original encode
+       */
+
+out.annotate(offsetString() + " debug info");
+      encode(file, null, null, out, true);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        // No contents to add.
+    out.write(encoded);
+  }
+
+  /**
+   * Performs debug info encoding.
+   *
+   * @param file {@code null-ok;} file to refer to during encoding
+   * @param prefix {@code null-ok;} prefix to attach to each line of output
+   * @param debugPrint {@code null-ok;} if specified, an alternate output for
+   * annotations
+   * @param out {@code null-ok;} if specified, where annotations should go
+   * @param consume whether to claim to have consumed output for
+   * {@code out}
+   * @return {@code non-null;} the encoded array
+   */
+  private byte[] encode(DexFile file, String prefix, PrintWriter debugPrint, AnnotatedOutput out,
+      boolean consume) {
+    byte[] result = encode0(file, prefix, debugPrint, out, consume);
+
+    if (enableEncoderSelfCheck && (file != null)) {
+      try {
+        DebugInfoDecoder.validateEncode(result, file, ref, code, isStatic);
+      } catch (RuntimeException ex) {
+        // Reconvert, annotating to System.err.
+        encode0(file, "", new PrintWriter(System.err, true), null, false);
+        throw ex;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // Encode the data and note the size.
+    return result;
+  }
 
-        try {
-            encoded = encode(addedTo.getFile(), null, null, null, false);
-            setWriteSize(encoded.length);
-        } catch (RuntimeException ex) {
-            throw ExceptionWithContext.withContext(ex,
-                    "...while placing debug info for " + ref.toHuman());
-        }
+  /**
+   * Helper for {@link #encode} to do most of the work.
+   *
+   * @param file {@code null-ok;} file to refer to during encoding
+   * @param prefix {@code null-ok;} prefix to attach to each line of output
+   * @param debugPrint {@code null-ok;} if specified, an alternate output for
+   * annotations
+   * @param out {@code null-ok;} if specified, where annotations should go
+   * @param consume whether to claim to have consumed output for
+   * {@code out}
+   * @return {@code non-null;} the encoded array
+   */
+  private byte[] encode0(DexFile file, String prefix, PrintWriter debugPrint, AnnotatedOutput out,
+      boolean consume) {
+    PositionList positions = code.getPositions();
+    LocalList locals = code.getLocals();
+    DalvInsnList insns = code.getInsns();
+    int codeSize = insns.codeSize();
+    int regSize = insns.getRegistersSize();
+
+    DebugInfoEncoder encoder =
+        new DebugInfoEncoder(positions, locals, file, codeSize, regSize, isStatic, ref);
+
+    byte[] result;
+
+    if ((debugPrint == null) && (out == null)) {
+      result = encoder.convert();
+    } else {
+      result = encoder.convertAndAnnotate(prefix, debugPrint, out, consume);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        throw new RuntimeException("unsupported");
-    }
-
-    /**
-     * Writes annotations for the elements of this list, as
-     * zero-length. This is meant to be used for dumping this instance
-     * directly after a code dump (with the real local list actually
-     * existing elsewhere in the output).
-     *
-     * @param file {@code non-null;} the file to use for referencing other sections
-     * @param out {@code non-null;} where to annotate to
-     * @param prefix {@code null-ok;} prefix to attach to each line of output
-     */
-    public void annotateTo(DexFile file, AnnotatedOutput out, String prefix) {
-        encode(file, prefix, null, out, false);
-    }
-
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param prefix {@code non-null;} prefix to attach to each line of output
-     */
-    public void debugPrint(PrintWriter out, String prefix) {
-        encode(null, prefix, out, null, false);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        if (out.annotates()) {
-            /*
-             * Re-run the encoder to generate the annotations,
-             * but write the bits from the original encode
-             */
-
-            out.annotate(offsetString() + " debug info");
-            encode(file, null, null, out, true);
-        }
-
-        out.write(encoded);
-    }
-
-    /**
-     * Performs debug info encoding.
-     *
-     * @param file {@code null-ok;} file to refer to during encoding
-     * @param prefix {@code null-ok;} prefix to attach to each line of output
-     * @param debugPrint {@code null-ok;} if specified, an alternate output for
-     * annotations
-     * @param out {@code null-ok;} if specified, where annotations should go
-     * @param consume whether to claim to have consumed output for
-     * {@code out}
-     * @return {@code non-null;} the encoded array
-     */
-    private byte[] encode(DexFile file, String prefix, PrintWriter debugPrint,
-            AnnotatedOutput out, boolean consume) {
-        byte[] result = encode0(file, prefix, debugPrint, out, consume);
-
-        if (ENABLE_ENCODER_SELF_CHECK && (file != null)) {
-            try {
-                DebugInfoDecoder.validateEncode(result, file, ref, code,
-                        isStatic);
-            } catch (RuntimeException ex) {
-                // Reconvert, annotating to System.err.
-                encode0(file, "", new PrintWriter(System.err, true), null,
-                        false);
-                throw ex;
-            }
-        }
-
-        return result;
-    }
-
-    /**
-     * Helper for {@link #encode} to do most of the work.
-     *
-     * @param file {@code null-ok;} file to refer to during encoding
-     * @param prefix {@code null-ok;} prefix to attach to each line of output
-     * @param debugPrint {@code null-ok;} if specified, an alternate output for
-     * annotations
-     * @param out {@code null-ok;} if specified, where annotations should go
-     * @param consume whether to claim to have consumed output for
-     * {@code out}
-     * @return {@code non-null;} the encoded array
-     */
-    private byte[] encode0(DexFile file, String prefix, PrintWriter debugPrint,
-            AnnotatedOutput out, boolean consume) {
-        PositionList positions = code.getPositions();
-        LocalList locals = code.getLocals();
-        DalvInsnList insns = code.getInsns();
-        int codeSize = insns.codeSize();
-        int regSize = insns.getRegistersSize();
-
-        DebugInfoEncoder encoder =
-            new DebugInfoEncoder(positions, locals,
-                    file, codeSize, regSize, isStatic, ref);
-
-        byte[] result;
-
-        if ((debugPrint == null) && (out == null)) {
-            result = encoder.convert();
-        } else {
-            result = encoder.convertAndAnnotate(prefix, debugPrint, out,
-                    consume);
-        }
-
-        return result;
-    }
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/DexFile.java b/dx/src/com/android/jack/dx/dex/file/DexFile.java
index c0fa5b1..027cb25 100644
--- a/dx/src/com/android/jack/dx/dex/file/DexFile.java
+++ b/dx/src/com/android/jack/dx/dex/file/DexFile.java
@@ -17,6 +17,7 @@
 package com.android.jack.dx.dex.file;
 
 import com.android.jack.dx.dex.DexOptions;
+import com.android.jack.dx.dex.file.MixedItemSection.SortType;
 import com.android.jack.dx.rop.cst.Constant;
 import com.android.jack.dx.rop.cst.CstBaseMethodRef;
 import com.android.jack.dx.rop.cst.CstEnumRef;
@@ -37,642 +38,641 @@
 import java.util.List;
 import java.util.zip.Adler32;
 
-import static com.android.jack.dx.dex.file.MixedItemSection.SortType;
-
 /**
  * Representation of an entire {@code .dex} (Dalvik EXecutable)
  * file, which itself consists of a set of Dalvik classes.
  */
 public final class DexFile {
-    /** options controlling the creation of the file */
-    private DexOptions dexOptions;
+  /** options controlling the creation of the file */
+  private DexOptions dexOptions;
 
-    /** {@code non-null;} word data section */
-    private final MixedItemSection wordData;
+  /** {@code non-null;} word data section */
+  private final MixedItemSection wordData;
 
-    /**
-     * {@code non-null;} type lists section. This is word data, but separating
-     * it from {@link #wordData} helps break what would otherwise be a
-     * circular dependency between the that and {@link #protoIds}.
+  /**
+   * {@code non-null;} type lists section. This is word data, but separating
+   * it from {@link #wordData} helps break what would otherwise be a
+   * circular dependency between the that and {@link #protoIds}.
+   */
+  private final MixedItemSection typeLists;
+
+  /**
+   * {@code non-null;} map section. The map needs to be in a section by itself
+   * for the self-reference mechanics to work in a reasonably
+   * straightforward way. See {@link MapItem#addMap} for more detail.
+   */
+  private final MixedItemSection map;
+
+  /** {@code non-null;} string data section */
+  private final MixedItemSection stringData;
+
+  /** {@code non-null;} string identifiers section */
+  private final StringIdsSection stringIds;
+
+  /** {@code non-null;} type identifiers section */
+  private final TypeIdsSection typeIds;
+
+  /** {@code non-null;} prototype identifiers section */
+  private final ProtoIdsSection protoIds;
+
+  /** {@code non-null;} field identifiers section */
+  private final FieldIdsSection fieldIds;
+
+  /** {@code non-null;} method identifiers section */
+  private final MethodIdsSection methodIds;
+
+  /** {@code non-null;} class definitions section */
+  private final ClassDefsSection classDefs;
+
+  /** {@code non-null;} class data section */
+  private final MixedItemSection classData;
+
+  /** {@code non-null;} byte data section */
+  private final MixedItemSection byteData;
+
+  /** {@code non-null;} file header */
+  private final HeaderSection header;
+
+  /**
+   * {@code non-null;} array of sections in the order they will appear in the
+   * final output file
+   */
+  private final Section[] sections;
+
+  /** {@code >= -1;} total file size or {@code -1} if unknown */
+  private int fileSize;
+
+  /** {@code >= 40;} maximum width of the file dump */
+  private int dumpWidth;
+
+  /** List of constant index mapping that must be used to remap binary */
+  private List<CstIndexMap> cstIndexMaps;
+
+  public DexFile(DexOptions dexOptions, List<CstIndexMap> cstIndexMaps) {
+    this.cstIndexMaps = cstIndexMaps;
+    this.dexOptions = dexOptions;
+
+    header = new HeaderSection(this);
+    typeLists = new MixedItemSection(null, this, 4, SortType.NONE);
+    wordData = new MixedItemSection("word_data", this, 4, SortType.TYPE);
+    stringData = new MixedItemSection("string_data", this, 1, SortType.INSTANCE);
+    classData = new MixedItemSection(null, this, 1, SortType.NONE);
+    byteData = new MixedItemSection("byte_data", this, 1, SortType.TYPE);
+    stringIds = new StringIdsSection(this);
+    typeIds = new TypeIdsSection(this);
+    protoIds = new ProtoIdsSection(this);
+    fieldIds = new FieldIdsSection(this);
+    methodIds = new MethodIdsSection(this);
+    classDefs = new ClassDefsSection(this);
+    map = new MixedItemSection("map", this, 4, SortType.NONE);
+
+    /*
+     * This is the list of sections in the order they appear in
+     * the final output.
      */
-    private final MixedItemSection typeLists;
+    sections = new Section[] {header,
+        stringIds,
+        typeIds,
+        protoIds,
+        fieldIds,
+        methodIds,
+        classDefs,
+        wordData,
+        typeLists,
+        stringData,
+        byteData,
+        classData,
+        map};
 
-    /**
-     * {@code non-null;} map section. The map needs to be in a section by itself
-     * for the self-reference mechanics to work in a reasonably
-     * straightforward way. See {@link MapItem#addMap} for more detail.
-     */
-    private final MixedItemSection map;
+    fileSize = -1;
+    dumpWidth = 79;
+  }
 
-    /** {@code non-null;} string data section */
-    private final MixedItemSection stringData;
+  /**
+   * Constructs an instance. It is initially empty.
+   */
+  public DexFile(DexOptions dexOptions) {
+    this(dexOptions, null);
+  }
 
-    /** {@code non-null;} string identifiers section */
-    private final StringIdsSection stringIds;
+  /**
+   * Returns true if this dex doesn't contain any class defs.
+   */
+  public boolean isEmpty() {
+    return classDefs.items().isEmpty();
+  }
 
-    /** {@code non-null;} type identifiers section */
-    private final TypeIdsSection typeIds;
+  /**
+   * Gets the dex-creation options object.
+   */
+  public DexOptions getDexOptions() {
+    return dexOptions;
+  }
 
-    /** {@code non-null;} prototype identifiers section */
-    private final ProtoIdsSection protoIds;
+  /**
+   * Adds a class to this instance. It is illegal to attempt to add more
+   * than one class with the same name.
+   *
+   * @param clazz {@code non-null;} the class to add
+   */
+  public void add(ClassDefItem clazz) {
+    classDefs.add(clazz);
+  }
 
-    /** {@code non-null;} field identifiers section */
-    private final FieldIdsSection fieldIds;
+  /**
+   * Gets the class definition with the given name, if any.
+   *
+   * @param name {@code non-null;} the class name to look for
+   * @return {@code null-ok;} the class with the given name, or {@code null}
+   * if there is no such class
+   */
+  public ClassDefItem getClassOrNull(String name) {
+    try {
+      Type type = Type.internClassName(name);
+      return (ClassDefItem) classDefs.get(new CstType(type));
+    } catch (IllegalArgumentException ex) {
+      // Translate exception, per contract.
+      return null;
+    }
+  }
 
-    /** {@code non-null;} method identifiers section */
-    private final MethodIdsSection methodIds;
+  /**
+   * Writes the contents of this instance as either a binary or a
+   * human-readable form, or both.
+   *
+   * @param out {@code null-ok;} where to write to
+   * @param humanOut {@code null-ok;} where to write human-oriented output to
+   * @param verbose whether to be verbose when writing human-oriented output
+   */
+  public void writeTo(OutputStream out, Writer humanOut, boolean verbose) throws IOException {
+    boolean annotate = (humanOut != null);
+    ByteArrayAnnotatedOutput result = toDex0(annotate, verbose);
 
-    /** {@code non-null;} class definitions section */
-    private final ClassDefsSection classDefs;
-
-    /** {@code non-null;} class data section */
-    private final MixedItemSection classData;
-
-    /** {@code non-null;} byte data section */
-    private final MixedItemSection byteData;
-
-    /** {@code non-null;} file header */
-    private final HeaderSection header;
-
-    /**
-     * {@code non-null;} array of sections in the order they will appear in the
-     * final output file
-     */
-    private final Section[] sections;
-
-    /** {@code >= -1;} total file size or {@code -1} if unknown */
-    private int fileSize;
-
-    /** {@code >= 40;} maximum width of the file dump */
-    private int dumpWidth;
-
-    /** List of constant index mapping that must be used to remap binary */
-    private List<CstIndexMap> cstIndexMaps;
-
-    public DexFile(DexOptions dexOptions, List<CstIndexMap> cstIndexMaps) {
-      this.cstIndexMaps = cstIndexMaps;
-      this.dexOptions = dexOptions;
-
-      header = new HeaderSection(this);
-      typeLists = new MixedItemSection(null, this, 4, SortType.NONE);
-      wordData = new MixedItemSection("word_data", this, 4, SortType.TYPE);
-      stringData =
-          new MixedItemSection("string_data", this, 1, SortType.INSTANCE);
-      classData = new MixedItemSection(null, this, 1, SortType.NONE);
-      byteData = new MixedItemSection("byte_data", this, 1, SortType.TYPE);
-      stringIds = new StringIdsSection(this);
-      typeIds = new TypeIdsSection(this);
-      protoIds = new ProtoIdsSection(this);
-      fieldIds = new FieldIdsSection(this);
-      methodIds = new MethodIdsSection(this);
-      classDefs = new ClassDefsSection(this);
-      map = new MixedItemSection("map", this, 4, SortType.NONE);
-
-      /*
-       * This is the list of sections in the order they appear in
-       * the final output.
-       */
-      sections = new Section[] {
-          header, stringIds, typeIds, protoIds, fieldIds, methodIds,
-          classDefs, wordData, typeLists, stringData, byteData,
-          classData, map };
-
-      fileSize = -1;
-      dumpWidth = 79;
+    if (out != null) {
+      out.write(result.getArray());
     }
 
-    /**
-     * Constructs an instance. It is initially empty.
-     */
-    public DexFile(DexOptions dexOptions) {
-      this(dexOptions, null);
+    if (annotate) {
+      result.writeAnnotationsTo(humanOut);
+    }
+  }
+
+  /**
+   * Returns the contents of this instance as a {@code .dex} file,
+   * in {@code byte[]} form.
+   *
+   * @param humanOut {@code null-ok;} where to write human-oriented output to
+   * @param verbose whether to be verbose when writing human-oriented output
+   * @return {@code non-null;} a {@code .dex} file for this instance
+   */
+  public byte[] toDex(Writer humanOut, boolean verbose) throws IOException {
+    boolean annotate = (humanOut != null);
+    ByteArrayAnnotatedOutput result = toDex0(annotate, verbose);
+
+    if (annotate) {
+      result.writeAnnotationsTo(humanOut);
     }
 
-    /**
-     * Returns true if this dex doesn't contain any class defs.
-     */
-    public boolean isEmpty() {
-        return classDefs.items().isEmpty();
+    return result.getArray();
+  }
+
+  /**
+   * Sets the maximum width of the human-oriented dump of the instance.
+   *
+   * @param dumpWidth {@code >= 40;} the width
+   */
+  public void setDumpWidth(int dumpWidth) {
+    if (dumpWidth < 40) {
+      throw new IllegalArgumentException("dumpWidth < 40");
     }
 
-    /**
-     * Gets the dex-creation options object.
-     */
-    public DexOptions getDexOptions() {
-        return dexOptions;
+    this.dumpWidth = dumpWidth;
+  }
+
+  /**
+   * Gets the total file size, if known.
+   *
+   * <p>This is package-scope in order to allow
+   * the {@link HeaderSection} to set itself up properly.</p>
+   *
+   * @return {@code >= 0;} the total file size
+   * @throws RuntimeException thrown if the file size is not yet known
+   */
+  /*package*/int getFileSize() {
+    if (fileSize < 0) {
+      throw new RuntimeException("file size not yet known");
     }
 
-    /**
-     * Adds a class to this instance. It is illegal to attempt to add more
-     * than one class with the same name.
-     *
-     * @param clazz {@code non-null;} the class to add
+    return fileSize;
+  }
+
+  /**
+   * Gets the string data section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the string data section
+   */
+  /*package*/MixedItemSection getStringData() {
+    return stringData;
+  }
+
+  /**
+   * Gets the word data section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the word data section
+   */
+  /*package*/MixedItemSection getWordData() {
+    return wordData;
+  }
+
+  /**
+   * Gets the type lists section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the word data section
+   */
+  /*package*/MixedItemSection getTypeLists() {
+    return typeLists;
+  }
+
+  /**
+   * Gets the map section.
+   *
+   * <p>This is package-scope in order to allow the header section
+   * to query it.</p>
+   *
+   * @return {@code non-null;} the map section
+   */
+  /*package*/MixedItemSection getMap() {
+    return map;
+  }
+
+  /**
+   * Gets the string identifiers section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the string identifiers section
+   */
+  public StringIdsSection getStringIds() {
+    return stringIds;
+  }
+
+  /**
+   * Gets the class definitions section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the class definitions section
+   */
+  /*package*/ClassDefsSection getClassDefs() {
+    return classDefs;
+  }
+
+  /**
+   * Gets the class data section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the class data section
+   */
+  /*package*/MixedItemSection getClassData() {
+    return classData;
+  }
+
+  /**
+   * Gets the type identifiers section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the class identifiers section
+   */
+  public TypeIdsSection getTypeIds() {
+    return typeIds;
+  }
+
+  /**
+   * Gets the prototype identifiers section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the prototype identifiers section
+   */
+  /*package*/ProtoIdsSection getProtoIds() {
+    return protoIds;
+  }
+
+  /**
+   * Gets the field identifiers section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the field identifiers section
+   */
+  public FieldIdsSection getFieldIds() {
+    return fieldIds;
+  }
+
+  /**
+   * Gets the method identifiers section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the method identifiers section
+   */
+  public MethodIdsSection getMethodIds() {
+    return methodIds;
+  }
+
+  /**
+   * Gets the byte data section.
+   *
+   * <p>This is package-scope in order to allow
+   * the various {@link Item} instances to add items to the
+   * instance.</p>
+   *
+   * @return {@code non-null;} the byte data section
+   */
+  /*package*/MixedItemSection getByteData() {
+    return byteData;
+  }
+
+  /**
+   * Gets the first section of the file that is to be considered
+   * part of the data section.
+   *
+   * <p>This is package-scope in order to allow the header section
+   * to query it.</p>
+   *
+   * @return {@code non-null;} the section
+   */
+  /*package*/Section getFirstDataSection() {
+    return wordData;
+  }
+
+  /**
+   * Gets the last section of the file that is to be considered
+   * part of the data section.
+   *
+   * <p>This is package-scope in order to allow the header section
+   * to query it.</p>
+   *
+   * @return {@code non-null;} the section
+   */
+  /*package*/Section getLastDataSection() {
+    return map;
+  }
+
+  /**
+   * Interns the given constant in the appropriate section of this
+   * instance, or do nothing if the given constant isn't the sort
+   * that should be interned.
+   *
+   * @param cst {@code non-null;} constant to possibly intern
+   */
+  /*package*/void internIfAppropriate(Constant cst) {
+    if (cst instanceof CstString) {
+      stringIds.intern((CstString) cst);
+    } else if (cst instanceof CstType) {
+      typeIds.intern((CstType) cst);
+    } else if (cst instanceof CstBaseMethodRef) {
+      methodIds.intern((CstBaseMethodRef) cst);
+    } else if (cst instanceof CstFieldRef) {
+      fieldIds.intern((CstFieldRef) cst);
+    } else if (cst instanceof CstEnumRef) {
+      fieldIds.intern(((CstEnumRef) cst).getFieldRef());
+    } else if (cst == null) {
+      throw new NullPointerException("cst == null");
+    }
+  }
+
+  /**
+   * Gets the {@link IndexedItem} corresponding to the given constant,
+   * if it is a constant that has such a correspondence, or return
+   * {@code null} if it isn't such a constant. This will throw
+   * an exception if the given constant <i>should</i> have been found
+   * but wasn't.
+   *
+   * @param cst {@code non-null;} the constant to look up
+   * @return {@code null-ok;} its corresponding item, if it has a corresponding
+   * item, or {@code null} if it's not that sort of constant
+   */
+  public IndexedItem findItemOrNull(Constant cst) {
+    if (cst instanceof CstString) {
+      return stringIds.get(cst);
+    } else if (cst instanceof CstType) {
+      return typeIds.get(cst);
+    } else if (cst instanceof CstBaseMethodRef) {
+      return methodIds.get(cst);
+    } else if (cst instanceof CstFieldRef) {
+      return fieldIds.get(cst);
+    } else {
+      return null;
+    }
+  }
+
+  /**
+   * Returns the contents of this instance as a {@code .dex} file,
+   * in a {@link ByteArrayAnnotatedOutput} instance.
+   *
+   * @param annotate whether or not to keep annotations
+   * @param verbose if annotating, whether to be verbose
+   * @return {@code non-null;} a {@code .dex} file for this instance
+   */
+  private ByteArrayAnnotatedOutput toDex0(boolean annotate, boolean verbose) {
+    /*
+     * The following is ordered so that the prepare() calls which
+     * add items happen before the calls to the sections that get
+     * added to.
      */
-    public void add(ClassDefItem clazz) {
-        classDefs.add(clazz);
+
+if (cstIndexMaps != null) {
+      for (CstIndexMap cstIndexMap : cstIndexMaps) {
+        cstIndexMap.mergeConstantsIntoDexFile(this);
+      }
     }
 
-    /**
-     * Gets the class definition with the given name, if any.
-     *
-     * @param name {@code non-null;} the class name to look for
-     * @return {@code null-ok;} the class with the given name, or {@code null}
-     * if there is no such class
-     */
-    public ClassDefItem getClassOrNull(String name) {
-        try {
-            Type type = Type.internClassName(name);
-            return (ClassDefItem) classDefs.get(new CstType(type));
-        } catch (IllegalArgumentException ex) {
-            // Translate exception, per contract.
-            return null;
-        }
-    }
+    classDefs.prepare();
+    classData.prepare();
+    wordData.prepare();
+    byteData.prepare();
+    methodIds.prepare();
+    fieldIds.prepare();
+    protoIds.prepare();
+    typeLists.prepare();
+    typeIds.prepare();
+    stringIds.prepare();
+    stringData.prepare();
+    header.prepare();
 
-    /**
-     * Writes the contents of this instance as either a binary or a
-     * human-readable form, or both.
-     *
-     * @param out {@code null-ok;} where to write to
-     * @param humanOut {@code null-ok;} where to write human-oriented output to
-     * @param verbose whether to be verbose when writing human-oriented output
-     */
-    public void writeTo(OutputStream out, Writer humanOut, boolean verbose)
-        throws IOException {
-        boolean annotate = (humanOut != null);
-        ByteArrayAnnotatedOutput result = toDex0(annotate, verbose);
+    // Place the sections within the file.
 
-        if (out != null) {
-            out.write(result.getArray());
+    int count = sections.length;
+    int offset = 0;
+
+    for (int i = 0; i < count; i++) {
+      Section one = sections[i];
+      int placedAt = one.setFileOffset(offset);
+      if (placedAt < offset) {
+        throw new RuntimeException("bogus placement for section " + i);
+      }
+
+      try {
+        if (one == map) {
+          /*
+           * Inform the map of all the sections, and add it
+           * to the file. This can only be done after all
+           * the other items have been sorted and placed.
+           */
+          MapItem.addMap(sections, map);
+          map.prepare();
         }
 
-        if (annotate) {
-            result.writeAnnotationsTo(humanOut);
-        }
-    }
-
-    /**
-     * Returns the contents of this instance as a {@code .dex} file,
-     * in {@code byte[]} form.
-     *
-     * @param humanOut {@code null-ok;} where to write human-oriented output to
-     * @param verbose whether to be verbose when writing human-oriented output
-     * @return {@code non-null;} a {@code .dex} file for this instance
-     */
-    public byte[] toDex(Writer humanOut, boolean verbose)
-        throws IOException {
-        boolean annotate = (humanOut != null);
-        ByteArrayAnnotatedOutput result = toDex0(annotate, verbose);
-
-        if (annotate) {
-            result.writeAnnotationsTo(humanOut);
+        if (one instanceof MixedItemSection) {
+          /*
+           * Place the items of a MixedItemSection that just
+           * got placed.
+           */
+          ((MixedItemSection) one).placeItems();
         }
 
-        return result.getArray();
+        offset = placedAt + one.writeSize();
+      } catch (RuntimeException ex) {
+        throw ExceptionWithContext.withContext(ex, "...while writing section " + i);
+      }
     }
 
-    /**
-     * Sets the maximum width of the human-oriented dump of the instance.
-     *
-     * @param dumpWidth {@code >= 40;} the width
-     */
-    public void setDumpWidth(int dumpWidth) {
-        if (dumpWidth < 40) {
-            throw new IllegalArgumentException("dumpWidth < 40");
+    // Write out all the sections.
+
+    fileSize = offset;
+    byte[] barr = new byte[fileSize];
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(barr);
+
+    if (annotate) {
+      out.enableAnnotations(dumpWidth, verbose);
+    }
+
+    for (int i = 0; i < count; i++) {
+      try {
+        Section one = sections[i];
+        int zeroCount = one.getFileOffset() - out.getCursor();
+        if (zeroCount < 0) {
+          throw new ExceptionWithContext("excess write of " + (-zeroCount));
         }
-
-        this.dumpWidth = dumpWidth;
-    }
-
-    /**
-     * Gets the total file size, if known.
-     *
-     * <p>This is package-scope in order to allow
-     * the {@link HeaderSection} to set itself up properly.</p>
-     *
-     * @return {@code >= 0;} the total file size
-     * @throws RuntimeException thrown if the file size is not yet known
-     */
-    /*package*/ int getFileSize() {
-        if (fileSize < 0) {
-            throw new RuntimeException("file size not yet known");
-        }
-
-        return fileSize;
-    }
-
-    /**
-     * Gets the string data section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the string data section
-     */
-    /*package*/ MixedItemSection getStringData() {
-        return stringData;
-    }
-
-    /**
-     * Gets the word data section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the word data section
-     */
-    /*package*/ MixedItemSection getWordData() {
-        return wordData;
-    }
-
-    /**
-     * Gets the type lists section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the word data section
-     */
-    /*package*/ MixedItemSection getTypeLists() {
-        return typeLists;
-    }
-
-    /**
-     * Gets the map section.
-     *
-     * <p>This is package-scope in order to allow the header section
-     * to query it.</p>
-     *
-     * @return {@code non-null;} the map section
-     */
-    /*package*/ MixedItemSection getMap() {
-        return map;
-    }
-
-    /**
-     * Gets the string identifiers section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the string identifiers section
-     */
-    public StringIdsSection getStringIds() {
-        return stringIds;
-    }
-
-    /**
-     * Gets the class definitions section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the class definitions section
-     */
-    /*package*/ ClassDefsSection getClassDefs() {
-        return classDefs;
-    }
-
-    /**
-     * Gets the class data section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the class data section
-     */
-    /*package*/ MixedItemSection getClassData() {
-        return classData;
-    }
-
-    /**
-     * Gets the type identifiers section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the class identifiers section
-     */
-    public TypeIdsSection getTypeIds() {
-        return typeIds;
-    }
-
-    /**
-     * Gets the prototype identifiers section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the prototype identifiers section
-     */
-    /*package*/ ProtoIdsSection getProtoIds() {
-        return protoIds;
-    }
-
-    /**
-     * Gets the field identifiers section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the field identifiers section
-     */
-    public FieldIdsSection getFieldIds() {
-        return fieldIds;
-    }
-
-    /**
-     * Gets the method identifiers section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the method identifiers section
-     */
-    public MethodIdsSection getMethodIds() {
-        return methodIds;
-    }
-
-    /**
-     * Gets the byte data section.
-     *
-     * <p>This is package-scope in order to allow
-     * the various {@link Item} instances to add items to the
-     * instance.</p>
-     *
-     * @return {@code non-null;} the byte data section
-     */
-    /*package*/ MixedItemSection getByteData() {
-        return byteData;
-    }
-
-    /**
-     * Gets the first section of the file that is to be considered
-     * part of the data section.
-     *
-     * <p>This is package-scope in order to allow the header section
-     * to query it.</p>
-     *
-     * @return {@code non-null;} the section
-     */
-    /*package*/ Section getFirstDataSection() {
-        return wordData;
-    }
-
-    /**
-     * Gets the last section of the file that is to be considered
-     * part of the data section.
-     *
-     * <p>This is package-scope in order to allow the header section
-     * to query it.</p>
-     *
-     * @return {@code non-null;} the section
-     */
-    /*package*/ Section getLastDataSection() {
-        return map;
-    }
-
-    /**
-     * Interns the given constant in the appropriate section of this
-     * instance, or do nothing if the given constant isn't the sort
-     * that should be interned.
-     *
-     * @param cst {@code non-null;} constant to possibly intern
-     */
-    /*package*/ void internIfAppropriate(Constant cst) {
-        if (cst instanceof CstString) {
-            stringIds.intern((CstString) cst);
-        } else if (cst instanceof CstType) {
-            typeIds.intern((CstType) cst);
-        } else if (cst instanceof CstBaseMethodRef) {
-            methodIds.intern((CstBaseMethodRef) cst);
-        } else if (cst instanceof CstFieldRef) {
-            fieldIds.intern((CstFieldRef) cst);
-        } else if (cst instanceof CstEnumRef) {
-            fieldIds.intern(((CstEnumRef) cst).getFieldRef());
-        } else if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
-    }
-
-    /**
-     * Gets the {@link IndexedItem} corresponding to the given constant,
-     * if it is a constant that has such a correspondence, or return
-     * {@code null} if it isn't such a constant. This will throw
-     * an exception if the given constant <i>should</i> have been found
-     * but wasn't.
-     *
-     * @param cst {@code non-null;} the constant to look up
-     * @return {@code null-ok;} its corresponding item, if it has a corresponding
-     * item, or {@code null} if it's not that sort of constant
-     */
-    public IndexedItem findItemOrNull(Constant cst) {
-        if (cst instanceof CstString) {
-            return stringIds.get(cst);
-        } else if (cst instanceof CstType) {
-            return typeIds.get(cst);
-        } else if (cst instanceof CstBaseMethodRef) {
-            return methodIds.get(cst);
-        } else if (cst instanceof CstFieldRef) {
-            return fieldIds.get(cst);
+        out.writeZeroes(one.getFileOffset() - out.getCursor());
+        one.writeTo(out);
+      } catch (RuntimeException ex) {
+        ExceptionWithContext ec;
+        if (ex instanceof ExceptionWithContext) {
+          ec = (ExceptionWithContext) ex;
         } else {
-            return null;
+          ec = new ExceptionWithContext(ex);
         }
+        ec.addContext("...while writing section " + i);
+        throw ec;
+      }
     }
 
-    /**
-     * Returns the contents of this instance as a {@code .dex} file,
-     * in a {@link ByteArrayAnnotatedOutput} instance.
-     *
-     * @param annotate whether or not to keep annotations
-     * @param verbose if annotating, whether to be verbose
-     * @return {@code non-null;} a {@code .dex} file for this instance
-     */
-    private ByteArrayAnnotatedOutput toDex0(boolean annotate,
-            boolean verbose) {
-        /*
-         * The following is ordered so that the prepare() calls which
-         * add items happen before the calls to the sections that get
-         * added to.
-         */
-
-        if (cstIndexMaps != null) {
-          for (CstIndexMap cstIndexMap : cstIndexMaps) {
-            cstIndexMap.mergeConstantsIntoDexFile(this);
-          }
-        }
-
-        classDefs.prepare();
-        classData.prepare();
-        wordData.prepare();
-        byteData.prepare();
-        methodIds.prepare();
-        fieldIds.prepare();
-        protoIds.prepare();
-        typeLists.prepare();
-        typeIds.prepare();
-        stringIds.prepare();
-        stringData.prepare();
-        header.prepare();
-
-        // Place the sections within the file.
-
-        int count = sections.length;
-        int offset = 0;
-
-        for (int i = 0; i < count; i++) {
-            Section one = sections[i];
-            int placedAt = one.setFileOffset(offset);
-            if (placedAt < offset) {
-                throw new RuntimeException("bogus placement for section " + i);
-            }
-
-            try {
-                if (one == map) {
-                    /*
-                     * Inform the map of all the sections, and add it
-                     * to the file. This can only be done after all
-                     * the other items have been sorted and placed.
-                     */
-                    MapItem.addMap(sections, map);
-                    map.prepare();
-                }
-
-                if (one instanceof MixedItemSection) {
-                    /*
-                     * Place the items of a MixedItemSection that just
-                     * got placed.
-                     */
-                    ((MixedItemSection) one).placeItems();
-                }
-
-                offset = placedAt + one.writeSize();
-            } catch (RuntimeException ex) {
-                throw ExceptionWithContext.withContext(ex,
-                        "...while writing section " + i);
-            }
-        }
-
-        // Write out all the sections.
-
-        fileSize = offset;
-        byte[] barr = new byte[fileSize];
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(barr);
-
-        if (annotate) {
-            out.enableAnnotations(dumpWidth, verbose);
-        }
-
-        for (int i = 0; i < count; i++) {
-            try {
-                Section one = sections[i];
-                int zeroCount = one.getFileOffset() - out.getCursor();
-                if (zeroCount < 0) {
-                    throw new ExceptionWithContext("excess write of " +
-                            (-zeroCount));
-                }
-                out.writeZeroes(one.getFileOffset() - out.getCursor());
-                one.writeTo(out);
-            } catch (RuntimeException ex) {
-                ExceptionWithContext ec;
-                if (ex instanceof ExceptionWithContext) {
-                    ec = (ExceptionWithContext) ex;
-                } else {
-                    ec = new ExceptionWithContext(ex);
-                }
-                ec.addContext("...while writing section " + i);
-                throw ec;
-            }
-        }
-
-        if (out.getCursor() != fileSize) {
-            throw new RuntimeException("foreshortened write");
-        }
-
-        // Perform final bookkeeping.
-
-        calcSignature(barr);
-        calcChecksum(barr);
-
-        if (annotate) {
-            wordData.writeIndexAnnotation(out, ItemType.TYPE_CODE_ITEM,
-                    "\nmethod code index:\n\n");
-            getStatistics().writeAnnotation(out);
-            out.finishAnnotating();
-        }
-
-        return out;
+    if (out.getCursor() != fileSize) {
+      throw new RuntimeException("foreshortened write");
     }
 
-    /**
-     * Generates and returns statistics for all the items in the file.
-     *
-     * @return {@code non-null;} the statistics
-     */
-    public Statistics getStatistics() {
-        Statistics stats = new Statistics();
+    // Perform final bookkeeping.
 
-        for (Section s : sections) {
-            stats.addAll(s);
-        }
+    calcSignature(barr);
+    calcChecksum(barr);
 
-        return stats;
+    if (annotate) {
+      wordData.writeIndexAnnotation(out, ItemType.TYPE_CODE_ITEM, "\nmethod code index:\n\n");
+      getStatistics().writeAnnotation(out);
+      out.finishAnnotating();
     }
 
-    /**
-     * Calculates the signature for the {@code .dex} file in the
-     * given array, and modify the array to contain it.
-     *
-     * @param bytes {@code non-null;} the bytes of the file
-     */
-    private static void calcSignature(byte[] bytes) {
-        MessageDigest md;
+    return out;
+  }
 
-        try {
-            md = MessageDigest.getInstance("SHA-1");
-        } catch (NoSuchAlgorithmException ex) {
-            throw new RuntimeException(ex);
-        }
+  /**
+   * Generates and returns statistics for all the items in the file.
+   *
+   * @return {@code non-null;} the statistics
+   */
+  public Statistics getStatistics() {
+    Statistics stats = new Statistics();
 
-        md.update(bytes, 32, bytes.length - 32);
-
-        try {
-            int amt = md.digest(bytes, 12, 20);
-            if (amt != 20) {
-                throw new RuntimeException("unexpected digest write: " + amt +
-                                           " bytes");
-            }
-        } catch (DigestException ex) {
-            throw new RuntimeException(ex);
-        }
+    for (Section s : sections) {
+      stats.addAll(s);
     }
 
-    /**
-     * Calculates the checksum for the {@code .dex} file in the
-     * given array, and modify the array to contain it.
-     *
-     * @param bytes {@code non-null;} the bytes of the file
-     */
-    private static void calcChecksum(byte[] bytes) {
-        Adler32 a32 = new Adler32();
+    return stats;
+  }
 
-        a32.update(bytes, 12, bytes.length - 12);
+  /**
+   * Calculates the signature for the {@code .dex} file in the
+   * given array, and modify the array to contain it.
+   *
+   * @param bytes {@code non-null;} the bytes of the file
+   */
+  private static void calcSignature(byte[] bytes) {
+    MessageDigest md;
 
-        int sum = (int) a32.getValue();
-
-        bytes[8]  = (byte) sum;
-        bytes[9]  = (byte) (sum >> 8);
-        bytes[10] = (byte) (sum >> 16);
-        bytes[11] = (byte) (sum >> 24);
+    try {
+      md = MessageDigest.getInstance("SHA-1");
+    } catch (NoSuchAlgorithmException ex) {
+      throw new RuntimeException(ex);
     }
+
+    md.update(bytes, 32, bytes.length - 32);
+
+    try {
+      int amt = md.digest(bytes, 12, 20);
+      if (amt != 20) {
+        throw new RuntimeException("unexpected digest write: " + amt + " bytes");
+      }
+    } catch (DigestException ex) {
+      throw new RuntimeException(ex);
+    }
+  }
+
+  /**
+   * Calculates the checksum for the {@code .dex} file in the
+   * given array, and modify the array to contain it.
+   *
+   * @param bytes {@code non-null;} the bytes of the file
+   */
+  private static void calcChecksum(byte[] bytes) {
+    Adler32 a32 = new Adler32();
+
+    a32.update(bytes, 12, bytes.length - 12);
+
+    int sum = (int) a32.getValue();
+
+    bytes[8] = (byte) sum;
+    bytes[9] = (byte) (sum >> 8);
+    bytes[10] = (byte) (sum >> 16);
+    bytes[11] = (byte) (sum >> 24);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/EncodedArrayItem.java b/dx/src/com/android/jack/dx/dex/file/EncodedArrayItem.java
index b87b7cc..7bad073 100644
--- a/dx/src/com/android/jack/dx/dex/file/EncodedArrayItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/EncodedArrayItem.java
@@ -24,99 +24,100 @@
  * Encoded array of constant values.
  */
 public final class EncodedArrayItem extends OffsettedItem {
-    /** the required alignment for instances of this class */
-    private static final int ALIGNMENT = 1;
+  /** the required alignment for instances of this class */
+  private static final int ALIGNMENT = 1;
 
-    /** {@code non-null;} the array to represent */
-    private final CstArray array;
+  /** {@code non-null;} the array to represent */
+  private final CstArray array;
 
-    /**
-     * {@code null-ok;} encoded form, ready for writing to a file; set during
-     * {@link #place0}
+  /**
+   * {@code null-ok;} encoded form, ready for writing to a file; set during
+   * {@link #place0}
+   */
+  private byte[] encodedForm;
+
+  /**
+   * Constructs an instance.
+   *
+   * @param array {@code non-null;} array to represent
+   */
+  public EncodedArrayItem(CstArray array) {
+    /*
+     * The write size isn't known up-front because (the variable-lengthed)
+     * leb128 type is used to represent some things.
      */
-    private byte[] encodedForm;
+    super(ALIGNMENT, -1);
 
-    /**
-     * Constructs an instance.
-     *
-     * @param array {@code non-null;} array to represent
-     */
-    public EncodedArrayItem(CstArray array) {
-        /*
-         * The write size isn't known up-front because (the variable-lengthed)
-         * leb128 type is used to represent some things.
-         */
-        super(ALIGNMENT, -1);
-
-        if (array == null) {
-            throw new NullPointerException("array == null");
-        }
-
-        this.array = array;
-        this.encodedForm = null;
+    if (array == null) {
+      throw new NullPointerException("array == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_ENCODED_ARRAY_ITEM;
+    this.array = array;
+    this.encodedForm = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_ENCODED_ARRAY_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return array.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(OffsettedItem other) {
+    EncodedArrayItem otherArray = (EncodedArrayItem) other;
+
+    return array.compareTo(otherArray.array);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return array.toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    ValueEncoder.addContents(file, array);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    // Encode the data and note the size.
+
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
+    ValueEncoder encoder = new ValueEncoder(addedTo.getFile(), out);
+
+    encoder.writeArray(array, false);
+    encodedForm = out.toByteArray();
+    setWriteSize(encodedForm.length);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+
+    if (annotates) {
+      out.annotate(0, offsetString() + " encoded array");
+
+      /*
+       * The output is to be annotated, so redo the work previously
+       * done by place0(), except this time annotations will actually
+       * get emitted.
+       */
+      ValueEncoder encoder = new ValueEncoder(file, out);
+      encoder.writeArray(array, true);
+    } else {
+      out.write(encodedForm);
     }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return array.hashCode();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(OffsettedItem other) {
-        EncodedArrayItem otherArray = (EncodedArrayItem) other;
-
-        return array.compareTo(otherArray.array);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return array.toHuman();
-    }
-
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        ValueEncoder.addContents(file, array);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        // Encode the data and note the size.
-
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput();
-        ValueEncoder encoder = new ValueEncoder(addedTo.getFile(), out);
-
-        encoder.writeArray(array, false);
-        encodedForm = out.toByteArray();
-        setWriteSize(encodedForm.length);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-
-        if (annotates) {
-            out.annotate(0, offsetString() + " encoded array");
-
-            /*
-             * The output is to be annotated, so redo the work previously
-             * done by place0(), except this time annotations will actually
-             * get emitted.
-             */
-            ValueEncoder encoder = new ValueEncoder(file, out);
-            encoder.writeArray(array, true);
-        } else {
-            out.write(encodedForm);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/EncodedField.java b/dx/src/com/android/jack/dx/dex/file/EncodedField.java
index 29a6484..cc3d068 100644
--- a/dx/src/com/android/jack/dx/dex/file/EncodedField.java
+++ b/dx/src/com/android/jack/dx/dex/file/EncodedField.java
@@ -28,127 +28,126 @@
 /**
  * Representation of a field of a class, of any sort.
  */
-public final class EncodedField extends EncodedMember
-        implements Comparable<EncodedField> {
-    /** {@code non-null;} constant for the field */
-    private final CstFieldRef field;
+public final class EncodedField extends EncodedMember implements Comparable<EncodedField> {
+  /** {@code non-null;} constant for the field */
+  private final CstFieldRef field;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param field {@code non-null;} constant for the field
-     * @param accessFlags access flags
+  /**
+   * Constructs an instance.
+   *
+   * @param field {@code non-null;} constant for the field
+   * @param accessFlags access flags
+   */
+  public EncodedField(CstFieldRef field, int accessFlags) {
+    super(accessFlags);
+
+    if (field == null) {
+      throw new NullPointerException("field == null");
+    }
+
+    /*
+     * TODO(dx team): Maybe check accessFlags, at least for
+     * easily-checked stuff?
      */
-    public EncodedField(CstFieldRef field, int accessFlags) {
-        super(accessFlags);
 
-        if (field == null) {
-            throw new NullPointerException("field == null");
-        }
+this.field = field;
+  }
 
-        /*
-         * TODO: Maybe check accessFlags, at least for
-         * easily-checked stuff?
-         */
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return field.hashCode();
+  }
 
-        this.field = field;
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof EncodedField)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        return field.hashCode();
+    return compareTo((EncodedField) other) == 0;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * <p><b>Note:</b> This compares the method constants only,
+   * ignoring any associated code, because it should never be the
+   * case that two different items with the same method constant
+   * ever appear in the same list (or same file, even).</p>
+   */
+  @Override
+  public int compareTo(EncodedField other) {
+    return field.compareTo(other.field);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append(getClass().getName());
+    sb.append('{');
+    sb.append(Hex.u2(getAccessFlags()));
+    sb.append(' ');
+    sb.append(field);
+    sb.append('}');
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    FieldIdsSection fieldIds = file.getFieldIds();
+    fieldIds.intern(field);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public CstString getName() {
+    return field.getNat().getName();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return field.toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void debugPrint(PrintWriter out, boolean verbose) {
+    // TODO(dx team): Maybe put something better here?
+    out.println(toString());
+  }
+
+  /**
+   * Gets the constant for the field.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public CstFieldRef getRef() {
+    return field;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int encode(DexFile file, AnnotatedOutput out, int lastIndex, int dumpSeq) {
+    int fieldIdx = file.getFieldIds().indexOf(field);
+    int diff = fieldIdx - lastIndex;
+    int accessFlags = getAccessFlags();
+
+    if (out.annotates()) {
+      out.annotate(0, String.format("  [%x] %s", dumpSeq, field.toHuman()));
+      out.annotate(Leb128Utils.unsignedLeb128Size(diff), "    field_idx:    " + Hex.u4(fieldIdx));
+      out.annotate(Leb128Utils.unsignedLeb128Size(accessFlags),
+          "    access_flags: " + AccessFlags.fieldString(accessFlags));
     }
 
-    /** {@inheritDoc} */
-    public boolean equals(Object other) {
-        if (! (other instanceof EncodedField)) {
-            return false;
-        }
+    out.writeUleb128(diff);
+    out.writeUleb128(accessFlags);
 
-        return compareTo((EncodedField) other) == 0;
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * <p><b>Note:</b> This compares the method constants only,
-     * ignoring any associated code, because it should never be the
-     * case that two different items with the same method constant
-     * ever appear in the same list (or same file, even).</p>
-     */
-    public int compareTo(EncodedField other) {
-        return field.compareTo(other.field);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        sb.append(getClass().getName());
-        sb.append('{');
-        sb.append(Hex.u2(getAccessFlags()));
-        sb.append(' ');
-        sb.append(field);
-        sb.append('}');
-        return sb.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        FieldIdsSection fieldIds = file.getFieldIds();
-        fieldIds.intern(field);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public CstString getName() {
-        return field.getNat().getName();
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return field.toHuman();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void debugPrint(PrintWriter out, boolean verbose) {
-        // TODO: Maybe put something better here?
-        out.println(toString());
-    }
-
-    /**
-     * Gets the constant for the field.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public CstFieldRef getRef() {
-        return field;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int encode(DexFile file, AnnotatedOutput out,
-            int lastIndex, int dumpSeq) {
-        int fieldIdx = file.getFieldIds().indexOf(field);
-        int diff = fieldIdx - lastIndex;
-        int accessFlags = getAccessFlags();
-
-        if (out.annotates()) {
-            out.annotate(0, String.format("  [%x] %s", dumpSeq,
-                            field.toHuman()));
-            out.annotate(Leb128Utils.unsignedLeb128Size(diff),
-                    "    field_idx:    " + Hex.u4(fieldIdx));
-            out.annotate(Leb128Utils.unsignedLeb128Size(accessFlags),
-                    "    access_flags: " +
-                    AccessFlags.fieldString(accessFlags));
-        }
-
-        out.writeUleb128(diff);
-        out.writeUleb128(accessFlags);
-
-        return fieldIdx;
-    }
+    return fieldIdx;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/EncodedMember.java b/dx/src/com/android/jack/dx/dex/file/EncodedMember.java
index 6502d0f..0a1a962 100644
--- a/dx/src/com/android/jack/dx/dex/file/EncodedMember.java
+++ b/dx/src/com/android/jack/dx/dex/file/EncodedMember.java
@@ -27,60 +27,59 @@
  * purposes of encoding it inside a {@link ClassDataItem}.
  */
 public abstract class EncodedMember implements ToHuman {
-    /** access flags */
-    private final int accessFlags;
+  /** access flags */
+  private final int accessFlags;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param accessFlags access flags for the member
-     */
-    public EncodedMember(int accessFlags) {
-        this.accessFlags = accessFlags;
-    }
+  /**
+   * Constructs an instance.
+   *
+   * @param accessFlags access flags for the member
+   */
+  public EncodedMember(int accessFlags) {
+    this.accessFlags = accessFlags;
+  }
 
-    /**
-     * Gets the access flags.
-     *
-     * @return the access flags
-     */
-    public final int getAccessFlags() {
-        return accessFlags;
-    }
+  /**
+   * Gets the access flags.
+   *
+   * @return the access flags
+   */
+  public final int getAccessFlags() {
+    return accessFlags;
+  }
 
-    /**
-     * Gets the name.
-     *
-     * @return {@code non-null;} the name
-     */
-    public abstract CstString getName();
+  /**
+   * Gets the name.
+   *
+   * @return {@code non-null;} the name
+   */
+  public abstract CstString getName();
 
-    /**
-     * Does a human-friendly dump of this instance.
-     *
-     * @param out {@code non-null;} where to dump
-     * @param verbose whether to be verbose with the output
-     */
-    public abstract void debugPrint(PrintWriter out, boolean verbose);
+  /**
+   * Does a human-friendly dump of this instance.
+   *
+   * @param out {@code non-null;} where to dump
+   * @param verbose whether to be verbose with the output
+   */
+  public abstract void debugPrint(PrintWriter out, boolean verbose);
 
-    /**
-     * Populates a {@link DexFile} with items from within this instance.
-     *
-     * @param file {@code non-null;} the file to populate
-     */
-    public abstract void addContents(DexFile file);
+  /**
+   * Populates a {@link DexFile} with items from within this instance.
+   *
+   * @param file {@code non-null;} the file to populate
+   */
+  public abstract void addContents(DexFile file);
 
-    /**
-     * Encodes this instance to the given output.
-     *
-     * @param file {@code non-null;} file this instance is part of
-     * @param out {@code non-null;} where to write to
-     * @param lastIndex {@code >= 0;} the previous member index value encoded, or
-     * {@code 0} if this is the first element to encode
-     * @param dumpSeq {@code >= 0;} sequence number of this instance for
-     * annotation purposes
-     * @return {@code >= 0;} the member index value that was encoded
-     */
-    public abstract int encode(DexFile file, AnnotatedOutput out,
-            int lastIndex, int dumpSeq);
+  /**
+   * Encodes this instance to the given output.
+   *
+   * @param file {@code non-null;} file this instance is part of
+   * @param out {@code non-null;} where to write to
+   * @param lastIndex {@code >= 0;} the previous member index value encoded, or
+   * {@code 0} if this is the first element to encode
+   * @param dumpSeq {@code >= 0;} sequence number of this instance for
+   * annotation purposes
+   * @return {@code >= 0;} the member index value that was encoded
+   */
+  public abstract int encode(DexFile file, AnnotatedOutput out, int lastIndex, int dumpSeq);
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/EncodedMethod.java b/dx/src/com/android/jack/dx/dex/file/EncodedMethod.java
index 924a604..c75fa04 100644
--- a/dx/src/com/android/jack/dx/dex/file/EncodedMethod.java
+++ b/dx/src/com/android/jack/dx/dex/file/EncodedMethod.java
@@ -28,164 +28,157 @@
 /**
  * Class that representats a method of a class.
  */
-public final class EncodedMethod extends EncodedMember
-        implements Comparable<EncodedMethod> {
-    /** {@code non-null;} constant for the method */
-    private final CstMethodRef method;
+public final class EncodedMethod extends EncodedMember implements Comparable<EncodedMethod> {
+  /** {@code non-null;} constant for the method */
+  private final CstMethodRef method;
 
-    /**
-     * {@code null-ok;} code for the method, if the method is neither
-     * {@code abstract} nor {@code native}
+  /**
+   * {@code null-ok;} code for the method, if the method is neither
+   * {@code abstract} nor {@code native}
+   */
+  private final OffsettedItem code;
+
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} constant for the method
+   * @param accessFlags access flags
+   * @param code {@code null-ok;} code for the method, if it is neither
+   * {@code abstract} nor {@code native}
+   */
+  public EncodedMethod(CstMethodRef method, int accessFlags, OffsettedItem code) {
+    super(accessFlags);
+
+    assert code == null || code instanceof Code;
+
+    if (method == null) {
+      throw new NullPointerException("method == null");
+    }
+
+    this.method = method;
+
+    this.code = code;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof EncodedMethod)) {
+      return false;
+    }
+
+    return compareTo((EncodedMethod) other) == 0;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * <p><b>Note:</b> This compares the method constants only,
+   * ignoring any associated code, because it should never be the
+   * case that two different items with the same method constant
+   * ever appear in the same list (or same file, even).</p>
+   */
+  @Override
+  public int compareTo(EncodedMethod other) {
+    return method.compareTo(other.method);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append(getClass().getName());
+    sb.append('{');
+    sb.append(Hex.u2(getAccessFlags()));
+    sb.append(' ');
+    sb.append(method);
+
+    if (code != null) {
+      sb.append(' ');
+      sb.append(code);
+    }
+
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    MethodIdsSection methodIds = file.getMethodIds();
+    MixedItemSection wordData = file.getWordData();
+
+    methodIds.intern(method);
+
+    if (code != null) {
+      wordData.add(code);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final String toHuman() {
+    return method.toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final CstString getName() {
+    return method.getNat().getName();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void debugPrint(PrintWriter out, boolean verbose) {
+    if (code == null) {
+      out.println(getRef().toHuman() + ": abstract or native");
+    } else {
+      ((Code) code).debugPrint(out, "  ", verbose);
+    }
+  }
+
+  /**
+   * Gets the constant for the method.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public final CstMethodRef getRef() {
+    return method;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int encode(DexFile file, AnnotatedOutput out, int lastIndex, int dumpSeq) {
+    int methodIdx = file.getMethodIds().indexOf(method);
+    int diff = methodIdx - lastIndex;
+    int accessFlags = getAccessFlags();
+    int codeOff = OffsettedItem.getAbsoluteOffsetOr0(code);
+    boolean hasCode = (codeOff != 0);
+    boolean shouldHaveCode =
+        (accessFlags & (AccessFlags.ACC_ABSTRACT | AccessFlags.ACC_NATIVE)) == 0;
+
+    /*
+     * Verify that code appears if and only if a method is
+     * declared to have it.
      */
-    private final OffsettedItem code;
-
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} constant for the method
-     * @param accessFlags access flags
-     * @param code {@code null-ok;} code for the method, if it is neither
-     * {@code abstract} nor {@code native}
-     */
-    public EncodedMethod(CstMethodRef method, int accessFlags, OffsettedItem code) {
-        super(accessFlags);
-
-        assert code == null || code instanceof Code;
-
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        this.method = method;
-
-        this.code = code;
+    if (hasCode != shouldHaveCode) {
+      throw new UnsupportedOperationException("code vs. access_flags mismatch");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (! (other instanceof EncodedMethod)) {
-            return false;
-        }
-
-        return compareTo((EncodedMethod) other) == 0;
+    if (out.annotates()) {
+      out.annotate(0, String.format("  [%x] %s", dumpSeq, method.toHuman()));
+      out.annotate(Leb128Utils.unsignedLeb128Size(diff), "    method_idx:   " + Hex.u4(methodIdx));
+      out.annotate(Leb128Utils.unsignedLeb128Size(accessFlags),
+          "    access_flags: " + AccessFlags.methodString(accessFlags));
+      out.annotate(Leb128Utils.unsignedLeb128Size(codeOff), "    code_off:     " + Hex.u4(codeOff));
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * <p><b>Note:</b> This compares the method constants only,
-     * ignoring any associated code, because it should never be the
-     * case that two different items with the same method constant
-     * ever appear in the same list (or same file, even).</p>
-     */
-    @Override
-    public int compareTo(EncodedMethod other) {
-        return method.compareTo(other.method);
-    }
+    out.writeUleb128(diff);
+    out.writeUleb128(accessFlags);
+    out.writeUleb128(codeOff);
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        sb.append(getClass().getName());
-        sb.append('{');
-        sb.append(Hex.u2(getAccessFlags()));
-        sb.append(' ');
-        sb.append(method);
-
-        if (code != null) {
-            sb.append(' ');
-            sb.append(code);
-        }
-
-        sb.append('}');
-
-        return sb.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        MethodIdsSection methodIds = file.getMethodIds();
-        MixedItemSection wordData = file.getWordData();
-
-        methodIds.intern(method);
-
-        if (code != null) {
-            wordData.add(code);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final String toHuman() {
-        return method.toHuman();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final CstString getName() {
-        return method.getNat().getName();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void debugPrint(PrintWriter out, boolean verbose) {
-        if (code == null) {
-            out.println(getRef().toHuman() + ": abstract or native");
-        } else {
-            ((Code) code).debugPrint(out, "  ", verbose);
-        }
-    }
-
-    /**
-     * Gets the constant for the method.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public final CstMethodRef getRef() {
-        return method;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int encode(DexFile file, AnnotatedOutput out,
-            int lastIndex, int dumpSeq) {
-        int methodIdx = file.getMethodIds().indexOf(method);
-        int diff = methodIdx - lastIndex;
-        int accessFlags = getAccessFlags();
-        int codeOff = OffsettedItem.getAbsoluteOffsetOr0(code);
-        boolean hasCode = (codeOff != 0);
-        boolean shouldHaveCode = (accessFlags &
-                (AccessFlags.ACC_ABSTRACT | AccessFlags.ACC_NATIVE)) == 0;
-
-        /*
-         * Verify that code appears if and only if a method is
-         * declared to have it.
-         */
-        if (hasCode != shouldHaveCode) {
-            throw new UnsupportedOperationException(
-                    "code vs. access_flags mismatch");
-        }
-
-        if (out.annotates()) {
-            out.annotate(0, String.format("  [%x] %s", dumpSeq,
-                            method.toHuman()));
-            out.annotate(Leb128Utils.unsignedLeb128Size(diff),
-                    "    method_idx:   " + Hex.u4(methodIdx));
-            out.annotate(Leb128Utils.unsignedLeb128Size(accessFlags),
-                    "    access_flags: " +
-                    AccessFlags.methodString(accessFlags));
-            out.annotate(Leb128Utils.unsignedLeb128Size(codeOff),
-                    "    code_off:     " + Hex.u4(codeOff));
-        }
-
-        out.writeUleb128(diff);
-        out.writeUleb128(accessFlags);
-        out.writeUleb128(codeOff);
-
-        return methodIdx;
-    }
+    return methodIdx;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/FieldAnnotationStruct.java b/dx/src/com/android/jack/dx/dex/file/FieldAnnotationStruct.java
index 8d11f73..afe4c56 100644
--- a/dx/src/com/android/jack/dx/dex/file/FieldAnnotationStruct.java
+++ b/dx/src/com/android/jack/dx/dex/file/FieldAnnotationStruct.java
@@ -25,98 +25,99 @@
 /**
  * Association of a field and its annotations.
  */
-public final class FieldAnnotationStruct
-        implements ToHuman, Comparable<FieldAnnotationStruct> {
-    /** {@code non-null;} the field in question */
-    private final CstFieldRef field;
+public final class FieldAnnotationStruct implements ToHuman, Comparable<FieldAnnotationStruct> {
+  /** {@code non-null;} the field in question */
+  private final CstFieldRef field;
 
-    /** {@code non-null;} the associated annotations */
-    private AnnotationSetItem annotations;
+  /** {@code non-null;} the associated annotations */
+  private AnnotationSetItem annotations;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param field {@code non-null;} the field in question
-     * @param annotations {@code non-null;} the associated annotations
-     */
-    public FieldAnnotationStruct(CstFieldRef field,
-            AnnotationSetItem annotations) {
-        if (field == null) {
-            throw new NullPointerException("field == null");
-        }
-
-        if (annotations == null) {
-            throw new NullPointerException("annotations == null");
-        }
-
-        this.field = field;
-        this.annotations = annotations;
+  /**
+   * Constructs an instance.
+   *
+   * @param field {@code non-null;} the field in question
+   * @param annotations {@code non-null;} the associated annotations
+   */
+  public FieldAnnotationStruct(CstFieldRef field, AnnotationSetItem annotations) {
+    if (field == null) {
+      throw new NullPointerException("field == null");
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        return field.hashCode();
+    if (annotations == null) {
+      throw new NullPointerException("annotations == null");
     }
 
-    /** {@inheritDoc} */
-    public boolean equals(Object other) {
-        if (! (other instanceof FieldAnnotationStruct)) {
-            return false;
-        }
+    this.field = field;
+    this.annotations = annotations;
+  }
 
-        return field.equals(((FieldAnnotationStruct) other).field);
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return field.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof FieldAnnotationStruct)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(FieldAnnotationStruct other) {
-        return field.compareTo(other.field);
+    return field.equals(((FieldAnnotationStruct) other).field);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(FieldAnnotationStruct other) {
+    return field.compareTo(other.field);
+  }
+
+  /** {@inheritDoc} */
+  public void addContents(DexFile file) {
+    FieldIdsSection fieldIds = file.getFieldIds();
+    MixedItemSection wordData = file.getWordData();
+
+    fieldIds.intern(field);
+    annotations = wordData.intern(annotations);
+  }
+
+  /** {@inheritDoc} */
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int fieldIdx = file.getFieldIds().indexOf(field);
+    int annotationsOff = annotations.getAbsoluteOffset();
+
+    if (out.annotates()) {
+      out.annotate(0, "    " + field.toHuman());
+      out.annotate(4, "      field_idx:       " + Hex.u4(fieldIdx));
+      out.annotate(4, "      annotations_off: " + Hex.u4(annotationsOff));
     }
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        FieldIdsSection fieldIds = file.getFieldIds();
-        MixedItemSection wordData = file.getWordData();
+    out.writeInt(fieldIdx);
+    out.writeInt(annotationsOff);
+  }
 
-        fieldIds.intern(field);
-        annotations = wordData.intern(annotations);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return field.toHuman() + ": " + annotations;
+  }
 
-    /** {@inheritDoc} */
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int fieldIdx = file.getFieldIds().indexOf(field);
-        int annotationsOff = annotations.getAbsoluteOffset();
+  /**
+   * Gets the field this item is for.
+   *
+   * @return {@code non-null;} the field
+   */
+  public CstFieldRef getField() {
+    return field;
+  }
 
-        if (out.annotates()) {
-            out.annotate(0, "    " + field.toHuman());
-            out.annotate(4, "      field_idx:       " + Hex.u4(fieldIdx));
-            out.annotate(4, "      annotations_off: " +
-                    Hex.u4(annotationsOff));
-        }
-
-        out.writeInt(fieldIdx);
-        out.writeInt(annotationsOff);
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return field.toHuman() + ": " + annotations;
-    }
-
-    /**
-     * Gets the field this item is for.
-     *
-     * @return {@code non-null;} the field
-     */
-    public CstFieldRef getField() {
-        return field;
-    }
-
-    /**
-     * Gets the associated annotations.
-     *
-     * @return {@code non-null;} the annotations
-     */
-    public Annotations getAnnotations() {
-        return annotations.getAnnotations();
-    }
+  /**
+   * Gets the associated annotations.
+   *
+   * @return {@code non-null;} the annotations
+   */
+  public Annotations getAnnotations() {
+    return annotations.getAnnotations();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/FieldIdItem.java b/dx/src/com/android/jack/dx/dex/file/FieldIdItem.java
index 373ae6c..df58131 100644
--- a/dx/src/com/android/jack/dx/dex/file/FieldIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/FieldIdItem.java
@@ -22,49 +22,49 @@
  * Representation of a field reference inside a Dalvik file.
  */
 public final class FieldIdItem extends MemberIdItem {
-    /**
-     * Constructs an instance.
-     *
-     * @param field {@code non-null;} the constant for the field
-     */
-    public FieldIdItem(CstFieldRef field) {
-        super(field);
-    }
+  /**
+   * Constructs an instance.
+   *
+   * @param field {@code non-null;} the constant for the field
+   */
+  public FieldIdItem(CstFieldRef field) {
+    super(field);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_FIELD_ID_ITEM;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_FIELD_ID_ITEM;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        super.addContents(file);
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    super.addContents(file);
 
-        TypeIdsSection typeIds = file.getTypeIds();
-        typeIds.intern(getFieldRef().getType());
-    }
+    TypeIdsSection typeIds = file.getTypeIds();
+    typeIds.intern(getFieldRef().getType());
+  }
 
-    /**
-     * Gets the field constant.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public CstFieldRef getFieldRef() {
-        return (CstFieldRef) getRef();
-    }
+  /**
+   * Gets the field constant.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public CstFieldRef getFieldRef() {
+    return (CstFieldRef) getRef();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int getTypoidIdx(DexFile file) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        return typeIds.indexOf(getFieldRef().getType());
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int getTypoidIdx(DexFile file) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    return typeIds.indexOf(getFieldRef().getType());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String getTypoidName() {
-        return "type_idx";
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String getTypoidName() {
+    return "type_idx";
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/FieldIdsSection.java b/dx/src/com/android/jack/dx/dex/file/FieldIdsSection.java
index 66d30f4..d623b74 100644
--- a/dx/src/com/android/jack/dx/dex/file/FieldIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/FieldIdsSection.java
@@ -28,110 +28,110 @@
  * Field refs list section of a {@code .dex} file.
  */
 public final class FieldIdsSection extends MemberIdsSection {
-    /**
-     * {@code non-null;} map from field constants to {@link
-     * FieldIdItem} instances
-     */
-    private final TreeMap<CstFieldRef, FieldIdItem> fieldIds;
+  /**
+   * {@code non-null;} map from field constants to {@link
+   * FieldIdItem} instances
+   */
+  private final TreeMap<CstFieldRef, FieldIdItem> fieldIds;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public FieldIdsSection(DexFile file) {
-        super("field_ids", file);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public FieldIdsSection(DexFile file) {
+    super("field_ids", file);
 
-        fieldIds = new TreeMap<CstFieldRef, FieldIdItem>();
+    fieldIds = new TreeMap<CstFieldRef, FieldIdItem>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return fieldIds.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return fieldIds.values();
+    throwIfNotPrepared();
+
+    IndexedItem result = fieldIds.get(cst);
+
+    if (result == null) {
+      throw new IllegalArgumentException("not found");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
 
-        IndexedItem result = fieldIds.get((CstFieldRef) cst);
+    int sz = fieldIds.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
 
-        if (result == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return result;
+    if (out.annotates()) {
+      out.annotate(4, "field_ids_size:  " + Hex.u4(sz));
+      out.annotate(4, "field_ids_off:   " + Hex.u4(offset));
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
 
-        int sz = fieldIds.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
-
-        if (out.annotates()) {
-            out.annotate(4, "field_ids_size:  " + Hex.u4(sz));
-            out.annotate(4, "field_ids_off:   " + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+  /**
+   * Interns an element into this instance.
+   *
+   * @param field {@code non-null;} the reference to intern
+   * @return {@code non-null;} the interned reference
+   */
+  public FieldIdItem intern(CstFieldRef field) {
+    if (field == null) {
+      throw new NullPointerException("field == null");
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param field {@code non-null;} the reference to intern
-     * @return {@code non-null;} the interned reference
-     */
-    public FieldIdItem intern(CstFieldRef field) {
-        if (field == null) {
-            throw new NullPointerException("field == null");
-        }
+    throwIfPrepared();
 
-        throwIfPrepared();
+    FieldIdItem result = fieldIds.get(field);
 
-        FieldIdItem result = fieldIds.get(field);
-
-        if (result == null) {
-            result = new FieldIdItem(field);
-            fieldIds.put(field, result);
-        }
-
-        return result;
+    if (result == null) {
+      result = new FieldIdItem(field);
+      fieldIds.put(field, result);
     }
 
-    /**
-     * Gets the index of the given reference, which must have been added
-     * to this instance.
-     *
-     * @param ref {@code non-null;} the reference to look up
-     * @return {@code >= 0;} the reference's index
-     */
-    public int indexOf(CstFieldRef ref) {
-        if (ref == null) {
-            throw new NullPointerException("ref == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
-
-        FieldIdItem item = fieldIds.get(ref);
-
-        if (item == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return item.getIndex();
+  /**
+   * Gets the index of the given reference, which must have been added
+   * to this instance.
+   *
+   * @param ref {@code non-null;} the reference to look up
+   * @return {@code >= 0;} the reference's index
+   */
+  public int indexOf(CstFieldRef ref) {
+    if (ref == null) {
+      throw new NullPointerException("ref == null");
     }
+
+    throwIfNotPrepared();
+
+    FieldIdItem item = fieldIds.get(ref);
+
+    if (item == null) {
+      throw new IllegalArgumentException("not found");
+    }
+
+    return item.getIndex();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/HeaderItem.java b/dx/src/com/android/jack/dx/dex/file/HeaderItem.java
index 4846235..281b8b2 100644
--- a/dx/src/com/android/jack/dx/dex/file/HeaderItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/HeaderItem.java
@@ -26,90 +26,88 @@
  * File header section of a {@code .dex} file.
  */
 public final class HeaderItem extends IndexedItem {
-    /**
-     * Constructs an instance.
+  /**
+   * Constructs an instance.
+   */
+  public HeaderItem() {
+    // This space intentionally left blank.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_HEADER_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.HEADER_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    // Nothing to do here.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int mapOff = file.getMap().getFileOffset();
+    Section firstDataSection = file.getFirstDataSection();
+    Section lastDataSection = file.getLastDataSection();
+    int dataOff = firstDataSection.getFileOffset();
+    int dataSize = lastDataSection.getFileOffset() + lastDataSection.writeSize() - dataOff;
+
+    String magic = file.getDexOptions().getMagic();
+
+    if (out.annotates()) {
+      out.annotate(8, "magic: " + new CstString(magic).toQuoted());
+      out.annotate(4, "checksum");
+      out.annotate(20, "signature");
+      out.annotate(4, "file_size:       " + Hex.u4(file.getFileSize()));
+      out.annotate(4, "header_size:     " + Hex.u4(SizeOf.HEADER_ITEM));
+      out.annotate(4, "endian_tag:      " + Hex.u4(DexFormat.ENDIAN_TAG));
+      out.annotate(4, "link_size:       0");
+      out.annotate(4, "link_off:        0");
+      out.annotate(4, "map_off:         " + Hex.u4(mapOff));
+    }
+
+    // Write the magic number.
+    for (int i = 0; i < 8; i++) {
+      out.writeByte(magic.charAt(i));
+    }
+
+    // Leave space for the checksum and signature.
+    out.writeZeroes(24);
+
+    out.writeInt(file.getFileSize());
+    out.writeInt(SizeOf.HEADER_ITEM);
+    out.writeInt(DexFormat.ENDIAN_TAG);
+
+    /*
+     * Write zeroes for the link size and data, as the output
+     * isn't a staticly linked file.
      */
-    public HeaderItem() {
-        // This space intentionally left blank.
+    out.writeZeroes(8);
+
+    out.writeInt(mapOff);
+
+    // Write out each section's respective header part.
+    file.getStringIds().writeHeaderPart(out);
+    file.getTypeIds().writeHeaderPart(out);
+    file.getProtoIds().writeHeaderPart(out);
+    file.getFieldIds().writeHeaderPart(out);
+    file.getMethodIds().writeHeaderPart(out);
+    file.getClassDefs().writeHeaderPart(out);
+
+    if (out.annotates()) {
+      out.annotate(4, "data_size:       " + Hex.u4(dataSize));
+      out.annotate(4, "data_off:        " + Hex.u4(dataOff));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_HEADER_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.HEADER_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        // Nothing to do here.
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int mapOff = file.getMap().getFileOffset();
-        Section firstDataSection = file.getFirstDataSection();
-        Section lastDataSection = file.getLastDataSection();
-        int dataOff = firstDataSection.getFileOffset();
-        int dataSize = lastDataSection.getFileOffset() +
-            lastDataSection.writeSize() - dataOff;
-
-        String magic = file.getDexOptions().getMagic();
-
-        if (out.annotates()) {
-            out.annotate(8, "magic: " + new CstString(magic).toQuoted());
-            out.annotate(4, "checksum");
-            out.annotate(20, "signature");
-            out.annotate(4, "file_size:       " +
-                         Hex.u4(file.getFileSize()));
-            out.annotate(4, "header_size:     " + Hex.u4(SizeOf.HEADER_ITEM));
-            out.annotate(4, "endian_tag:      " + Hex.u4(DexFormat.ENDIAN_TAG));
-            out.annotate(4, "link_size:       0");
-            out.annotate(4, "link_off:        0");
-            out.annotate(4, "map_off:         " + Hex.u4(mapOff));
-        }
-
-        // Write the magic number.
-        for (int i = 0; i < 8; i++) {
-            out.writeByte(magic.charAt(i));
-        }
-
-        // Leave space for the checksum and signature.
-        out.writeZeroes(24);
-
-        out.writeInt(file.getFileSize());
-        out.writeInt(SizeOf.HEADER_ITEM);
-        out.writeInt(DexFormat.ENDIAN_TAG);
-
-        /*
-         * Write zeroes for the link size and data, as the output
-         * isn't a staticly linked file.
-         */
-        out.writeZeroes(8);
-
-        out.writeInt(mapOff);
-
-        // Write out each section's respective header part.
-        file.getStringIds().writeHeaderPart(out);
-        file.getTypeIds().writeHeaderPart(out);
-        file.getProtoIds().writeHeaderPart(out);
-        file.getFieldIds().writeHeaderPart(out);
-        file.getMethodIds().writeHeaderPart(out);
-        file.getClassDefs().writeHeaderPart(out);
-
-        if (out.annotates()) {
-            out.annotate(4, "data_size:       " + Hex.u4(dataSize));
-            out.annotate(4, "data_off:        " + Hex.u4(dataOff));
-        }
-
-        out.writeInt(dataSize);
-        out.writeInt(dataOff);
-    }
+    out.writeInt(dataSize);
+    out.writeInt(dataOff);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/HeaderSection.java b/dx/src/com/android/jack/dx/dex/file/HeaderSection.java
index e2043e6..a5df91b 100644
--- a/dx/src/com/android/jack/dx/dex/file/HeaderSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/HeaderSection.java
@@ -26,38 +26,38 @@
  * File header section of a {@code .dex} file.
  */
 public final class HeaderSection extends UniformItemSection {
-    /** {@code non-null;} the list of the one item in the section */
-    private final List<HeaderItem> list;
+  /** {@code non-null;} the list of the one item in the section */
+  private final List<HeaderItem> list;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public HeaderSection(DexFile file) {
-        super(null, file, 4);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public HeaderSection(DexFile file) {
+    super(null, file, 4);
 
-        HeaderItem item = new HeaderItem();
-        item.setIndex(0);
+    HeaderItem item = new HeaderItem();
+    item.setIndex(0);
 
-        this.list = Collections.singletonList(item);
-    }
+    this.list = Collections.singletonList(item);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        return null;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    return null;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return list;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return list;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        // Nothing to do here.
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    // Nothing to do here.
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/IdItem.java b/dx/src/com/android/jack/dx/dex/file/IdItem.java
index acf82c4..df27a71 100644
--- a/dx/src/com/android/jack/dx/dex/file/IdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/IdItem.java
@@ -22,40 +22,40 @@
  * Representation of a reference to an item inside a Dalvik file.
  */
 public abstract class IdItem extends IndexedItem {
-    /**
-     * {@code non-null;} the type constant for the defining class of
-     * the reference
-     */
-    private final CstType type;
+  /**
+   * {@code non-null;} the type constant for the defining class of
+   * the reference
+   */
+  private final CstType type;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param type {@code non-null;} the type constant for the defining
-     * class of the reference
-     */
-    public IdItem(CstType type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
-
-        this.type = type;
+  /**
+   * Constructs an instance.
+   *
+   * @param type {@code non-null;} the type constant for the defining
+   * class of the reference
+   */
+  public IdItem(CstType type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        typeIds.intern(type);
-    }
+    this.type = type;
+  }
 
-    /**
-     * Gets the type constant for the defining class of the
-     * reference.
-     *
-     * @return {@code non-null;} the type constant
-     */
-    public final CstType getDefiningClass() {
-        return type;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    typeIds.intern(type);
+  }
+
+  /**
+   * Gets the type constant for the defining class of the
+   * reference.
+   *
+   * @return {@code non-null;} the type constant
+   */
+  public final CstType getDefiningClass() {
+    return type;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ImportedCodeItem.java b/dx/src/com/android/jack/dx/dex/file/ImportedCodeItem.java
index c3d6fd1..0bf8a04 100644
--- a/dx/src/com/android/jack/dx/dex/file/ImportedCodeItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/ImportedCodeItem.java
@@ -16,16 +16,13 @@
 
 package com.android.jack.dx.dex.file;
 
-import java.io.PrintWriter;
-
 import com.android.jack.dx.io.Code;
-import com.android.jack.dx.io.CodeReader;
-import com.android.jack.dx.io.Opcodes;
 import com.android.jack.dx.io.Code.CatchHandler;
 import com.android.jack.dx.io.Code.Try;
+import com.android.jack.dx.io.CodeReader;
+import com.android.jack.dx.io.Opcodes;
 import com.android.jack.dx.io.instructions.DecodedInstruction;
 import com.android.jack.dx.io.instructions.ShortArrayCodeOutput;
-import com.android.jack.dx.rop.cst.Constant;
 import com.android.jack.dx.rop.cst.CstIndexMap;
 import com.android.jack.dx.rop.cst.CstMethodRef;
 import com.android.jack.dx.util.AnnotatedOutput;
@@ -33,10 +30,13 @@
 import com.android.jack.dx.util.DexException;
 import com.android.jack.dx.util.Hex;
 
+import java.io.PrintWriter;
+
 /**
  * Representation of all the parts needed to import methods from a {@code dex} file into another.
  */
-public final class ImportedCodeItem extends OffsettedItem implements com.android.jack.dx.dex.file.Code {
+public final class ImportedCodeItem extends OffsettedItem implements
+    com.android.jack.dx.dex.file.Code {
 
   /** {@code null-ok;} the imported debug info or {@code null} if there is none; */
   ImportedDebugInfoItem debugInfoItem = null;
@@ -101,6 +101,7 @@
   }
 
   /** {@inheritDoc} */
+  @Override
   public void addContents(DexFile file) {
     if (debugInfoItem != null) {
       file.getByteData().add(debugInfoItem);
@@ -132,7 +133,8 @@
   protected void place0(Section addedTo, int offset) {
     int triesLength = code.getTries().length;
 
-    encodedHandlers = triesLength != 0 ? encodeAndRemapCatchHandler(addedTo.getFile()) : new byte[0];
+    encodedHandlers =
+        triesLength != 0 ? encodeAndRemapCatchHandler(addedTo.getFile()) : new byte[0];
 
     int catchesSize = triesLength * CatchStructs.TRY_ITEM_WRITE_SIZE + encodedHandlers.length;
 
@@ -314,6 +316,7 @@
 
   private class GenericVisitor implements CodeReader.Visitor {
 
+    @Override
     public void visit(DecodedInstruction[] all, DecodedInstruction decodedInst) {
       remappedInstructions[remappingIndex++] = decodedInst;
     }
@@ -335,8 +338,8 @@
       int newIndex = cstIndexMap.getRemappedCstStringIndex(file, decodedInst.getIndex());
 
       if (decodedInst.getOpcode() != Opcodes.CONST_STRING_JUMBO && (newIndex > 0xffff)) {
-        throw new DexException("Cannot remap new index " + newIndex
-            + " into a non-jumbo instruction!");
+        throw new DexException(
+            "Cannot remap new index " + newIndex + " into a non-jumbo instruction!");
       }
 
       remappedInstructions[remappingIndex++] = decodedInst.withIndex(newIndex);
@@ -356,8 +359,8 @@
 
     @Override
     public void visit(DecodedInstruction[] all, DecodedInstruction decodedInst) {
-      remappedInstructions[remappingIndex++] =
-          decodedInst.withIndex(cstIndexMap.getRemappedCstFieldRefIndex(file, decodedInst.getIndex()));
+      remappedInstructions[remappingIndex++] = decodedInst.withIndex(
+          cstIndexMap.getRemappedCstFieldRefIndex(file, decodedInst.getIndex()));
     }
   }
 
@@ -392,9 +395,8 @@
 
     @Override
     public void visit(DecodedInstruction[] all, DecodedInstruction decodedInst) {
-      remappedInstructions[remappingIndex++] =
-          decodedInst.withIndex(cstIndexMap.getRemappedCstBaseMethodRefIndex(file,
-              decodedInst.getIndex()));
+      remappedInstructions[remappingIndex++] = decodedInst.withIndex(
+          cstIndexMap.getRemappedCstBaseMethodRefIndex(file, decodedInst.getIndex()));
     }
   }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ImportedDebugInfoItem.java b/dx/src/com/android/jack/dx/dex/file/ImportedDebugInfoItem.java
index 1d7b4cb..4219ebb 100644
--- a/dx/src/com/android/jack/dx/dex/file/ImportedDebugInfoItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/ImportedDebugInfoItem.java
@@ -27,13 +27,15 @@
 import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL;
 import static com.android.jack.dx.dex.file.DebugInfoConstants.DBG_START_LOCAL_EXTENDED;
 
-import java.io.PrintWriter;
-
 import com.android.jack.dx.io.DexBuffer;
-import com.android.jack.dx.rop.cst.Constant;
 import com.android.jack.dx.rop.cst.CstIndexMap;
 import com.android.jack.dx.util.AnnotatedOutput;
 
+import java.io.PrintWriter;
+
+/**
+ * TODO(jack team)
+ */
 public class ImportedDebugInfoItem extends OffsettedItem {
 
   /** the required alignment for instances of this class */
diff --git a/dx/src/com/android/jack/dx/dex/file/IndexedItem.java b/dx/src/com/android/jack/dx/dex/file/IndexedItem.java
index 6e2c83b..9bfefec 100644
--- a/dx/src/com/android/jack/dx/dex/file/IndexedItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/IndexedItem.java
@@ -20,62 +20,62 @@
  * An item in a Dalvik file which is referenced by index.
  */
 public abstract class IndexedItem extends Item {
-    /** {@code >= -1;} assigned index of the item, or {@code -1} if not
-     * yet assigned */
-    private int index;
+  /** {@code >= -1;} assigned index of the item, or {@code -1} if not
+   * yet assigned */
+  private int index;
 
-    /**
-     * Constructs an instance. The index is initially unassigned.
-     */
-    public IndexedItem() {
-        index = -1;
+  /**
+   * Constructs an instance. The index is initially unassigned.
+   */
+  public IndexedItem() {
+    index = -1;
+  }
+
+  /**
+   * Gets whether or not this instance has been assigned an index.
+   *
+   * @return {@code true} iff this instance has been assigned an index
+   */
+  public final boolean hasIndex() {
+    return (index >= 0);
+  }
+
+  /**
+   * Gets the item index.
+   *
+   * @return {@code >= 0;} the index
+   * @throws RuntimeException thrown if the item index is not yet assigned
+   */
+  public final int getIndex() {
+    if (index < 0) {
+      throw new RuntimeException("index not yet set");
     }
 
-    /**
-     * Gets whether or not this instance has been assigned an index.
-     *
-     * @return {@code true} iff this instance has been assigned an index
-     */
-    public final boolean hasIndex() {
-        return (index >= 0);
+    return index;
+  }
+
+  /**
+   * Sets the item index. This method may only ever be called once
+   * per instance, and this will throw a {@code RuntimeException} if
+   * called a second (or subsequent) time.
+   *
+   * @param index {@code >= 0;} the item index
+   */
+  public final void setIndex(int index) {
+    if (this.index != -1) {
+      throw new RuntimeException("index already set");
     }
 
-    /**
-     * Gets the item index.
-     *
-     * @return {@code >= 0;} the index
-     * @throws RuntimeException thrown if the item index is not yet assigned
-     */
-    public final int getIndex() {
-        if (index < 0) {
-            throw new RuntimeException("index not yet set");
-        }
+    this.index = index;
+  }
 
-        return index;
-    }
-
-    /**
-     * Sets the item index. This method may only ever be called once
-     * per instance, and this will throw a {@code RuntimeException} if
-     * called a second (or subsequent) time.
-     *
-     * @param index {@code >= 0;} the item index
-     */
-    public final void setIndex(int index) {
-        if (this.index != -1) {
-            throw new RuntimeException("index already set");
-        }
-
-        this.index = index;
-    }
-
-    /**
-     * Gets the index of this item as a string, suitable for including in
-     * annotations.
-     *
-     * @return {@code non-null;} the index string
-     */
-    public final String indexString() {
-        return '[' + Integer.toHexString(index) + ']';
-    }
+  /**
+   * Gets the index of this item as a string, suitable for including in
+   * annotations.
+   *
+   * @return {@code non-null;} the index string
+   */
+  public final String indexString() {
+    return '[' + Integer.toHexString(index) + ']';
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/Item.java b/dx/src/com/android/jack/dx/dex/file/Item.java
index 6dca0e5..f1ecd64 100644
--- a/dx/src/com/android/jack/dx/dex/file/Item.java
+++ b/dx/src/com/android/jack/dx/dex/file/Item.java
@@ -23,58 +23,58 @@
  * repeated piece of a Dalvik file.
  */
 public abstract class Item {
-    /**
-     * Constructs an instance.
-     */
-    public Item() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance.
+   */
+  public Item() {
+    // This space intentionally left blank.
+  }
 
-    /**
-     * Returns the item type for this instance.
-     *
-     * @return {@code non-null;} the item type
-     */
-    public abstract ItemType itemType();
+  /**
+   * Returns the item type for this instance.
+   *
+   * @return {@code non-null;} the item type
+   */
+  public abstract ItemType itemType();
 
-    /**
-     * Returns the human name for the particular type of item this
-     * instance is.
-     *
-     * @return {@code non-null;} the name
-     */
-    public final String typeName() {
-        return itemType().toHuman();
-    }
+  /**
+   * Returns the human name for the particular type of item this
+   * instance is.
+   *
+   * @return {@code non-null;} the name
+   */
+  public final String typeName() {
+    return itemType().toHuman();
+  }
 
-    /**
-     * Gets the size of this instance when written, in bytes.
-     *
-     * @return {@code >= 0;} the write size
-     */
-    public abstract int writeSize();
+  /**
+   * Gets the size of this instance when written, in bytes.
+   *
+   * @return {@code >= 0;} the write size
+   */
+  public abstract int writeSize();
 
-    /**
-     * Populates a {@link DexFile} with items from within this instance.
-     * This will <i>not</i> add an item to the file for this instance itself
-     * (which should have been done by whatever refers to this instance).
-     *
-     * <p><b>Note:</b> Subclasses must override this to do something
-     * appropriate.</p>
-     *
-     * @param file {@code non-null;} the file to populate
-     */
-    public abstract void addContents(DexFile file);
+  /**
+   * Populates a {@link DexFile} with items from within this instance.
+   * This will <i>not</i> add an item to the file for this instance itself
+   * (which should have been done by whatever refers to this instance).
+   *
+   * <p><b>Note:</b> Subclasses must override this to do something
+   * appropriate.</p>
+   *
+   * @param file {@code non-null;} the file to populate
+   */
+  public abstract void addContents(DexFile file);
 
-    /**
-     * Writes the representation of this instance to the given data section,
-     * using the given {@link DexFile} to look things up as needed.
-     * If this instance keeps track of its offset, then this method will
-     * note the written offset and will also throw an exception if this
-     * instance has already been written.
-     *
-     * @param file {@code non-null;} the file to use for reference
-     * @param out {@code non-null;} where to write to
-     */
-    public abstract void writeTo(DexFile file, AnnotatedOutput out);
+  /**
+   * Writes the representation of this instance to the given data section,
+   * using the given {@link DexFile} to look things up as needed.
+   * If this instance keeps track of its offset, then this method will
+   * note the written offset and will also throw an exception if this
+   * instance has already been written.
+   *
+   * @param file {@code non-null;} the file to use for reference
+   * @param out {@code non-null;} where to write to
+   */
+  public abstract void writeTo(DexFile file, AnnotatedOutput out);
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ItemType.java b/dx/src/com/android/jack/dx/dex/file/ItemType.java
index 6d8f274..2516994 100644
--- a/dx/src/com/android/jack/dx/dex/file/ItemType.java
+++ b/dx/src/com/android/jack/dx/dex/file/ItemType.java
@@ -22,76 +22,77 @@
  * Enumeration of all the top-level item types.
  */
 public enum ItemType implements ToHuman {
-    TYPE_HEADER_ITEM(               0x0000, "header_item"),
-    TYPE_STRING_ID_ITEM(            0x0001, "string_id_item"),
-    TYPE_TYPE_ID_ITEM(              0x0002, "type_id_item"),
-    TYPE_PROTO_ID_ITEM(             0x0003, "proto_id_item"),
-    TYPE_FIELD_ID_ITEM(             0x0004, "field_id_item"),
-    TYPE_METHOD_ID_ITEM(            0x0005, "method_id_item"),
-    TYPE_CLASS_DEF_ITEM(            0x0006, "class_def_item"),
-    TYPE_MAP_LIST(                  0x1000, "map_list"),
-    TYPE_TYPE_LIST(                 0x1001, "type_list"),
-    TYPE_ANNOTATION_SET_REF_LIST(   0x1002, "annotation_set_ref_list"),
-    TYPE_ANNOTATION_SET_ITEM(       0x1003, "annotation_set_item"),
-    TYPE_CLASS_DATA_ITEM(           0x2000, "class_data_item"),
-    TYPE_CODE_ITEM(                 0x2001, "code_item"),
-    TYPE_STRING_DATA_ITEM(          0x2002, "string_data_item"),
-    TYPE_DEBUG_INFO_ITEM(           0x2003, "debug_info_item"),
-    TYPE_ANNOTATION_ITEM(           0x2004, "annotation_item"),
-    TYPE_ENCODED_ARRAY_ITEM(        0x2005, "encoded_array_item"),
-    TYPE_ANNOTATIONS_DIRECTORY_ITEM(0x2006, "annotations_directory_item"),
-    TYPE_MAP_ITEM(                  -1,     "map_item"),
-    TYPE_TYPE_ITEM(                 -1,     "type_item"),
-    TYPE_EXCEPTION_HANDLER_ITEM(    -1,     "exception_handler_item"),
-    TYPE_ANNOTATION_SET_REF_ITEM(   -1,     "annotation_set_ref_item");
+  TYPE_HEADER_ITEM(0x0000, "header_item"),
+  TYPE_STRING_ID_ITEM(0x0001, "string_id_item"),
+  TYPE_TYPE_ID_ITEM(0x0002, "type_id_item"),
+  TYPE_PROTO_ID_ITEM(0x0003, "proto_id_item"),
+  TYPE_FIELD_ID_ITEM(0x0004, "field_id_item"),
+  TYPE_METHOD_ID_ITEM(0x0005, "method_id_item"),
+  TYPE_CLASS_DEF_ITEM(0x0006, "class_def_item"),
+  TYPE_MAP_LIST(0x1000, "map_list"),
+  TYPE_TYPE_LIST(0x1001, "type_list"),
+  TYPE_ANNOTATION_SET_REF_LIST(0x1002, "annotation_set_ref_list"),
+  TYPE_ANNOTATION_SET_ITEM(0x1003, "annotation_set_item"),
+  TYPE_CLASS_DATA_ITEM(0x2000, "class_data_item"),
+  TYPE_CODE_ITEM(0x2001, "code_item"),
+  TYPE_STRING_DATA_ITEM(0x2002, "string_data_item"),
+  TYPE_DEBUG_INFO_ITEM(0x2003, "debug_info_item"),
+  TYPE_ANNOTATION_ITEM(0x2004, "annotation_item"),
+  TYPE_ENCODED_ARRAY_ITEM(0x2005, "encoded_array_item"),
+  TYPE_ANNOTATIONS_DIRECTORY_ITEM(0x2006, "annotations_directory_item"),
+  TYPE_MAP_ITEM(-1, "map_item"),
+  TYPE_TYPE_ITEM(-1, "type_item"),
+  TYPE_EXCEPTION_HANDLER_ITEM(-1, "exception_handler_item"),
+  TYPE_ANNOTATION_SET_REF_ITEM(-1, "annotation_set_ref_item");
 
-    /** value when represented in a {@link MapItem} */
-    private final int mapValue;
+  /** value when represented in a {@link MapItem} */
+  private final int mapValue;
 
-    /** {@code non-null;} name of the type */
-    private final String typeName;
+  /** {@code non-null;} name of the type */
+  private final String typeName;
 
-    /** {@code non-null;} the short human name */
-    private final String humanName;
+  /** {@code non-null;} the short human name */
+  private final String humanName;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param mapValue value when represented in a {@link MapItem}
-     * @param typeName {@code non-null;} name of the type
-     */
-    private ItemType(int mapValue, String typeName) {
-        this.mapValue = mapValue;
-        this.typeName = typeName;
+  /**
+   * Constructs an instance.
+   *
+   * @param mapValue value when represented in a {@link MapItem}
+   * @param typeName {@code non-null;} name of the type
+   */
+  private ItemType(int mapValue, String typeName) {
+    this.mapValue = mapValue;
+    this.typeName = typeName;
 
-        // Make the human name.
-        String human = typeName;
-        if (human.endsWith("_item")) {
-            human = human.substring(0, human.length() - 5);
-        }
-        this.humanName = human.replace('_', ' ');
+    // Make the human name.
+    String human = typeName;
+    if (human.endsWith("_item")) {
+      human = human.substring(0, human.length() - 5);
     }
+    this.humanName = human.replace('_', ' ');
+  }
 
-    /**
-     * Gets the map value.
-     *
-     * @return the map value
-     */
-    public int getMapValue() {
-        return mapValue;
-    }
+  /**
+   * Gets the map value.
+   *
+   * @return the map value
+   */
+  public int getMapValue() {
+    return mapValue;
+  }
 
-    /**
-     * Gets the type name.
-     *
-     * @return {@code non-null;} the type name
-     */
-    public String getTypeName() {
-        return typeName;
-    }
+  /**
+   * Gets the type name.
+   *
+   * @return {@code non-null;} the type name
+   */
+  public String getTypeName() {
+    return typeName;
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return humanName;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return humanName;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MapItem.java b/dx/src/com/android/jack/dx/dex/file/MapItem.java
index d0bc331..21f1724 100644
--- a/dx/src/com/android/jack/dx/dex/file/MapItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/MapItem.java
@@ -25,211 +25,188 @@
  * Class that represents a map item.
  */
 public final class MapItem extends OffsettedItem {
-    /** file alignment of this class, in bytes */
-    private static final int ALIGNMENT = 4;
+  /** file alignment of this class, in bytes */
+  private static final int ALIGNMENT = 4;
 
-    /** write size of this class, in bytes: three {@code uint}s */
-    private static final int WRITE_SIZE = (4 * 3);
+  /** write size of this class, in bytes: three {@code uint}s */
+  private static final int WRITE_SIZE = (4 * 3);
 
-    /** {@code non-null;} item type this instance covers */
-    private final ItemType type;
+  /** {@code non-null;} item type this instance covers */
+  private final ItemType type;
 
-    /** {@code non-null;} section this instance covers */
-    private final Section section;
+  /** {@code non-null;} section this instance covers */
+  private final Section section;
 
-    /**
-     * {@code null-ok;} first item covered or {@code null} if this is
-     * a self-reference
-     */
-    private final Item firstItem;
+  /**
+   * {@code null-ok;} first item covered or {@code null} if this is
+   * a self-reference
+   */
+  private final Item firstItem;
 
-    /**
-     * {@code null-ok;} last item covered or {@code null} if this is
-     * a self-reference
-     */
-    private final Item lastItem;
+  /**
+   * {@code > 0;} count of items covered; {@code 1} if this
+   * is a self-reference
+   */
+  private final int itemCount;
 
-    /**
-     * {@code > 0;} count of items covered; {@code 1} if this
-     * is a self-reference
-     */
-    private final int itemCount;
-
-    /**
-     * Constructs a list item with instances of this class representing
-     * the contents of the given array of sections, adding it to the
-     * given map section.
-     *
-     * @param sections {@code non-null;} the sections
-     * @param mapSection {@code non-null;} the section that the resulting map
-     * should be added to; it should be empty on entry to this method
-     */
-    public static void addMap(Section[] sections,
-            MixedItemSection mapSection) {
-        if (sections == null) {
-            throw new NullPointerException("sections == null");
-        }
-
-        if (mapSection.items().size() != 0) {
-            throw new IllegalArgumentException(
-                    "mapSection.items().size() != 0");
-        }
-
-        ArrayList<MapItem> items = new ArrayList<MapItem>(50);
-
-        for (Section section : sections) {
-            ItemType currentType = null;
-            Item firstItem = null;
-            Item lastItem = null;
-            int count = 0;
-
-            for (Item item : section.items()) {
-                ItemType type = item.itemType();
-                if (type != currentType) {
-                    if (count != 0) {
-                        items.add(new MapItem(currentType, section,
-                                        firstItem, lastItem, count));
-                    }
-                    currentType = type;
-                    firstItem = item;
-                    count = 0;
-                }
-                lastItem = item;
-                count++;
-            }
-
-            if (count != 0) {
-                // Add a MapItem for the final items in the section.
-                items.add(new MapItem(currentType, section,
-                                firstItem, lastItem, count));
-            } else if (section == mapSection) {
-                // Add a MapItem for the self-referential section.
-                items.add(new MapItem(mapSection));
-            }
-        }
-
-        mapSection.add(
-                new UniformListItem<MapItem>(ItemType.TYPE_MAP_LIST, items));
+  /**
+   * Constructs a list item with instances of this class representing
+   * the contents of the given array of sections, adding it to the
+   * given map section.
+   *
+   * @param sections {@code non-null;} the sections
+   * @param mapSection {@code non-null;} the section that the resulting map
+   * should be added to; it should be empty on entry to this method
+   */
+  public static void addMap(Section[] sections, MixedItemSection mapSection) {
+    if (sections == null) {
+      throw new NullPointerException("sections == null");
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param type {@code non-null;} item type this instance covers
-     * @param section {@code non-null;} section this instance covers
-     * @param firstItem {@code non-null;} first item covered
-     * @param lastItem {@code non-null;} last item covered
-     * @param itemCount {@code > 0;} count of items covered
-     */
-    private MapItem(ItemType type, Section section, Item firstItem,
-            Item lastItem, int itemCount) {
-        super(ALIGNMENT, WRITE_SIZE);
-
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
-
-        if (section == null) {
-            throw new NullPointerException("section == null");
-        }
-
-        if (firstItem == null) {
-            throw new NullPointerException("firstItem == null");
-        }
-
-        if (lastItem == null) {
-            throw new NullPointerException("lastItem == null");
-        }
-
-        if (itemCount <= 0) {
-            throw new IllegalArgumentException("itemCount <= 0");
-        }
-
-        this.type = type;
-        this.section = section;
-        this.firstItem = firstItem;
-        this.lastItem = lastItem;
-        this.itemCount = itemCount;
+    if (mapSection.items().size() != 0) {
+      throw new IllegalArgumentException("mapSection.items().size() != 0");
     }
 
-    /**
-     * Constructs a self-referential instance. This instance is meant to
-     * represent the section containing the {@code map_list}.
-     *
-     * @param section {@code non-null;} section this instance covers
-     */
-    private MapItem(Section section) {
-        super(ALIGNMENT, WRITE_SIZE);
+    ArrayList<MapItem> items = new ArrayList<MapItem>(50);
 
-        if (section == null) {
-            throw new NullPointerException("section == null");
+    for (Section section : sections) {
+      ItemType currentType = null;
+      Item firstItem = null;
+      int count = 0;
+
+      for (Item item : section.items()) {
+        ItemType type = item.itemType();
+        if (type != currentType) {
+          if (count != 0) {
+            items.add(new MapItem(currentType, section, firstItem, count));
+          }
+          currentType = type;
+          firstItem = item;
+          count = 0;
         }
+        count++;
+      }
 
-        this.type = ItemType.TYPE_MAP_LIST;
-        this.section = section;
-        this.firstItem = null;
-        this.lastItem = null;
-        this.itemCount = 1;
+      if (count != 0) {
+        // Add a MapItem for the final items in the section.
+        items.add(new MapItem(currentType, section, firstItem, count));
+      } else if (section == mapSection) {
+        // Add a MapItem for the self-referential section.
+        items.add(new MapItem(mapSection));
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_MAP_ITEM;
+    mapSection.add(new UniformListItem<MapItem>(ItemType.TYPE_MAP_LIST, items));
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param type {@code non-null;} item type this instance covers
+   * @param section {@code non-null;} section this instance covers
+   * @param firstItem {@code non-null;} first item covered
+   * @param itemCount {@code > 0;} count of items covered
+   */
+  private MapItem(ItemType type, Section section, Item firstItem, int itemCount) {
+    super(ALIGNMENT, WRITE_SIZE);
+
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        sb.append(getClass().getName());
-        sb.append('{');
-        sb.append(section.toString());
-        sb.append(' ');
-        sb.append(type.toHuman());
-        sb.append('}');
-
-        return sb.toString();
+    if (section == null) {
+      throw new NullPointerException("section == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        // We have nothing to add.
+    if (firstItem == null) {
+      throw new NullPointerException("firstItem == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final String toHuman() {
-        return toString();
+    if (itemCount <= 0) {
+      throw new IllegalArgumentException("itemCount <= 0");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        int value = type.getMapValue();
-        int offset;
+    this.type = type;
+    this.section = section;
+    this.firstItem = firstItem;
+    this.itemCount = itemCount;
+  }
 
-        if (firstItem == null) {
-            offset = section.getFileOffset();
-        } else {
-            offset = section.getAbsoluteItemOffset(firstItem);
-        }
+  /**
+   * Constructs a self-referential instance. This instance is meant to
+   * represent the section containing the {@code map_list}.
+   *
+   * @param section {@code non-null;} section this instance covers
+   */
+  private MapItem(Section section) {
+    super(ALIGNMENT, WRITE_SIZE);
 
-        if (out.annotates()) {
-            out.annotate(0, offsetString() + ' ' + type.getTypeName() +
-                    " map");
-            out.annotate(2, "  type:   " + Hex.u2(value) + " // " +
-                    type.toString());
-            out.annotate(2, "  unused: 0");
-            out.annotate(4, "  size:   " + Hex.u4(itemCount));
-            out.annotate(4, "  offset: " + Hex.u4(offset));
-        }
-
-        out.writeShort(value);
-        out.writeShort(0); // unused
-        out.writeInt(itemCount);
-        out.writeInt(offset);
+    if (section == null) {
+      throw new NullPointerException("section == null");
     }
+
+    this.type = ItemType.TYPE_MAP_LIST;
+    this.section = section;
+    this.firstItem = null;
+    this.itemCount = 1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_MAP_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append(getClass().getName());
+    sb.append('{');
+    sb.append(section.toString());
+    sb.append(' ');
+    sb.append(type.toHuman());
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    // We have nothing to add.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final String toHuman() {
+    return toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    int value = type.getMapValue();
+    int offset;
+
+    if (firstItem == null) {
+      offset = section.getFileOffset();
+    } else {
+      offset = section.getAbsoluteItemOffset(firstItem);
+    }
+
+    if (out.annotates()) {
+      out.annotate(0, offsetString() + ' ' + type.getTypeName() + " map");
+      out.annotate(2, "  type:   " + Hex.u2(value) + " // " + type.toString());
+      out.annotate(2, "  unused: 0");
+      out.annotate(4, "  size:   " + Hex.u4(itemCount));
+      out.annotate(4, "  offset: " + Hex.u4(offset));
+    }
+
+    out.writeShort(value);
+    out.writeShort(0); // unused
+    out.writeInt(itemCount);
+    out.writeInt(offset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MemberIdItem.java b/dx/src/com/android/jack/dx/dex/file/MemberIdItem.java
index bb6674a..c2011a4 100644
--- a/dx/src/com/android/jack/dx/dex/file/MemberIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/MemberIdItem.java
@@ -27,83 +27,82 @@
  * Dalvik file.
  */
 public abstract class MemberIdItem extends IdItem {
-    /** {@code non-null;} the constant for the member */
-    private final CstMemberRef cst;
+  /** {@code non-null;} the constant for the member */
+  private final CstMemberRef cst;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param cst {@code non-null;} the constant for the member
-     */
-    public MemberIdItem(CstMemberRef cst) {
-        super(cst.getDefiningClass());
+  /**
+   * Constructs an instance.
+   *
+   * @param cst {@code non-null;} the constant for the member
+   */
+  public MemberIdItem(CstMemberRef cst) {
+    super(cst.getDefiningClass());
 
-        this.cst = cst;
+    this.cst = cst;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.MEMBER_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    super.addContents(file);
+
+    StringIdsSection stringIds = file.getStringIds();
+    stringIds.intern(getRef().getNat().getName());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final void writeTo(DexFile file, AnnotatedOutput out) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    StringIdsSection stringIds = file.getStringIds();
+    CstNat nat = cst.getNat();
+    int classIdx = typeIds.indexOf(getDefiningClass());
+    int nameIdx = stringIds.indexOf(nat.getName());
+    int typoidIdx = getTypoidIdx(file);
+
+    if (out.annotates()) {
+      out.annotate(0, indexString() + ' ' + cst.toHuman());
+      out.annotate(2, "  class_idx: " + Hex.u2(classIdx));
+      out.annotate(2, String.format("  %-10s %s", getTypoidName() + ':', Hex.u2(typoidIdx)));
+      out.annotate(4, "  name_idx:  " + Hex.u4(nameIdx));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.MEMBER_ID_ITEM;
-    }
+    out.writeShort(classIdx);
+    out.writeShort(typoidIdx);
+    out.writeInt(nameIdx);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        super.addContents(file);
+  /**
+   * Returns the index of the type-like thing associated with
+   * this item, in order that it may be written out. Subclasses must
+   * override this to get whatever it is they need to store.
+   *
+   * @param file {@code non-null;} the file being written
+   * @return the index in question
+   */
+  protected abstract int getTypoidIdx(DexFile file);
 
-        StringIdsSection stringIds = file.getStringIds();
-        stringIds.intern(getRef().getNat().getName());
-    }
+  /**
+   * Returns the field name of the type-like thing associated with
+   * this item, for listing-generating purposes. Subclasses must override
+   * this.
+   *
+   * @return {@code non-null;} the name in question
+   */
+  protected abstract String getTypoidName();
 
-    /** {@inheritDoc} */
-    @Override
-    public final void writeTo(DexFile file, AnnotatedOutput out) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        StringIdsSection stringIds = file.getStringIds();
-        CstNat nat = cst.getNat();
-        int classIdx = typeIds.indexOf(getDefiningClass());
-        int nameIdx = stringIds.indexOf(nat.getName());
-        int typoidIdx = getTypoidIdx(file);
-
-        if (out.annotates()) {
-            out.annotate(0, indexString() + ' ' + cst.toHuman());
-            out.annotate(2, "  class_idx: " + Hex.u2(classIdx));
-            out.annotate(2, String.format("  %-10s %s", getTypoidName() + ':',
-                            Hex.u2(typoidIdx)));
-            out.annotate(4, "  name_idx:  " + Hex.u4(nameIdx));
-        }
-
-        out.writeShort(classIdx);
-        out.writeShort(typoidIdx);
-        out.writeInt(nameIdx);
-    }
-
-    /**
-     * Returns the index of the type-like thing associated with
-     * this item, in order that it may be written out. Subclasses must
-     * override this to get whatever it is they need to store.
-     *
-     * @param file {@code non-null;} the file being written
-     * @return the index in question
-     */
-    protected abstract int getTypoidIdx(DexFile file);
-
-    /**
-     * Returns the field name of the type-like thing associated with
-     * this item, for listing-generating purposes. Subclasses must override
-     * this.
-     *
-     * @return {@code non-null;} the name in question
-     */
-    protected abstract String getTypoidName();
-
-    /**
-     * Gets the member constant.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public final CstMemberRef getRef() {
-        return cst;
-    }
+  /**
+   * Gets the member constant.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public final CstMemberRef getRef() {
+    return cst;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MemberIdsSection.java b/dx/src/com/android/jack/dx/dex/file/MemberIdsSection.java
index 628f109..e173590 100644
--- a/dx/src/com/android/jack/dx/dex/file/MemberIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/MemberIdsSection.java
@@ -27,54 +27,59 @@
  * Member (field or method) refs list section of a {@code .dex} file.
  */
 public abstract class MemberIdsSection extends UniformItemSection {
-    /** The largest addressable member is 0xffff, in the dex spec as field@CCCC or meth@CCCC. */
-    private static final int MAX_MEMBERS = 0x10000;
+  /** The largest addressable member is 0xffff, in the dex spec as field@CCCC or meth@CCCC. */
+  private static final int MAX_MEMBERS = 0x10000;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param name {@code null-ok;} the name of this instance, for annotation
-     * purposes
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public MemberIdsSection(String name, DexFile file) {
-        super(name, file, 4);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param name {@code null-ok;} the name of this instance, for annotation
+   * purposes
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public MemberIdsSection(String name, DexFile file) {
+    super(name, file, 4);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    int idx = 0;
+
+    if (items().size() > MAX_MEMBERS) {
+      throw new DexException(tooManyMembersMessage());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        int idx = 0;
+    for (Object i : items()) {
+      ((MemberIdItem) i).setIndex(idx);
+      idx++;
+    }
+  }
 
-        if (items().size() > MAX_MEMBERS) {
-            throw new DexException(tooManyMembersMessage());
-        }
-
-        for (Object i : items()) {
-            ((MemberIdItem) i).setIndex(idx);
-            idx++;
-        }
+  private String tooManyMembersMessage() {
+    Map<String, AtomicInteger> membersByPackage = new TreeMap<String, AtomicInteger>();
+    for (Object member : items()) {
+      String packageName = ((MemberIdItem) member).getDefiningClass().getPackageName();
+      AtomicInteger count = membersByPackage.get(packageName);
+      if (count == null) {
+        count = new AtomicInteger();
+        membersByPackage.put(packageName, count);
+      }
+      count.incrementAndGet();
     }
 
-    private String tooManyMembersMessage() {
-        Map<String, AtomicInteger> membersByPackage = new TreeMap<String, AtomicInteger>();
-        for (Object member : items()) {
-            String packageName = ((MemberIdItem) member).getDefiningClass().getPackageName();
-            AtomicInteger count = membersByPackage.get(packageName);
-            if (count == null) {
-                count = new AtomicInteger();
-                membersByPackage.put(packageName, count);
-            }
-            count.incrementAndGet();
-        }
-
-        Formatter formatter = new Formatter();
-        String memberType = this instanceof MethodIdsSection ? "methods" : "fields";
-        formatter.format("Too many %s: %d; max is %d. By package:",
-                memberType, items().size(), MAX_MEMBERS);
-        for (Map.Entry<String, AtomicInteger> entry : membersByPackage.entrySet()) {
-            formatter.format("%n%6d %s", entry.getValue().get(), entry.getKey());
-        }
-        return formatter.toString();
+    Formatter formatter = null;
+    try {
+      formatter = new Formatter();
+      String memberType = this instanceof MethodIdsSection ? "methods" : "fields";
+      formatter.format("Too many %s: %d; max is %d. By package:", memberType, items().size(),
+          MAX_MEMBERS);
+      for (Map.Entry<String, AtomicInteger> entry : membersByPackage.entrySet()) {
+        formatter.format("%n%6d %s", entry.getValue().get(), entry.getKey());
+      }
+      return formatter.toString();
+    } finally {
+      formatter.close();
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MethodAnnotationStruct.java b/dx/src/com/android/jack/dx/dex/file/MethodAnnotationStruct.java
index 8e2ca32..a12fa0f 100644
--- a/dx/src/com/android/jack/dx/dex/file/MethodAnnotationStruct.java
+++ b/dx/src/com/android/jack/dx/dex/file/MethodAnnotationStruct.java
@@ -25,98 +25,99 @@
 /**
  * Association of a method and its annotations.
  */
-public final class MethodAnnotationStruct
-        implements ToHuman, Comparable<MethodAnnotationStruct> {
-    /** {@code non-null;} the method in question */
-    private final CstMethodRef method;
+public final class MethodAnnotationStruct implements ToHuman, Comparable<MethodAnnotationStruct> {
+  /** {@code non-null;} the method in question */
+  private final CstMethodRef method;
 
-    /** {@code non-null;} the associated annotations */
-    private AnnotationSetItem annotations;
+  /** {@code non-null;} the associated annotations */
+  private AnnotationSetItem annotations;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the method in question
-     * @param annotations {@code non-null;} the associated annotations
-     */
-    public MethodAnnotationStruct(CstMethodRef method,
-            AnnotationSetItem annotations) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        if (annotations == null) {
-            throw new NullPointerException("annotations == null");
-        }
-
-        this.method = method;
-        this.annotations = annotations;
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the method in question
+   * @param annotations {@code non-null;} the associated annotations
+   */
+  public MethodAnnotationStruct(CstMethodRef method, AnnotationSetItem annotations) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        return method.hashCode();
+    if (annotations == null) {
+      throw new NullPointerException("annotations == null");
     }
 
-    /** {@inheritDoc} */
-    public boolean equals(Object other) {
-        if (! (other instanceof MethodAnnotationStruct)) {
-            return false;
-        }
+    this.method = method;
+    this.annotations = annotations;
+  }
 
-        return method.equals(((MethodAnnotationStruct) other).method);
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return method.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof MethodAnnotationStruct)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(MethodAnnotationStruct other) {
-        return method.compareTo(other.method);
+    return method.equals(((MethodAnnotationStruct) other).method);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(MethodAnnotationStruct other) {
+    return method.compareTo(other.method);
+  }
+
+  /** {@inheritDoc} */
+  public void addContents(DexFile file) {
+    MethodIdsSection methodIds = file.getMethodIds();
+    MixedItemSection wordData = file.getWordData();
+
+    methodIds.intern(method);
+    annotations = wordData.intern(annotations);
+  }
+
+  /** {@inheritDoc} */
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int methodIdx = file.getMethodIds().indexOf(method);
+    int annotationsOff = annotations.getAbsoluteOffset();
+
+    if (out.annotates()) {
+      out.annotate(0, "    " + method.toHuman());
+      out.annotate(4, "      method_idx:      " + Hex.u4(methodIdx));
+      out.annotate(4, "      annotations_off: " + Hex.u4(annotationsOff));
     }
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        MethodIdsSection methodIds = file.getMethodIds();
-        MixedItemSection wordData = file.getWordData();
+    out.writeInt(methodIdx);
+    out.writeInt(annotationsOff);
+  }
 
-        methodIds.intern(method);
-        annotations = wordData.intern(annotations);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return method.toHuman() + ": " + annotations;
+  }
 
-    /** {@inheritDoc} */
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int methodIdx = file.getMethodIds().indexOf(method);
-        int annotationsOff = annotations.getAbsoluteOffset();
+  /**
+   * Gets the method this item is for.
+   *
+   * @return {@code non-null;} the method
+   */
+  public CstMethodRef getMethod() {
+    return method;
+  }
 
-        if (out.annotates()) {
-            out.annotate(0, "    " + method.toHuman());
-            out.annotate(4, "      method_idx:      " + Hex.u4(methodIdx));
-            out.annotate(4, "      annotations_off: " +
-                    Hex.u4(annotationsOff));
-        }
-
-        out.writeInt(methodIdx);
-        out.writeInt(annotationsOff);
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return method.toHuman() + ": " + annotations;
-    }
-
-    /**
-     * Gets the method this item is for.
-     *
-     * @return {@code non-null;} the method
-     */
-    public CstMethodRef getMethod() {
-        return method;
-    }
-
-    /**
-     * Gets the associated annotations.
-     *
-     * @return {@code non-null;} the annotations
-     */
-    public Annotations getAnnotations() {
-        return annotations.getAnnotations();
-    }
+  /**
+   * Gets the associated annotations.
+   *
+   * @return {@code non-null;} the annotations
+   */
+  public Annotations getAnnotations() {
+    return annotations.getAnnotations();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MethodIdItem.java b/dx/src/com/android/jack/dx/dex/file/MethodIdItem.java
index 3684172..6efc3b0 100644
--- a/dx/src/com/android/jack/dx/dex/file/MethodIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/MethodIdItem.java
@@ -22,49 +22,49 @@
  * Representation of a method reference inside a Dalvik file.
  */
 public final class MethodIdItem extends MemberIdItem {
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the constant for the method
-     */
-    public MethodIdItem(CstBaseMethodRef method) {
-        super(method);
-    }
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the constant for the method
+   */
+  public MethodIdItem(CstBaseMethodRef method) {
+    super(method);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_METHOD_ID_ITEM;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_METHOD_ID_ITEM;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        super.addContents(file);
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    super.addContents(file);
 
-        ProtoIdsSection protoIds = file.getProtoIds();
-        protoIds.intern(getMethodRef().getPrototype());
-    }
+    ProtoIdsSection protoIds = file.getProtoIds();
+    protoIds.intern(getMethodRef().getPrototype());
+  }
 
-    /**
-     * Gets the method constant.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public CstBaseMethodRef getMethodRef() {
-        return (CstBaseMethodRef) getRef();
-    }
+  /**
+   * Gets the method constant.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public CstBaseMethodRef getMethodRef() {
+    return (CstBaseMethodRef) getRef();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int getTypoidIdx(DexFile file) {
-        ProtoIdsSection protoIds = file.getProtoIds();
-        return protoIds.indexOf(getMethodRef().getPrototype());
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int getTypoidIdx(DexFile file) {
+    ProtoIdsSection protoIds = file.getProtoIds();
+    return protoIds.indexOf(getMethodRef().getPrototype());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected String getTypoidName() {
-        return "proto_idx";
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected String getTypoidName() {
+    return "proto_idx";
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MethodIdsSection.java b/dx/src/com/android/jack/dx/dex/file/MethodIdsSection.java
index 34f528e..f3dc0a6 100644
--- a/dx/src/com/android/jack/dx/dex/file/MethodIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/MethodIdsSection.java
@@ -28,110 +28,110 @@
  * Method refs list section of a {@code .dex} file.
  */
 public final class MethodIdsSection extends MemberIdsSection {
-    /**
-     * {@code non-null;} map from method constants to {@link
-     * MethodIdItem} instances
-     */
-    private final TreeMap<CstBaseMethodRef, MethodIdItem> methodIds;
+  /**
+   * {@code non-null;} map from method constants to {@link
+   * MethodIdItem} instances
+   */
+  private final TreeMap<CstBaseMethodRef, MethodIdItem> methodIds;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public MethodIdsSection(DexFile file) {
-        super("method_ids", file);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public MethodIdsSection(DexFile file) {
+    super("method_ids", file);
 
-        methodIds = new TreeMap<CstBaseMethodRef, MethodIdItem>();
+    methodIds = new TreeMap<CstBaseMethodRef, MethodIdItem>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return methodIds.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return methodIds.values();
+    throwIfNotPrepared();
+
+    IndexedItem result = methodIds.get(cst);
+
+    if (result == null) {
+      throw new IllegalArgumentException("not found");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
 
-        IndexedItem result = methodIds.get((CstBaseMethodRef) cst);
+    int sz = methodIds.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
 
-        if (result == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return result;
+    if (out.annotates()) {
+      out.annotate(4, "method_ids_size: " + Hex.u4(sz));
+      out.annotate(4, "method_ids_off:  " + Hex.u4(offset));
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
 
-        int sz = methodIds.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
-
-        if (out.annotates()) {
-            out.annotate(4, "method_ids_size: " + Hex.u4(sz));
-            out.annotate(4, "method_ids_off:  " + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+  /**
+   * Interns an element into this instance.
+   *
+   * @param method {@code non-null;} the reference to intern
+   * @return {@code non-null;} the interned reference
+   */
+  public MethodIdItem intern(CstBaseMethodRef method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param method {@code non-null;} the reference to intern
-     * @return {@code non-null;} the interned reference
-     */
-    public MethodIdItem intern(CstBaseMethodRef method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
+    throwIfPrepared();
 
-        throwIfPrepared();
+    MethodIdItem result = methodIds.get(method);
 
-        MethodIdItem result = methodIds.get(method);
-
-        if (result == null) {
-            result = new MethodIdItem(method);
-            methodIds.put(method, result);
-        }
-
-        return result;
+    if (result == null) {
+      result = new MethodIdItem(method);
+      methodIds.put(method, result);
     }
 
-    /**
-     * Gets the index of the given reference, which must have been added
-     * to this instance.
-     *
-     * @param ref {@code non-null;} the reference to look up
-     * @return {@code >= 0;} the reference's index
-     */
-    public int indexOf(CstBaseMethodRef ref) {
-        if (ref == null) {
-            throw new NullPointerException("ref == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
-
-        MethodIdItem item = methodIds.get(ref);
-
-        if (item == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return item.getIndex();
+  /**
+   * Gets the index of the given reference, which must have been added
+   * to this instance.
+   *
+   * @param ref {@code non-null;} the reference to look up
+   * @return {@code >= 0;} the reference's index
+   */
+  public int indexOf(CstBaseMethodRef ref) {
+    if (ref == null) {
+      throw new NullPointerException("ref == null");
     }
+
+    throwIfNotPrepared();
+
+    MethodIdItem item = methodIds.get(ref);
+
+    if (item == null) {
+      throw new IllegalArgumentException("not found");
+    }
+
+    return item.getIndex();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/MixedItemSection.java b/dx/src/com/android/jack/dx/dex/file/MixedItemSection.java
index 914f78a..ad45a50 100644
--- a/dx/src/com/android/jack/dx/dex/file/MixedItemSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/MixedItemSection.java
@@ -39,324 +39,323 @@
  * have a larger alignment requirement than the alignment of this instance.
  */
 public final class MixedItemSection extends Section {
-    static enum SortType {
-        /** no sorting */
-        NONE,
+  static enum SortType {
+    /** no sorting */
+    NONE,
 
-        /** sort by type only */
-        TYPE,
+    /** sort by type only */
+    TYPE,
 
-        /** sort in class-major order, with instances sorted per-class */
-        INSTANCE;
-    };
+    /** sort in class-major order, with instances sorted per-class */
+    INSTANCE;
+  };
 
-    /** {@code non-null;} sorter which sorts instances by type */
-    private static final Comparator<OffsettedItem> TYPE_SORTER =
-        new Comparator<OffsettedItem>() {
-        public int compare(OffsettedItem item1, OffsettedItem item2) {
-            ItemType type1 = item1.itemType();
-            ItemType type2 = item2.itemType();
-            return type1.compareTo(type2);
-        }
-    };
-
-    /** {@code non-null;} the items in this part */
-    private final ArrayList<OffsettedItem> items;
-
-    /** {@code non-null;} items that have been explicitly interned */
-    private final HashMap<OffsettedItem, OffsettedItem> interns;
-
-    /** {@code non-null;} how to sort the items */
-    private final SortType sort;
-
-    /**
-     * {@code >= -1;} the current size of this part, in bytes, or {@code -1}
-     * if not yet calculated
-     */
-    private int writeSize;
-
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param name {@code null-ok;} the name of this instance, for annotation
-     * purposes
-     * @param file {@code non-null;} file that this instance is part of
-     * @param alignment {@code > 0;} alignment requirement for the final output;
-     * must be a power of 2
-     * @param sort how the items should be sorted in the final output
-     */
-    public MixedItemSection(String name, DexFile file, int alignment,
-            SortType sort) {
-        super(name, file, alignment);
-
-        this.items = new ArrayList<OffsettedItem>(100);
-        this.interns = new HashMap<OffsettedItem, OffsettedItem>(100);
-        this.sort = sort;
-        this.writeSize = -1;
-    }
-
-    /** {@inheritDoc} */
+  /** {@code non-null;} sorter which sorts instances by type */
+  private static final Comparator<OffsettedItem> TYPE_SORTER = new Comparator<OffsettedItem>() {
     @Override
-    public Collection<? extends Item> items() {
-        return items;
+    public int compare(OffsettedItem item1, OffsettedItem item2) {
+      ItemType type1 = item1.itemType();
+      ItemType type2 = item2.itemType();
+      return type1.compareTo(type2);
+    }
+  };
+
+  /** {@code non-null;} the items in this part */
+  private final ArrayList<OffsettedItem> items;
+
+  /** {@code non-null;} items that have been explicitly interned */
+  private final HashMap<OffsettedItem, OffsettedItem> interns;
+
+  /** {@code non-null;} how to sort the items */
+  private final SortType sort;
+
+  /**
+   * {@code >= -1;} the current size of this part, in bytes, or {@code -1}
+   * if not yet calculated
+   */
+  private int writeSize;
+
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param name {@code null-ok;} the name of this instance, for annotation
+   * purposes
+   * @param file {@code non-null;} file that this instance is part of
+   * @param alignment {@code > 0;} alignment requirement for the final output;
+   * must be a power of 2
+   * @param sort how the items should be sorted in the final output
+   */
+  public MixedItemSection(String name, DexFile file, int alignment, SortType sort) {
+    super(name, file, alignment);
+
+    this.items = new ArrayList<OffsettedItem>(100);
+    this.interns = new HashMap<OffsettedItem, OffsettedItem>(100);
+    this.sort = sort;
+    this.writeSize = -1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return items;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    throwIfNotPrepared();
+    return writeSize;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getAbsoluteItemOffset(Item item) {
+    OffsettedItem oi = (OffsettedItem) item;
+    return oi.getAbsoluteOffset();
+  }
+
+  /**
+   * Gets the size of this instance, in items.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int size() {
+    return items.size();
+  }
+
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
+
+    if (writeSize == -1) {
+      throw new RuntimeException("write size not yet set");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        throwIfNotPrepared();
-        return writeSize;
+    int sz = writeSize;
+    int offset = (sz == 0) ? 0 : getFileOffset();
+    String name = getName();
+
+    if (name == null) {
+      name = "<unnamed>";
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int getAbsoluteItemOffset(Item item) {
-        OffsettedItem oi = (OffsettedItem) item;
-        return oi.getAbsoluteOffset();
+    int spaceCount = 15 - name.length();
+    char[] spaceArr = new char[spaceCount];
+    Arrays.fill(spaceArr, ' ');
+    String spaces = new String(spaceArr);
+
+    if (out.annotates()) {
+      out.annotate(4, name + "_size:" + spaces + Hex.u4(sz));
+      out.annotate(4, name + "_off: " + spaces + Hex.u4(offset));
     }
 
-    /**
-     * Gets the size of this instance, in items.
-     *
-     * @return {@code >= 0;} the size
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
+
+  /**
+   * Adds an item to this instance. This will in turn tell the given item
+   * that it has been added to this instance. It is invalid to add the
+   * same item to more than one instance, nor to add the same items
+   * multiple times to a single instance.
+   *
+   * @param item {@code non-null;} the item to add
+   */
+  public void add(OffsettedItem item) {
+    throwIfPrepared();
+
+    try {
+      if (item.getAlignment() > getAlignment()) {
+        throw new IllegalArgumentException("incompatible item alignment");
+      }
+    } catch (NullPointerException ex) {
+      // Elucidate the exception.
+      throw new NullPointerException("item == null");
+    }
+
+    items.add(item);
+  }
+
+  /**
+   * Interns an item in this instance, returning the interned instance
+   * (which may not be the one passed in). This will add the item if no
+   * equal item has been added.
+   *
+   * @param item {@code non-null;} the item to intern
+   * @return {@code non-null;} the equivalent interned instance
+   */
+  @SuppressWarnings("unchecked")
+  public <T extends OffsettedItem> T intern(T item) {
+    throwIfPrepared();
+
+    OffsettedItem result = interns.get(item);
+
+    if (result != null) {
+      return (T) result;
+    }
+
+    add(item);
+    interns.put(item, item);
+    return item;
+  }
+
+  /**
+   * Gets an item which was previously interned.
+   *
+   * @param item {@code non-null;} the item to look for
+   * @return {@code non-null;} the equivalent already-interned instance
+   */
+  @SuppressWarnings("unchecked")
+  public <T extends OffsettedItem> T get(T item) {
+    throwIfNotPrepared();
+
+    OffsettedItem result = interns.get(item);
+
+    if (result != null) {
+      return (T) result;
+    }
+
+    throw new NoSuchElementException(item.toString());
+  }
+
+  /**
+   * Writes an index of contents of the items in this instance of the
+   * given type. If there are none, this writes nothing. If there are any,
+   * then the index is preceded by the given intro string.
+   *
+   * @param out {@code non-null;} where to write to
+   * @param itemType {@code non-null;} the item type of interest
+   * @param intro {@code non-null;} the introductory string for non-empty indices
+   */
+  public void writeIndexAnnotation(AnnotatedOutput out, ItemType itemType, String intro) {
+    throwIfNotPrepared();
+
+    TreeMap<String, OffsettedItem> index = new TreeMap<String, OffsettedItem>();
+
+    for (OffsettedItem item : items) {
+      if (item.itemType() == itemType) {
+        String label = item.toHuman();
+        index.put(label, item);
+      }
+    }
+
+    if (index.size() == 0) {
+      return;
+    }
+
+    out.annotate(0, intro);
+
+    for (Map.Entry<String, OffsettedItem> entry : index.entrySet()) {
+      String label = entry.getKey();
+      OffsettedItem item = entry.getValue();
+      out.annotate(0, item.offsetString() + ' ' + label + '\n');
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void prepare0() {
+    DexFile file = getFile();
+
+    /*
+     * It's okay for new items to be added as a result of an
+     * addContents() call; we just have to deal with the possibility.
      */
-    public int size() {
-        return items.size();
+
+int i = 0;
+    for (;;) {
+      int sz = items.size();
+      if (i >= sz) {
+        break;
+      }
+
+      for (/*i*/; i < sz; i++) {
+        OffsettedItem one = items.get(i);
+        one.addContents(file);
+      }
+    }
+  }
+
+  /**
+   * Places all the items in this instance at particular offsets. This
+   * will call {@link OffsettedItem#place} on each item. If an item
+   * does not know its write size before the call to {@code place},
+   * it is that call which is responsible for setting the write size.
+   * This method may only be called once per instance; subsequent calls
+   * will throw an exception.
+   */
+  public void placeItems() {
+    throwIfNotPrepared();
+
+    switch (sort) {
+      case INSTANCE: {
+        Collections.sort(items);
+        break;
+      }
+      case TYPE: {
+        Collections.sort(items, TYPE_SORTER);
+        break;
+      }
+      default:
+        /* continue */
+        break;
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
+    int sz = items.size();
+    int outAt = 0;
+    for (int i = 0; i < sz; i++) {
+      OffsettedItem one = items.get(i);
+      try {
+        int placedAt = one.place(this, outAt);
 
-        if (writeSize == -1) {
-            throw new RuntimeException("write size not yet set");
+        if (placedAt < outAt) {
+          throw new RuntimeException("bogus place() result for " + one);
         }
 
-        int sz = writeSize;
-        int offset = (sz == 0) ? 0 : getFileOffset();
-        String name = getName();
-
-        if (name == null) {
-            name = "<unnamed>";
-        }
-
-        int spaceCount = 15 - name.length();
-        char[] spaceArr = new char[spaceCount];
-        Arrays.fill(spaceArr, ' ');
-        String spaces = new String(spaceArr);
-
-        if (out.annotates()) {
-            out.annotate(4, name + "_size:" + spaces + Hex.u4(sz));
-            out.annotate(4, name + "_off: " + spaces + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+        outAt = placedAt + one.writeSize();
+      } catch (RuntimeException ex) {
+        throw ExceptionWithContext.withContext(ex, "...while placing " + one);
+      }
     }
 
-    /**
-     * Adds an item to this instance. This will in turn tell the given item
-     * that it has been added to this instance. It is invalid to add the
-     * same item to more than one instance, nor to add the same items
-     * multiple times to a single instance.
-     *
-     * @param item {@code non-null;} the item to add
-     */
-    public void add(OffsettedItem item) {
-        throwIfPrepared();
+    writeSize = outAt;
+  }
 
-        try {
-            if (item.getAlignment() > getAlignment()) {
-                throw new IllegalArgumentException(
-                        "incompatible item alignment");
-            }
-        } catch (NullPointerException ex) {
-            // Elucidate the exception.
-            throw new NullPointerException("item == null");
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(AnnotatedOutput out) {
+    boolean annotates = out.annotates();
+    boolean first = true;
+    DexFile file = getFile();
+    int at = 0;
+
+    for (OffsettedItem one : items) {
+      if (annotates) {
+        if (first) {
+          first = false;
+        } else {
+          out.annotate(0, "\n");
         }
+      }
 
-        items.add(item);
+      int alignMask = one.getAlignment() - 1;
+      int writeAt = (at + alignMask) & ~alignMask;
+
+      if (at != writeAt) {
+        out.writeZeroes(writeAt - at);
+        at = writeAt;
+      }
+
+      one.writeTo(file, out);
+      at += one.writeSize();
     }
 
-    /**
-     * Interns an item in this instance, returning the interned instance
-     * (which may not be the one passed in). This will add the item if no
-     * equal item has been added.
-     *
-     * @param item {@code non-null;} the item to intern
-     * @return {@code non-null;} the equivalent interned instance
-     */
-    public <T extends OffsettedItem> T intern(T item) {
-        throwIfPrepared();
-
-        OffsettedItem result = interns.get(item);
-
-        if (result != null) {
-            return (T) result;
-        }
-
-        add(item);
-        interns.put(item, item);
-        return item;
+    if (at != writeSize) {
+      throw new RuntimeException("output size mismatch");
     }
-
-    /**
-     * Gets an item which was previously interned.
-     *
-     * @param item {@code non-null;} the item to look for
-     * @return {@code non-null;} the equivalent already-interned instance
-     */
-    public <T extends OffsettedItem> T get(T item) {
-        throwIfNotPrepared();
-
-        OffsettedItem result = interns.get(item);
-
-        if (result != null) {
-            return (T) result;
-        }
-
-        throw new NoSuchElementException(item.toString());
-    }
-
-    /**
-     * Writes an index of contents of the items in this instance of the
-     * given type. If there are none, this writes nothing. If there are any,
-     * then the index is preceded by the given intro string.
-     *
-     * @param out {@code non-null;} where to write to
-     * @param itemType {@code non-null;} the item type of interest
-     * @param intro {@code non-null;} the introductory string for non-empty indices
-     */
-    public void writeIndexAnnotation(AnnotatedOutput out, ItemType itemType,
-            String intro) {
-        throwIfNotPrepared();
-
-        TreeMap<String, OffsettedItem> index =
-            new TreeMap<String, OffsettedItem>();
-
-        for (OffsettedItem item : items) {
-            if (item.itemType() == itemType) {
-                String label = item.toHuman();
-                index.put(label, item);
-            }
-        }
-
-        if (index.size() == 0) {
-            return;
-        }
-
-        out.annotate(0, intro);
-
-        for (Map.Entry<String, OffsettedItem> entry : index.entrySet()) {
-            String label = entry.getKey();
-            OffsettedItem item = entry.getValue();
-            out.annotate(0, item.offsetString() + ' ' + label + '\n');
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void prepare0() {
-        DexFile file = getFile();
-
-        /*
-         * It's okay for new items to be added as a result of an
-         * addContents() call; we just have to deal with the possibility.
-         */
-
-        int i = 0;
-        for (;;) {
-            int sz = items.size();
-            if (i >= sz) {
-                break;
-            }
-
-            for (/*i*/; i < sz; i++) {
-                OffsettedItem one = items.get(i);
-                one.addContents(file);
-            }
-        }
-    }
-
-    /**
-     * Places all the items in this instance at particular offsets. This
-     * will call {@link OffsettedItem#place} on each item. If an item
-     * does not know its write size before the call to {@code place},
-     * it is that call which is responsible for setting the write size.
-     * This method may only be called once per instance; subsequent calls
-     * will throw an exception.
-     */
-    public void placeItems() {
-        throwIfNotPrepared();
-
-        switch (sort) {
-            case INSTANCE: {
-                Collections.sort(items);
-                break;
-            }
-            case TYPE: {
-                Collections.sort(items, TYPE_SORTER);
-                break;
-            }
-        }
-
-        int sz = items.size();
-        int outAt = 0;
-        for (int i = 0; i < sz; i++) {
-            OffsettedItem one = items.get(i);
-            try {
-                int placedAt = one.place(this, outAt);
-
-                if (placedAt < outAt) {
-                    throw new RuntimeException("bogus place() result for " +
-                            one);
-                }
-
-                outAt = placedAt + one.writeSize();
-            } catch (RuntimeException ex) {
-                throw ExceptionWithContext.withContext(ex,
-                        "...while placing " + one);
-            }
-        }
-
-        writeSize = outAt;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(AnnotatedOutput out) {
-        boolean annotates = out.annotates();
-        boolean first = true;
-        DexFile file = getFile();
-        int at = 0;
-
-        for (OffsettedItem one : items) {
-            if (annotates) {
-                if (first) {
-                    first = false;
-                } else {
-                    out.annotate(0, "\n");
-                }
-            }
-
-            int alignMask = one.getAlignment() - 1;
-            int writeAt = (at + alignMask) & ~alignMask;
-
-            if (at != writeAt) {
-                out.writeZeroes(writeAt - at);
-                at = writeAt;
-            }
-
-            one.writeTo(file, out);
-            at += one.writeSize();
-        }
-
-        if (at != writeSize) {
-            throw new RuntimeException("output size mismatch");
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/OffsettedItem.java b/dx/src/com/android/jack/dx/dex/file/OffsettedItem.java
index b171f68..6c294aa 100644
--- a/dx/src/com/android/jack/dx/dex/file/OffsettedItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/OffsettedItem.java
@@ -22,293 +22,291 @@
 /**
  * An item in a Dalvik file which is referenced by absolute offset.
  */
-public abstract class OffsettedItem extends Item
-        implements Comparable<OffsettedItem> {
-    /** {@code > 0;} alignment requirement */
-    private final int alignment;
+public abstract class OffsettedItem extends Item implements Comparable<OffsettedItem> {
+  /** {@code > 0;} alignment requirement */
+  private final int alignment;
 
-    /** {@code >= -1;} the size of this instance when written, in bytes, or
-     * {@code -1} if not yet known */
-    private int writeSize;
+  /** {@code >= -1;} the size of this instance when written, in bytes, or
+   * {@code -1} if not yet known */
+  private int writeSize;
 
-    /**
-     * {@code null-ok;} section the item was added to, or {@code null} if
-     * not yet added
-     */
-    private Section addedTo;
+  /**
+   * {@code null-ok;} section the item was added to, or {@code null} if
+   * not yet added
+   */
+  private Section addedTo;
 
-    /**
-     * {@code >= -1;} assigned offset of the item from the start of its section,
-     * or {@code -1} if not yet assigned
-     */
-    private int offset;
+  /**
+   * {@code >= -1;} assigned offset of the item from the start of its section,
+   * or {@code -1} if not yet assigned
+   */
+  private int offset;
 
-    /**
-     * Gets the absolute offset of the given item, returning {@code 0}
-     * if handed {@code null}.
-     *
-     * @param item {@code null-ok;} the item in question
-     * @return {@code >= 0;} the item's absolute offset, or {@code 0}
-     * if {@code item == null}
-     */
-    public static int getAbsoluteOffsetOr0(OffsettedItem item) {
-        if (item == null) {
-            return 0;
-        }
-
-        return item.getAbsoluteOffset();
+  /**
+   * Gets the absolute offset of the given item, returning {@code 0}
+   * if handed {@code null}.
+   *
+   * @param item {@code null-ok;} the item in question
+   * @return {@code >= 0;} the item's absolute offset, or {@code 0}
+   * if {@code item == null}
+   */
+  public static int getAbsoluteOffsetOr0(OffsettedItem item) {
+    if (item == null) {
+      return 0;
     }
 
-    /**
-     * Constructs an instance. The offset is initially unassigned.
-     *
-     * @param alignment {@code > 0;} output alignment requirement; must be a
-     * power of 2
-     * @param writeSize {@code >= -1;} the size of this instance when written,
-     * in bytes, or {@code -1} if not immediately known
-     */
-    public OffsettedItem(int alignment, int writeSize) {
-        Section.validateAlignment(alignment);
+    return item.getAbsoluteOffset();
+  }
 
-        if (writeSize < -1) {
-            throw new IllegalArgumentException("writeSize < -1");
-        }
+  /**
+   * Constructs an instance. The offset is initially unassigned.
+   *
+   * @param alignment {@code > 0;} output alignment requirement; must be a
+   * power of 2
+   * @param writeSize {@code >= -1;} the size of this instance when written,
+   * in bytes, or {@code -1} if not immediately known
+   */
+  public OffsettedItem(int alignment, int writeSize) {
+    Section.validateAlignment(alignment);
 
-        this.alignment = alignment;
-        this.writeSize = writeSize;
-        this.addedTo = null;
-        this.offset = -1;
+    if (writeSize < -1) {
+      throw new IllegalArgumentException("writeSize < -1");
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * Comparisons for this class are defined to be type-major (if the
-     * types don't match then the objects are not equal), with
-     * {@link #compareTo0} deciding same-type comparisons.
-     */
-    @Override
-    public final boolean equals(Object other) {
-        if (this == other) {
-            return true;
-        }
+    this.alignment = alignment;
+    this.writeSize = writeSize;
+    this.addedTo = null;
+    this.offset = -1;
+  }
 
-        OffsettedItem otherItem = (OffsettedItem) other;
-        ItemType thisType = itemType();
-        ItemType otherType = otherItem.itemType();
-
-        if (thisType != otherType) {
-            return false;
-        }
-
-        return (compareTo0(otherItem) == 0);
+  /**
+   * {@inheritDoc}
+   *
+   * Comparisons for this class are defined to be type-major (if the
+   * types don't match then the objects are not equal), with
+   * {@link #compareTo0} deciding same-type comparisons.
+   */
+  @Override
+  public final boolean equals(Object other) {
+    if (this == other) {
+      return true;
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * Comparisons for this class are defined to be class-major (if the
-     * classes don't match then the objects are not equal), with
-     * {@link #compareTo0} deciding same-class comparisons.
-     */
-    public final int compareTo(OffsettedItem other) {
-        if (this == other) {
-            return 0;
-        }
+    OffsettedItem otherItem = (OffsettedItem) other;
+    ItemType thisType = itemType();
+    ItemType otherType = otherItem.itemType();
 
-        ItemType thisType = itemType();
-        ItemType otherType = other.itemType();
-
-        if (thisType != otherType) {
-            return thisType.compareTo(otherType);
-        }
-
-        return compareTo0(other);
+    if (thisType != otherType) {
+      return false;
     }
 
-    /**
-     * Sets the write size of this item. This may only be called once
-     * per instance, and only if the size was unknown upon instance
-     * creation.
-     *
-     * @param writeSize {@code > 0;} the write size, in bytes
-     */
-    public final void setWriteSize(int writeSize) {
-        if (writeSize < 0) {
-            throw new IllegalArgumentException("writeSize < 0");
-        }
+    return (compareTo0(otherItem) == 0);
+  }
 
-        if (this.writeSize >= 0) {
-            throw new UnsupportedOperationException("writeSize already set");
-        }
-
-        this.writeSize = writeSize;
+  /**
+   * {@inheritDoc}
+   *
+   * Comparisons for this class are defined to be class-major (if the
+   * classes don't match then the objects are not equal), with
+   * {@link #compareTo0} deciding same-class comparisons.
+   */
+  @Override
+  public final int compareTo(OffsettedItem other) {
+    if (this == other) {
+      return 0;
     }
 
-    /** {@inheritDoc}
-     *
-     * @throws UnsupportedOperationException thrown if the write size
-     * is not yet known
-     */
-    @Override
-    public final int writeSize() {
-        if (writeSize < 0) {
-            throw new UnsupportedOperationException("writeSize is unknown");
-        }
+    ItemType thisType = itemType();
+    ItemType otherType = other.itemType();
 
-        return writeSize;
+    if (thisType != otherType) {
+      return thisType.compareTo(otherType);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final void writeTo(DexFile file, AnnotatedOutput out) {
-        out.alignTo(alignment);
+    return compareTo0(other);
+  }
 
-        try {
-            if (writeSize < 0) {
-                throw new UnsupportedOperationException(
-                        "writeSize is unknown");
-            }
-            out.assertCursor(getAbsoluteOffset());
-        } catch (RuntimeException ex) {
-            throw ExceptionWithContext.withContext(ex,
-                    "...while writing " + this);
-        }
-
-        writeTo0(file, out);
+  /**
+   * Sets the write size of this item. This may only be called once
+   * per instance, and only if the size was unknown upon instance
+   * creation.
+   *
+   * @param writeSize {@code > 0;} the write size, in bytes
+   */
+  public final void setWriteSize(int writeSize) {
+    if (writeSize < 0) {
+      throw new IllegalArgumentException("writeSize < 0");
     }
 
-    /**
-     * Gets the relative item offset. The offset is from the start of
-     * the section which the instance was written to.
-     *
-     * @return {@code >= 0;} the offset
-     * @throws RuntimeException thrown if the offset is not yet known
-     */
-    public final int getRelativeOffset() {
-        if (offset < 0) {
-            throw new RuntimeException("offset not yet known");
-        }
-
-        return offset;
+    if (this.writeSize >= 0) {
+      throw new UnsupportedOperationException("writeSize already set");
     }
 
-    /**
-     * Gets the absolute item offset. The offset is from the start of
-     * the file which the instance was written to.
-     *
-     * @return {@code >= 0;} the offset
-     * @throws RuntimeException thrown if the offset is not yet known
-     */
-    public final int getAbsoluteOffset() {
-        if (offset < 0) {
-            throw new RuntimeException("offset not yet known");
-        }
+    this.writeSize = writeSize;
+  }
 
-        return addedTo.getAbsoluteOffset(offset);
+  /** {@inheritDoc}
+   *
+   * @throws UnsupportedOperationException thrown if the write size
+   * is not yet known
+   */
+  @Override
+  public final int writeSize() {
+    if (writeSize < 0) {
+      throw new UnsupportedOperationException("writeSize is unknown");
     }
 
-    /**
-     * Indicates that this item has been added to the given section at
-     * the given offset. It is only valid to call this method once per
-     * instance.
-     *
-     * @param addedTo {@code non-null;} the section this instance has
-     * been added to
-     * @param offset {@code >= 0;} the desired offset from the start of the
-     * section where this instance was placed
-     * @return {@code >= 0;} the offset that this instance should be placed at
-     * in order to meet its alignment constraint
-     */
-    public final int place(Section addedTo, int offset) {
-        if (addedTo == null) {
-            throw new NullPointerException("addedTo == null");
-        }
+    return writeSize;
+  }
 
-        if (offset < 0) {
-            throw new IllegalArgumentException("offset < 0");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public final void writeTo(DexFile file, AnnotatedOutput out) {
+    out.alignTo(alignment);
 
-        if (this.addedTo != null) {
-            throw new RuntimeException("already written");
-        }
-
-        int mask = alignment - 1;
-        offset = (offset + mask) & ~mask;
-
-        this.addedTo = addedTo;
-        this.offset = offset;
-
-        place0(addedTo, offset);
-
-        return offset;
+    try {
+      if (writeSize < 0) {
+        throw new UnsupportedOperationException("writeSize is unknown");
+      }
+      out.assertCursor(getAbsoluteOffset());
+    } catch (RuntimeException ex) {
+      throw ExceptionWithContext.withContext(ex, "...while writing " + this);
     }
 
-    /**
-     * Gets the alignment requirement of this instance. An instance should
-     * only be written when so aligned.
-     *
-     * @return {@code > 0;} the alignment requirement; must be a power of 2
-     */
-    public final int getAlignment() {
-        return alignment;
+    writeTo0(file, out);
+  }
+
+  /**
+   * Gets the relative item offset. The offset is from the start of
+   * the section which the instance was written to.
+   *
+   * @return {@code >= 0;} the offset
+   * @throws RuntimeException thrown if the offset is not yet known
+   */
+  public final int getRelativeOffset() {
+    if (offset < 0) {
+      throw new RuntimeException("offset not yet known");
     }
 
-    /**
-     * Gets the absolute offset of this item as a string, suitable for
-     * including in annotations.
-     *
-     * @return {@code non-null;} the offset string
-     */
-    public final String offsetString() {
-        return '[' + Integer.toHexString(getAbsoluteOffset()) + ']';
+    return offset;
+  }
+
+  /**
+   * Gets the absolute item offset. The offset is from the start of
+   * the file which the instance was written to.
+   *
+   * @return {@code >= 0;} the offset
+   * @throws RuntimeException thrown if the offset is not yet known
+   */
+  public final int getAbsoluteOffset() {
+    if (offset < 0) {
+      throw new RuntimeException("offset not yet known");
     }
 
-    /**
-     * Gets a short human-readable string representing this instance.
-     *
-     * @return {@code non-null;} the human form
-     */
-    public abstract String toHuman();
+    return addedTo.getAbsoluteOffset(offset);
+  }
 
-    /**
-     * Compares this instance to another which is guaranteed to be of
-     * the same class. The default implementation of this method is to
-     * throw an exception (unsupported operation). If a particular
-     * class needs to actually sort, then it should override this
-     * method.
-     *
-     * @param other {@code non-null;} instance to compare to
-     * @return {@code -1}, {@code 0}, or {@code 1}, depending
-     * on the sort order of this instance and the other
-     */
-    protected int compareTo0(OffsettedItem other) {
-        throw new UnsupportedOperationException("unsupported");
+  /**
+   * Indicates that this item has been added to the given section at
+   * the given offset. It is only valid to call this method once per
+   * instance.
+   *
+   * @param addedTo {@code non-null;} the section this instance has
+   * been added to
+   * @param offset {@code >= 0;} the desired offset from the start of the
+   * section where this instance was placed
+   * @return {@code >= 0;} the offset that this instance should be placed at
+   * in order to meet its alignment constraint
+   */
+  public final int place(Section addedTo, int offset) {
+    if (addedTo == null) {
+      throw new NullPointerException("addedTo == null");
     }
 
-    /**
-     * Does additional work required when placing an instance. The
-     * default implementation of this method is a no-op. If a
-     * particular class needs to do something special, then it should
-     * override this method. In particular, if this instance did not
-     * know its write size up-front, then this method is responsible
-     * for setting it.
-     *
-     * @param addedTo {@code non-null;} the section this instance has been added to
-     * @param offset {@code >= 0;} the offset from the start of the
-     * section where this instance was placed
-     */
-    protected void place0(Section addedTo, int offset) {
-        // This space intentionally left blank.
+    if (offset < 0) {
+      throw new IllegalArgumentException("offset < 0");
     }
 
-    /**
-     * Performs the actual write of the contents of this instance to
-     * the given data section. This is called by {@link #writeTo},
-     * which will have taken care of ensuring alignment.
-     *
-     * @param file {@code non-null;} the file to use for reference
-     * @param out {@code non-null;} where to write to
-     */
-    protected abstract void writeTo0(DexFile file, AnnotatedOutput out);
+    if (this.addedTo != null) {
+      throw new RuntimeException("already written");
+    }
+
+    int mask = alignment - 1;
+    offset = (offset + mask) & ~mask;
+
+    this.addedTo = addedTo;
+    this.offset = offset;
+
+    place0(addedTo, offset);
+
+    return offset;
+  }
+
+  /**
+   * Gets the alignment requirement of this instance. An instance should
+   * only be written when so aligned.
+   *
+   * @return {@code > 0;} the alignment requirement; must be a power of 2
+   */
+  public final int getAlignment() {
+    return alignment;
+  }
+
+  /**
+   * Gets the absolute offset of this item as a string, suitable for
+   * including in annotations.
+   *
+   * @return {@code non-null;} the offset string
+   */
+  public final String offsetString() {
+    return '[' + Integer.toHexString(getAbsoluteOffset()) + ']';
+  }
+
+  /**
+   * Gets a short human-readable string representing this instance.
+   *
+   * @return {@code non-null;} the human form
+   */
+  public abstract String toHuman();
+
+  /**
+   * Compares this instance to another which is guaranteed to be of
+   * the same class. The default implementation of this method is to
+   * throw an exception (unsupported operation). If a particular
+   * class needs to actually sort, then it should override this
+   * method.
+   *
+   * @param other {@code non-null;} instance to compare to
+   * @return {@code -1}, {@code 0}, or {@code 1}, depending
+   * on the sort order of this instance and the other
+   */
+  protected int compareTo0(OffsettedItem other) {
+    throw new UnsupportedOperationException("unsupported");
+  }
+
+  /**
+   * Does additional work required when placing an instance. The
+   * default implementation of this method is a no-op. If a
+   * particular class needs to do something special, then it should
+   * override this method. In particular, if this instance did not
+   * know its write size up-front, then this method is responsible
+   * for setting it.
+   *
+   * @param addedTo {@code non-null;} the section this instance has been added to
+   * @param offset {@code >= 0;} the offset from the start of the
+   * section where this instance was placed
+   */
+  protected void place0(Section addedTo, int offset) {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Performs the actual write of the contents of this instance to
+   * the given data section. This is called by {@link #writeTo},
+   * which will have taken care of ensuring alignment.
+   *
+   * @param file {@code non-null;} the file to use for reference
+   * @param out {@code non-null;} where to write to
+   */
+  protected abstract void writeTo0(DexFile file, AnnotatedOutput out);
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ParameterAnnotationStruct.java b/dx/src/com/android/jack/dx/dex/file/ParameterAnnotationStruct.java
index 57c4db5..c8ad228 100644
--- a/dx/src/com/android/jack/dx/dex/file/ParameterAnnotationStruct.java
+++ b/dx/src/com/android/jack/dx/dex/file/ParameterAnnotationStruct.java
@@ -28,134 +28,135 @@
 /**
  * Association of a method and its parameter annotations.
  */
-public final class ParameterAnnotationStruct
-        implements ToHuman, Comparable<ParameterAnnotationStruct> {
-    /** {@code non-null;} the method in question */
-    private final CstMethodRef method;
+public final class ParameterAnnotationStruct implements ToHuman,
+    Comparable<ParameterAnnotationStruct> {
+  /** {@code non-null;} the method in question */
+  private final CstMethodRef method;
 
-    /** {@code non-null;} the associated annotations list */
-    private final AnnotationsList annotationsList;
+  /** {@code non-null;} the associated annotations list */
+  private final AnnotationsList annotationsList;
 
-    /** {@code non-null;} the associated annotations list, as an item */
-    private final UniformListItem<AnnotationSetRefItem> annotationsItem;
+  /** {@code non-null;} the associated annotations list, as an item */
+  private final UniformListItem<AnnotationSetRefItem> annotationsItem;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the method in question
-     * @param annotationsList {@code non-null;} the associated annotations list
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the method in question
+   * @param annotationsList {@code non-null;} the associated annotations list
+   */
+  public ParameterAnnotationStruct(CstMethodRef method, AnnotationsList annotationsList) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
+    }
+
+    if (annotationsList == null) {
+      throw new NullPointerException("annotationsList == null");
+    }
+
+    this.method = method;
+    this.annotationsList = annotationsList;
+
+    /*
+     * Construct an item for the annotations list. TODO(dx team): This
+     * requires way too much copying; fix it.
      */
-    public ParameterAnnotationStruct(CstMethodRef method,
-            AnnotationsList annotationsList) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
 
-        if (annotationsList == null) {
-            throw new NullPointerException("annotationsList == null");
-        }
+int size = annotationsList.size();
+    ArrayList<AnnotationSetRefItem> arrayList = new ArrayList<AnnotationSetRefItem>(size);
 
-        this.method = method;
-        this.annotationsList = annotationsList;
-
-        /*
-         * Construct an item for the annotations list. TODO: This
-         * requires way too much copying; fix it.
-         */
-
-        int size = annotationsList.size();
-        ArrayList<AnnotationSetRefItem> arrayList = new
-            ArrayList<AnnotationSetRefItem>(size);
-
-        for (int i = 0; i < size; i++) {
-            Annotations annotations = annotationsList.get(i);
-            AnnotationSetItem item = new AnnotationSetItem(annotations);
-            arrayList.add(new AnnotationSetRefItem(item));
-        }
-
-        this.annotationsItem = new UniformListItem<AnnotationSetRefItem>(
-                ItemType.TYPE_ANNOTATION_SET_REF_LIST, arrayList);
+    for (int i = 0; i < size; i++) {
+      Annotations annotations = annotationsList.get(i);
+      AnnotationSetItem item = new AnnotationSetItem(annotations);
+      arrayList.add(new AnnotationSetRefItem(item));
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        return method.hashCode();
+    this.annotationsItem =
+        new UniformListItem<AnnotationSetRefItem>(ItemType.TYPE_ANNOTATION_SET_REF_LIST, arrayList);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return method.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof ParameterAnnotationStruct)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public boolean equals(Object other) {
-        if (! (other instanceof ParameterAnnotationStruct)) {
-            return false;
-        }
+    return method.equals(((ParameterAnnotationStruct) other).method);
+  }
 
-        return method.equals(((ParameterAnnotationStruct) other).method);
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(ParameterAnnotationStruct other) {
+    return method.compareTo(other.method);
+  }
+
+  /** {@inheritDoc} */
+  public void addContents(DexFile file) {
+    MethodIdsSection methodIds = file.getMethodIds();
+    MixedItemSection wordData = file.getWordData();
+
+    methodIds.intern(method);
+    wordData.add(annotationsItem);
+  }
+
+  /** {@inheritDoc} */
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int methodIdx = file.getMethodIds().indexOf(method);
+    int annotationsOff = annotationsItem.getAbsoluteOffset();
+
+    if (out.annotates()) {
+      out.annotate(0, "    " + method.toHuman());
+      out.annotate(4, "      method_idx:      " + Hex.u4(methodIdx));
+      out.annotate(4, "      annotations_off: " + Hex.u4(annotationsOff));
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(ParameterAnnotationStruct other) {
-        return method.compareTo(other.method);
+    out.writeInt(methodIdx);
+    out.writeInt(annotationsOff);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    StringBuilder sb = new StringBuilder();
+
+    sb.append(method.toHuman());
+    sb.append(": ");
+
+    boolean first = true;
+    for (AnnotationSetRefItem item : annotationsItem.getItems()) {
+      if (first) {
+        first = false;
+      } else {
+        sb.append(", ");
+      }
+      sb.append(item.toHuman());
     }
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        MethodIdsSection methodIds = file.getMethodIds();
-        MixedItemSection wordData = file.getWordData();
+    return sb.toString();
+  }
 
-        methodIds.intern(method);
-        wordData.add(annotationsItem);
-    }
+  /**
+   * Gets the method this item is for.
+   *
+   * @return {@code non-null;} the method
+   */
+  public CstMethodRef getMethod() {
+    return method;
+  }
 
-    /** {@inheritDoc} */
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int methodIdx = file.getMethodIds().indexOf(method);
-        int annotationsOff = annotationsItem.getAbsoluteOffset();
-
-        if (out.annotates()) {
-            out.annotate(0, "    " + method.toHuman());
-            out.annotate(4, "      method_idx:      " + Hex.u4(methodIdx));
-            out.annotate(4, "      annotations_off: " +
-                    Hex.u4(annotationsOff));
-        }
-
-        out.writeInt(methodIdx);
-        out.writeInt(annotationsOff);
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        StringBuilder sb = new StringBuilder();
-
-        sb.append(method.toHuman());
-        sb.append(": ");
-
-        boolean first = true;
-        for (AnnotationSetRefItem item : annotationsItem.getItems()) {
-            if (first) {
-                first = false;
-            } else {
-                sb.append(", ");
-            }
-            sb.append(item.toHuman());
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * Gets the method this item is for.
-     *
-     * @return {@code non-null;} the method
-     */
-    public CstMethodRef getMethod() {
-        return method;
-    }
-
-    /**
-     * Gets the associated annotations list.
-     *
-     * @return {@code non-null;} the annotations list
-     */
-    public AnnotationsList getAnnotationsList() {
-        return annotationsList;
-    }
+  /**
+   * Gets the associated annotations list.
+   *
+   * @return {@code non-null;} the annotations list
+   */
+  public AnnotationsList getAnnotationsList() {
+    return annotationsList;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ProtoIdItem.java b/dx/src/com/android/jack/dx/dex/file/ProtoIdItem.java
index 1707125..9db6c26 100644
--- a/dx/src/com/android/jack/dx/dex/file/ProtoIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/ProtoIdItem.java
@@ -28,132 +28,130 @@
  * Representation of a method prototype reference inside a Dalvik file.
  */
 public final class ProtoIdItem extends IndexedItem {
-    /** {@code non-null;} the wrapped prototype */
-    private final Prototype prototype;
+  /** {@code non-null;} the wrapped prototype */
+  private final Prototype prototype;
 
-    /** {@code non-null;} the short-form of the prototype */
-    private final CstString shortForm;
+  /** {@code non-null;} the short-form of the prototype */
+  private final CstString shortForm;
 
-    /**
-     * {@code null-ok;} the list of parameter types or {@code null} if this
-     * prototype has no parameters
-     */
-    private TypeListItem parameterTypes;
+  /**
+   * {@code null-ok;} the list of parameter types or {@code null} if this
+   * prototype has no parameters
+   */
+  private TypeListItem parameterTypes;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param prototype {@code non-null;} the constant for the prototype
-     */
-    public ProtoIdItem(Prototype prototype) {
-        if (prototype == null) {
-            throw new NullPointerException("prototype == null");
+  /**
+   * Constructs an instance.
+   *
+   * @param prototype {@code non-null;} the constant for the prototype
+   */
+  public ProtoIdItem(Prototype prototype) {
+    if (prototype == null) {
+      throw new NullPointerException("prototype == null");
+    }
+
+    this.prototype = prototype;
+    this.shortForm = makeShortForm(prototype);
+
+    StdTypeList parameters = prototype.getParameterTypes();
+    this.parameterTypes = (parameters.size() == 0) ? null : new TypeListItem(parameters);
+  }
+
+  /**
+   * Creates the short-form of the given prototype.
+   *
+   * @param prototype {@code non-null;} the prototype
+   * @return {@code non-null;} the short form
+   */
+  private static CstString makeShortForm(Prototype prototype) {
+    StdTypeList parameters = prototype.getParameterTypes();
+    int size = parameters.size();
+    StringBuilder sb = new StringBuilder(size + 1);
+
+    sb.append(shortFormCharFor(prototype.getReturnType()));
+
+    for (int i = 0; i < size; i++) {
+      sb.append(shortFormCharFor(parameters.getType(i)));
+    }
+
+    return new CstString(sb.toString());
+  }
+
+  /**
+   * Gets the short-form character for the given type.
+   *
+   * @param type {@code non-null;} the type
+   * @return the corresponding short-form character
+   */
+  private static char shortFormCharFor(Type type) {
+    char descriptorChar = type.getDescriptor().charAt(0);
+
+    if (descriptorChar == '[') {
+      return 'L';
+    }
+
+    return descriptorChar;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_PROTO_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.PROTO_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    StringIdsSection stringIds = file.getStringIds();
+    TypeIdsSection typeIds = file.getTypeIds();
+    MixedItemSection typeLists = file.getTypeLists();
+
+    typeIds.intern(prototype.getReturnType());
+    stringIds.intern(shortForm);
+
+    if (parameterTypes != null) {
+      parameterTypes = typeLists.intern(parameterTypes);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int shortyIdx = file.getStringIds().indexOf(shortForm);
+    int returnIdx = file.getTypeIds().indexOf(prototype.getReturnType());
+    int paramsOff = OffsettedItem.getAbsoluteOffsetOr0(parameterTypes);
+
+    if (out.annotates()) {
+      StringBuilder sb = new StringBuilder();
+      sb.append(prototype.getReturnType().toHuman());
+      sb.append(" proto(");
+
+      StdTypeList params = prototype.getParameterTypes();
+      int size = params.size();
+
+      for (int i = 0; i < size; i++) {
+        if (i != 0) {
+          sb.append(", ");
         }
+        sb.append(params.getType(i).toHuman());
+      }
 
-        this.prototype = prototype;
-        this.shortForm = makeShortForm(prototype);
-
-        StdTypeList parameters = prototype.getParameterTypes();
-        this.parameterTypes = (parameters.size() == 0) ? null
-            : new TypeListItem(parameters);
+      sb.append(")");
+      out.annotate(0, indexString() + ' ' + sb.toString());
+      out.annotate(4, "  shorty_idx:      " + Hex.u4(shortyIdx) + " // " + shortForm.toQuoted());
+      out.annotate(4,
+          "  return_type_idx: " + Hex.u4(returnIdx) + " // " + prototype.getReturnType().toHuman());
+      out.annotate(4, "  parameters_off:  " + Hex.u4(paramsOff));
     }
 
-    /**
-     * Creates the short-form of the given prototype.
-     *
-     * @param prototype {@code non-null;} the prototype
-     * @return {@code non-null;} the short form
-     */
-    private static CstString makeShortForm(Prototype prototype) {
-        StdTypeList parameters = prototype.getParameterTypes();
-        int size = parameters.size();
-        StringBuilder sb = new StringBuilder(size + 1);
-
-        sb.append(shortFormCharFor(prototype.getReturnType()));
-
-        for (int i = 0; i < size; i++) {
-            sb.append(shortFormCharFor(parameters.getType(i)));
-        }
-
-        return new CstString(sb.toString());
-    }
-
-    /**
-     * Gets the short-form character for the given type.
-     *
-     * @param type {@code non-null;} the type
-     * @return the corresponding short-form character
-     */
-    private static char shortFormCharFor(Type type) {
-        char descriptorChar = type.getDescriptor().charAt(0);
-
-        if (descriptorChar == '[') {
-            return 'L';
-        }
-
-        return descriptorChar;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_PROTO_ID_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.PROTO_ID_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        StringIdsSection stringIds = file.getStringIds();
-        TypeIdsSection typeIds = file.getTypeIds();
-        MixedItemSection typeLists = file.getTypeLists();
-
-        typeIds.intern(prototype.getReturnType());
-        stringIds.intern(shortForm);
-
-        if (parameterTypes != null) {
-            parameterTypes = typeLists.intern(parameterTypes);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int shortyIdx = file.getStringIds().indexOf(shortForm);
-        int returnIdx = file.getTypeIds().indexOf(prototype.getReturnType());
-        int paramsOff = OffsettedItem.getAbsoluteOffsetOr0(parameterTypes);
-
-        if (out.annotates()) {
-            StringBuilder sb = new StringBuilder();
-            sb.append(prototype.getReturnType().toHuman());
-            sb.append(" proto(");
-
-            StdTypeList params = prototype.getParameterTypes();
-            int size = params.size();
-
-            for (int i = 0; i < size; i++) {
-                if (i != 0) {
-                    sb.append(", ");
-                }
-                sb.append(params.getType(i).toHuman());
-            }
-
-            sb.append(")");
-            out.annotate(0, indexString() + ' ' + sb.toString());
-            out.annotate(4, "  shorty_idx:      " + Hex.u4(shortyIdx) +
-                    " // " + shortForm.toQuoted());
-            out.annotate(4, "  return_type_idx: " + Hex.u4(returnIdx) +
-                    " // " + prototype.getReturnType().toHuman());
-            out.annotate(4, "  parameters_off:  " + Hex.u4(paramsOff));
-        }
-
-        out.writeInt(shortyIdx);
-        out.writeInt(returnIdx);
-        out.writeInt(paramsOff);
-    }
+    out.writeInt(shortyIdx);
+    out.writeInt(returnIdx);
+    out.writeInt(paramsOff);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java b/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
index a588d00..33cb976 100644
--- a/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
@@ -29,112 +29,112 @@
  * {@code .dex} file.
  */
 public final class ProtoIdsSection extends UniformItemSection {
-    /**
-     * {@code non-null;} map from method prototypes to {@link ProtoIdItem} instances
-     */
-    private final TreeMap<Prototype, ProtoIdItem> protoIds;
+  /**
+   * {@code non-null;} map from method prototypes to {@link ProtoIdItem} instances
+   */
+  private final TreeMap<Prototype, ProtoIdItem> protoIds;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public ProtoIdsSection(DexFile file) {
-        super("proto_ids", file, 4);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public ProtoIdsSection(DexFile file) {
+    super("proto_ids", file, 4);
 
-        protoIds = new TreeMap<Prototype, ProtoIdItem>();
+    protoIds = new TreeMap<Prototype, ProtoIdItem>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return protoIds.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    throw new UnsupportedOperationException("unsupported");
+  }
+
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
+
+    int sz = protoIds.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
+
+    if (sz > 65536) {
+      throw new UnsupportedOperationException("too many proto ids");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return protoIds.values();
+    if (out.annotates()) {
+      out.annotate(4, "proto_ids_size:  " + Hex.u4(sz));
+      out.annotate(4, "proto_ids_off:   " + Hex.u4(offset));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        throw new UnsupportedOperationException("unsupported");
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
+
+  /**
+   * Interns an element into this instance.
+   *
+   * @param prototype {@code non-null;} the prototype to intern
+   * @return {@code non-null;} the interned reference
+   */
+  public ProtoIdItem intern(Prototype prototype) {
+    if (prototype == null) {
+      throw new NullPointerException("prototype == null");
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
+    throwIfPrepared();
 
-        int sz = protoIds.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
+    ProtoIdItem result = protoIds.get(prototype);
 
-        if (sz > 65536) {
-            throw new UnsupportedOperationException("too many proto ids");
-        }
-
-        if (out.annotates()) {
-            out.annotate(4, "proto_ids_size:  " + Hex.u4(sz));
-            out.annotate(4, "proto_ids_off:   " + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+    if (result == null) {
+      result = new ProtoIdItem(prototype);
+      protoIds.put(prototype, result);
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param prototype {@code non-null;} the prototype to intern
-     * @return {@code non-null;} the interned reference
-     */
-    public ProtoIdItem intern(Prototype prototype) {
-        if (prototype == null) {
-            throw new NullPointerException("prototype == null");
-        }
+    return result;
+  }
 
-        throwIfPrepared();
-
-        ProtoIdItem result = protoIds.get(prototype);
-
-        if (result == null) {
-            result = new ProtoIdItem(prototype);
-            protoIds.put(prototype, result);
-        }
-
-        return result;
+  /**
+   * Gets the index of the given prototype, which must have
+   * been added to this instance.
+   *
+   * @param prototype {@code non-null;} the prototype to look up
+   * @return {@code >= 0;} the reference's index
+   */
+  public int indexOf(Prototype prototype) {
+    if (prototype == null) {
+      throw new NullPointerException("prototype == null");
     }
 
-    /**
-     * Gets the index of the given prototype, which must have
-     * been added to this instance.
-     *
-     * @param prototype {@code non-null;} the prototype to look up
-     * @return {@code >= 0;} the reference's index
-     */
-    public int indexOf(Prototype prototype) {
-        if (prototype == null) {
-            throw new NullPointerException("prototype == null");
-        }
+    throwIfNotPrepared();
 
-        throwIfNotPrepared();
+    ProtoIdItem item = protoIds.get(prototype);
 
-        ProtoIdItem item = protoIds.get(prototype);
-
-        if (item == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return item.getIndex();
+    if (item == null) {
+      throw new IllegalArgumentException("not found");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        int idx = 0;
+    return item.getIndex();
+  }
 
-        for (Object i : items()) {
-            ((ProtoIdItem) i).setIndex(idx);
-            idx++;
-        }
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    int idx = 0;
+
+    for (Object i : items()) {
+      ((ProtoIdItem) i).setIndex(idx);
+      idx++;
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/Section.java b/dx/src/com/android/jack/dx/dex/file/Section.java
index 6b86364..46d332d 100644
--- a/dx/src/com/android/jack/dx/dex/file/Section.java
+++ b/dx/src/com/android/jack/dx/dex/file/Section.java
@@ -25,263 +25,261 @@
  * of items of some sort or other.
  */
 public abstract class Section {
-    /** {@code null-ok;} name of this part, for annotation purposes */
-    private final String name;
+  /** {@code null-ok;} name of this part, for annotation purposes */
+  private final String name;
 
-    /** {@code non-null;} file that this instance is part of */
-    private final DexFile file;
+  /** {@code non-null;} file that this instance is part of */
+  private final DexFile file;
 
-    /** {@code > 0;} alignment requirement for the final output;
-     * must be a power of 2 */
-    private final int alignment;
+  /** {@code > 0;} alignment requirement for the final output;
+   * must be a power of 2 */
+  private final int alignment;
 
-    /** {@code >= -1;} offset from the start of the file to this part, or
-     * {@code -1} if not yet known */
-    private int fileOffset;
+  /** {@code >= -1;} offset from the start of the file to this part, or
+   * {@code -1} if not yet known */
+  private int fileOffset;
 
-    /** whether {@link #prepare} has been called successfully on this
-     * instance */
-    private boolean prepared;
+  /** whether {@link #prepare} has been called successfully on this
+   * instance */
+  private boolean prepared;
 
-    /**
-     * Validates an alignment.
-     *
-     * @param alignment the alignment
-     * @throws IllegalArgumentException thrown if {@code alignment}
-     * isn't a positive power of 2
-     */
-    public static void validateAlignment(int alignment) {
-        if ((alignment <= 0) ||
-            (alignment & (alignment - 1)) != 0) {
-            throw new IllegalArgumentException("invalid alignment");
-        }
+  /**
+   * Validates an alignment.
+   *
+   * @param alignment the alignment
+   * @throws IllegalArgumentException thrown if {@code alignment}
+   * isn't a positive power of 2
+   */
+  public static void validateAlignment(int alignment) {
+    if ((alignment <= 0) || (alignment & (alignment - 1)) != 0) {
+      throw new IllegalArgumentException("invalid alignment");
+    }
+  }
+
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param name {@code null-ok;} the name of this instance, for annotation
+   * purposes
+   * @param file {@code non-null;} file that this instance is part of
+   * @param alignment {@code > 0;} alignment requirement for the final output;
+   * must be a power of 2
+   */
+  public Section(String name, DexFile file, int alignment) {
+    if (file == null) {
+      throw new NullPointerException("file == null");
     }
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param name {@code null-ok;} the name of this instance, for annotation
-     * purposes
-     * @param file {@code non-null;} file that this instance is part of
-     * @param alignment {@code > 0;} alignment requirement for the final output;
-     * must be a power of 2
-     */
-    public Section(String name, DexFile file, int alignment) {
-        if (file == null) {
-            throw new NullPointerException("file == null");
-        }
+    validateAlignment(alignment);
 
-        validateAlignment(alignment);
+    this.name = name;
+    this.file = file;
+    this.alignment = alignment;
+    this.fileOffset = -1;
+    this.prepared = false;
+  }
 
-        this.name = name;
-        this.file = file;
-        this.alignment = alignment;
-        this.fileOffset = -1;
-        this.prepared = false;
+  /**
+   * Gets the file that this instance is part of.
+   *
+   * @return {@code non-null;} the file
+   */
+  public final DexFile getFile() {
+    return file;
+  }
+
+  /**
+   * Gets the alignment for this instance's final output.
+   *
+   * @return {@code > 0;} the alignment
+   */
+  public final int getAlignment() {
+    return alignment;
+  }
+
+  /**
+   * Gets the offset from the start of the file to this part. This
+   * throws an exception if the offset has not yet been set.
+   *
+   * @return {@code >= 0;} the file offset
+   */
+  public final int getFileOffset() {
+    if (fileOffset < 0) {
+      throw new RuntimeException("fileOffset not set");
     }
 
-    /**
-     * Gets the file that this instance is part of.
-     *
-     * @return {@code non-null;} the file
-     */
-    public final DexFile getFile() {
-        return file;
+    return fileOffset;
+  }
+
+  /**
+   * Sets the file offset. It is only valid to call this method once
+   * once per instance.
+   *
+   * @param fileOffset {@code >= 0;} the desired offset from the start of the
+   * file where this for this instance
+   * @return {@code >= 0;} the offset that this instance should be placed at
+   * in order to meet its alignment constraint
+   */
+  public final int setFileOffset(int fileOffset) {
+    if (fileOffset < 0) {
+      throw new IllegalArgumentException("fileOffset < 0");
     }
 
-    /**
-     * Gets the alignment for this instance's final output.
-     *
-     * @return {@code > 0;} the alignment
-     */
-    public final int getAlignment() {
-        return alignment;
+    if (this.fileOffset >= 0) {
+      throw new RuntimeException("fileOffset already set");
     }
 
-    /**
-     * Gets the offset from the start of the file to this part. This
-     * throws an exception if the offset has not yet been set.
-     *
-     * @return {@code >= 0;} the file offset
-     */
-    public final int getFileOffset() {
-        if (fileOffset < 0) {
-            throw new RuntimeException("fileOffset not set");
-        }
+    int mask = alignment - 1;
+    fileOffset = (fileOffset + mask) & ~mask;
 
-        return fileOffset;
+    this.fileOffset = fileOffset;
+
+    return fileOffset;
+  }
+
+  /**
+   * Writes this instance to the given raw data object.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  public final void writeTo(AnnotatedOutput out) {
+    throwIfNotPrepared();
+    align(out);
+
+    int cursor = out.getCursor();
+
+    if (fileOffset < 0) {
+      fileOffset = cursor;
+    } else if (fileOffset != cursor) {
+      throw new RuntimeException(
+          "alignment mismatch: for " + this + ", at " + cursor + ", but expected " + fileOffset);
     }
 
-    /**
-     * Sets the file offset. It is only valid to call this method once
-     * once per instance.
-     *
-     * @param fileOffset {@code >= 0;} the desired offset from the start of the
-     * file where this for this instance
-     * @return {@code >= 0;} the offset that this instance should be placed at
-     * in order to meet its alignment constraint
-     */
-    public final int setFileOffset(int fileOffset) {
-        if (fileOffset < 0) {
-            throw new IllegalArgumentException("fileOffset < 0");
-        }
-
-        if (this.fileOffset >= 0) {
-            throw new RuntimeException("fileOffset already set");
-        }
-
-        int mask = alignment - 1;
-        fileOffset = (fileOffset + mask) & ~mask;
-
-        this.fileOffset = fileOffset;
-
-        return fileOffset;
+    if (out.annotates()) {
+      if (name != null) {
+        out.annotate(0, "\n" + name + ":");
+      } else if (cursor != 0) {
+        out.annotate(0, "\n");
+      }
     }
 
-    /**
-     * Writes this instance to the given raw data object.
-     *
-     * @param out {@code non-null;} where to write to
-     */
-    public final void writeTo(AnnotatedOutput out) {
-        throwIfNotPrepared();
-        align(out);
+    writeTo0(out);
+  }
 
-        int cursor = out.getCursor();
-
-        if (fileOffset < 0) {
-            fileOffset = cursor;
-        } else if (fileOffset != cursor) {
-            throw new RuntimeException("alignment mismatch: for " + this +
-                                       ", at " + cursor +
-                                       ", but expected " + fileOffset);
-        }
-
-        if (out.annotates()) {
-            if (name != null) {
-                out.annotate(0, "\n" + name + ":");
-            } else if (cursor != 0) {
-                out.annotate(0, "\n");
-            }
-        }
-
-        writeTo0(out);
+  /**
+   * Returns the absolute file offset, given an offset from the
+   * start of this instance's output. This is only valid to call
+   * once this instance has been assigned a file offset (via {@link
+   * #setFileOffset}).
+   *
+   * @param relative {@code >= 0;} the relative offset
+   * @return {@code >= 0;} the corresponding absolute file offset
+   */
+  public final int getAbsoluteOffset(int relative) {
+    if (relative < 0) {
+      throw new IllegalArgumentException("relative < 0");
     }
 
-    /**
-     * Returns the absolute file offset, given an offset from the
-     * start of this instance's output. This is only valid to call
-     * once this instance has been assigned a file offset (via {@link
-     * #setFileOffset}).
-     *
-     * @param relative {@code >= 0;} the relative offset
-     * @return {@code >= 0;} the corresponding absolute file offset
-     */
-    public final int getAbsoluteOffset(int relative) {
-        if (relative < 0) {
-            throw new IllegalArgumentException("relative < 0");
-        }
-
-        if (fileOffset < 0) {
-            throw new RuntimeException("fileOffset not yet set");
-        }
-
-        return fileOffset + relative;
+    if (fileOffset < 0) {
+      throw new RuntimeException("fileOffset not yet set");
     }
 
-    /**
-     * Returns the absolute file offset of the given item which must
-     * be contained in this section. This is only valid to call
-     * once this instance has been assigned a file offset (via {@link
-     * #setFileOffset}).
-     *
-     * <p><b>Note:</b> Subclasses must implement this as appropriate for
-     * their contents.</p>
-     *
-     * @param item {@code non-null;} the item in question
-     * @return {@code >= 0;} the item's absolute file offset
-     */
-    public abstract int getAbsoluteItemOffset(Item item);
+    return fileOffset + relative;
+  }
 
-    /**
-     * Prepares this instance for writing. This performs any necessary
-     * prerequisites, including particularly adding stuff to other
-     * sections. This method may only be called once per instance;
-     * subsequent calls will throw an exception.
-     */
-    public final void prepare() {
-        throwIfPrepared();
-        prepare0();
-        prepared = true;
+  /**
+   * Returns the absolute file offset of the given item which must
+   * be contained in this section. This is only valid to call
+   * once this instance has been assigned a file offset (via {@link
+   * #setFileOffset}).
+   *
+   * <p><b>Note:</b> Subclasses must implement this as appropriate for
+   * their contents.</p>
+   *
+   * @param item {@code non-null;} the item in question
+   * @return {@code >= 0;} the item's absolute file offset
+   */
+  public abstract int getAbsoluteItemOffset(Item item);
+
+  /**
+   * Prepares this instance for writing. This performs any necessary
+   * prerequisites, including particularly adding stuff to other
+   * sections. This method may only be called once per instance;
+   * subsequent calls will throw an exception.
+   */
+  public final void prepare() {
+    throwIfPrepared();
+    prepare0();
+    prepared = true;
+  }
+
+  /**
+   * Gets the collection of all the items in this section.
+   * It is not valid to attempt to change the returned list.
+   *
+   * @return {@code non-null;} the items
+   */
+  public abstract Collection<? extends Item> items();
+
+  /**
+   * Does the main work of {@link #prepare}.
+   */
+  protected abstract void prepare0();
+
+  /**
+   * Gets the size of this instance when output, in bytes.
+   *
+   * @return {@code >= 0;} the size of this instance, in bytes
+   */
+  public abstract int writeSize();
+
+  /**
+   * Throws an exception if {@link #prepare} has not been
+   * called on this instance.
+   */
+  protected final void throwIfNotPrepared() {
+    if (!prepared) {
+      throw new RuntimeException("not prepared");
     }
+  }
 
-    /**
-     * Gets the collection of all the items in this section.
-     * It is not valid to attempt to change the returned list.
-     *
-     * @return {@code non-null;} the items
-     */
-    public abstract Collection<? extends Item> items();
-
-    /**
-     * Does the main work of {@link #prepare}.
-     */
-    protected abstract void prepare0();
-
-    /**
-     * Gets the size of this instance when output, in bytes.
-     *
-     * @return {@code >= 0;} the size of this instance, in bytes
-     */
-    public abstract int writeSize();
-
-    /**
-     * Throws an exception if {@link #prepare} has not been
-     * called on this instance.
-     */
-    protected final void throwIfNotPrepared() {
-        if (!prepared) {
-            throw new RuntimeException("not prepared");
-        }
+  /**
+   * Throws an exception if {@link #prepare} has already been called
+   * on this instance.
+   */
+  protected final void throwIfPrepared() {
+    if (prepared) {
+      throw new RuntimeException("already prepared");
     }
+  }
 
-    /**
-     * Throws an exception if {@link #prepare} has already been called
-     * on this instance.
-     */
-    protected final void throwIfPrepared() {
-        if (prepared) {
-            throw new RuntimeException("already prepared");
-        }
-    }
+  /**
+   * Aligns the output of the given data to the alignment of this instance.
+   *
+   * @param out {@code non-null;} the output to align
+   */
+  protected final void align(AnnotatedOutput out) {
+    out.alignTo(alignment);
+  }
 
-    /**
-     * Aligns the output of the given data to the alignment of this instance.
-     *
-     * @param out {@code non-null;} the output to align
-     */
-    protected final void align(AnnotatedOutput out) {
-        out.alignTo(alignment);
-    }
+  /**
+   * Writes this instance to the given raw data object. This gets
+   * called by {@link #writeTo} after aligning the cursor of
+   * {@code out} and verifying that either the assigned file
+   * offset matches the actual cursor {@code out} or that the
+   * file offset was not previously assigned, in which case it gets
+   * assigned to {@code out}'s cursor.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  protected abstract void writeTo0(AnnotatedOutput out);
 
-    /**
-     * Writes this instance to the given raw data object. This gets
-     * called by {@link #writeTo} after aligning the cursor of
-     * {@code out} and verifying that either the assigned file
-     * offset matches the actual cursor {@code out} or that the
-     * file offset was not previously assigned, in which case it gets
-     * assigned to {@code out}'s cursor.
-     *
-     * @param out {@code non-null;} where to write to
-     */
-    protected abstract void writeTo0(AnnotatedOutput out);
-
-    /**
-     * Returns the name of this section, for annotation purposes.
-     *
-     * @return {@code null-ok;} name of this part, for annotation purposes
-     */
-    protected final String getName() {
-        return name;
-    }
+  /**
+   * Returns the name of this section, for annotation purposes.
+   *
+   * @return {@code null-ok;} name of this part, for annotation purposes
+   */
+  protected final String getName() {
+    return name;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/Statistics.java b/dx/src/com/android/jack/dx/dex/file/Statistics.java
index c31a9d8..9e75182 100644
--- a/dx/src/com/android/jack/dx/dex/file/Statistics.java
+++ b/dx/src/com/android/jack/dx/dex/file/Statistics.java
@@ -26,170 +26,169 @@
  * Statistics about the contents of a file.
  */
 public final class Statistics {
-    /** {@code non-null;} data about each type of item */
-    private final HashMap<String, Data> dataMap;
+  /** {@code non-null;} data about each type of item */
+  private final HashMap<String, Data> dataMap;
+
+  /**
+   * Constructs an instance.
+   */
+  public Statistics() {
+    dataMap = new HashMap<String, Data>(50);
+  }
+
+  /**
+   * Adds the given item to the statistics.
+   *
+   * @param item {@code non-null;} the item to add
+   */
+  public void add(Item item) {
+    String typeName = item.typeName();
+    Data data = dataMap.get(typeName);
+
+    if (data == null) {
+      dataMap.put(typeName, new Data(item, typeName));
+    } else {
+      data.add(item);
+    }
+  }
+
+  /**
+   * Adds the given list of items to the statistics.
+   *
+   * @param list {@code non-null;} the list of items to add
+   */
+  public void addAll(Section list) {
+    Collection<? extends Item> items = list.items();
+    for (Item item : items) {
+      add(item);
+    }
+  }
+
+  /**
+   * Writes the statistics as an annotation.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  public final void writeAnnotation(AnnotatedOutput out) {
+    if (dataMap.size() == 0) {
+      return;
+    }
+
+    out.annotate(0, "\nstatistics:\n");
+
+    TreeMap<String, Data> sortedData = new TreeMap<String, Data>();
+
+    for (Data data : dataMap.values()) {
+      sortedData.put(data.name, data);
+    }
+
+    for (Data data : sortedData.values()) {
+      data.writeAnnotation(out);
+    }
+  }
+
+  public String toHuman() {
+    StringBuilder sb = new StringBuilder();
+
+    sb.append("Statistics:\n");
+
+    TreeMap<String, Data> sortedData = new TreeMap<String, Data>();
+
+    for (Data data : dataMap.values()) {
+      sortedData.put(data.name, data);
+    }
+
+    for (Data data : sortedData.values()) {
+      sb.append(data.toHuman());
+    }
+
+    return sb.toString();
+  }
+
+  /**
+   * Statistical data about a particular class.
+   */
+  private static class Data {
+    /** {@code non-null;} name to use as a label */
+    private final String name;
+
+    /** {@code >= 0;} number of instances */
+    private int count;
+
+    /** {@code >= 0;} total size of instances in bytes */
+    private int totalSize;
+
+    /** {@code >= 0;} largest size of any individual item */
+    private int largestSize;
+
+    /** {@code >= 0;} smallest size of any individual item */
+    private int smallestSize;
 
     /**
-     * Constructs an instance.
+     * Constructs an instance for the given item.
+     *
+     * @param item {@code non-null;} item in question
+     * @param name {@code non-null;} type name to use
      */
-    public Statistics() {
-        dataMap = new HashMap<String, Data>(50);
+    public Data(Item item, String name) {
+      int size = item.writeSize();
+
+      this.name = name;
+      this.count = 1;
+      this.totalSize = size;
+      this.largestSize = size;
+      this.smallestSize = size;
     }
 
     /**
-     * Adds the given item to the statistics.
+     * Incorporates a new item. This assumes the type name matches.
      *
-     * @param item {@code non-null;} the item to add
+     * @param item {@code non-null;} item to incorporate
      */
     public void add(Item item) {
-        String typeName = item.typeName();
-        Data data = dataMap.get(typeName);
+      int size = item.writeSize();
 
-        if (data == null) {
-            dataMap.put(typeName, new Data(item, typeName));
-        } else {
-            data.add(item);
-        }
+      count++;
+      totalSize += size;
+
+      if (size > largestSize) {
+        largestSize = size;
+      }
+
+      if (size < smallestSize) {
+        smallestSize = size;
+      }
     }
 
     /**
-     * Adds the given list of items to the statistics.
-     *
-     * @param list {@code non-null;} the list of items to add
-     */
-    public void addAll(Section list) {
-        Collection<? extends Item> items = list.items();
-        for (Item item : items) {
-            add(item);
-        }
-    }
-
-    /**
-     * Writes the statistics as an annotation.
+     * Writes this instance as an annotation.
      *
      * @param out {@code non-null;} where to write to
      */
-    public final void writeAnnotation(AnnotatedOutput out) {
-        if (dataMap.size() == 0) {
-            return;
-        }
-
-        out.annotate(0, "\nstatistics:\n");
-
-        TreeMap<String, Data> sortedData = new TreeMap<String, Data>();
-
-        for (Data data : dataMap.values()) {
-            sortedData.put(data.name, data);
-        }
-
-        for (Data data : sortedData.values()) {
-            data.writeAnnotation(out);
-        }
-    }
-
-    public String toHuman() {
-        StringBuilder sb = new StringBuilder();
-
-        sb.append("Statistics:\n");
-
-        TreeMap<String, Data> sortedData = new TreeMap<String, Data>();
-
-        for (Data data : dataMap.values()) {
-            sortedData.put(data.name, data);
-        }
-
-        for (Data data : sortedData.values()) {
-            sb.append(data.toHuman());
-        }
-
-        return sb.toString();
+    public void writeAnnotation(AnnotatedOutput out) {
+      out.annotate(toHuman());
     }
 
     /**
-     * Statistical data about a particular class.
+     * Generates a human-readable string for this data item.
+     *
+     * @return string for human consumption.
      */
-    private static class Data {
-        /** {@code non-null;} name to use as a label */
-        private final String name;
+    public String toHuman() {
+      StringBuilder sb = new StringBuilder();
 
-        /** {@code >= 0;} number of instances */
-        private int count;
+      sb.append("  " + name + ": " + count + " item" + (count == 1 ? "" : "s") + "; " + totalSize
+          + " bytes total\n");
 
-        /** {@code >= 0;} total size of instances in bytes */
-        private int totalSize;
+      if (smallestSize == largestSize) {
+        sb.append("    " + smallestSize + " bytes/item\n");
+      } else {
+        int average = totalSize / count;
+        sb.append(
+            "    " + smallestSize + ".." + largestSize + " bytes/item; average " + average + "\n");
+      }
 
-        /** {@code >= 0;} largest size of any individual item */
-        private int largestSize;
-
-        /** {@code >= 0;} smallest size of any individual item */
-        private int smallestSize;
-
-        /**
-         * Constructs an instance for the given item.
-         *
-         * @param item {@code non-null;} item in question
-         * @param name {@code non-null;} type name to use
-         */
-        public Data(Item item, String name) {
-            int size = item.writeSize();
-
-            this.name = name;
-            this.count = 1;
-            this.totalSize = size;
-            this.largestSize = size;
-            this.smallestSize = size;
-        }
-
-        /**
-         * Incorporates a new item. This assumes the type name matches.
-         *
-         * @param item {@code non-null;} item to incorporate
-         */
-        public void add(Item item) {
-            int size = item.writeSize();
-
-            count++;
-            totalSize += size;
-
-            if (size > largestSize) {
-                largestSize = size;
-            }
-
-            if (size < smallestSize) {
-                smallestSize = size;
-            }
-        }
-
-        /**
-         * Writes this instance as an annotation.
-         *
-         * @param out {@code non-null;} where to write to
-         */
-        public void writeAnnotation(AnnotatedOutput out) {
-            out.annotate(toHuman());
-        }
-
-        /**
-         * Generates a human-readable string for this data item.
-         *
-         * @return string for human consumption.
-         */
-        public String toHuman() {
-            StringBuilder sb = new StringBuilder();
-
-            sb.append("  " + name + ": " +
-                         count + " item" + (count == 1 ? "" : "s") + "; " +
-                         totalSize + " bytes total\n");
-
-            if (smallestSize == largestSize) {
-                sb.append("    " + smallestSize + " bytes/item\n");
-            } else {
-                int average = totalSize / count;
-                sb.append("    " + smallestSize + ".." + largestSize +
-                             " bytes/item; average " + average + "\n");
-            }
-
-            return sb.toString();
-        }
+      return sb.toString();
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/StringDataItem.java b/dx/src/com/android/jack/dx/dex/file/StringDataItem.java
index ee91266..bf15879 100644
--- a/dx/src/com/android/jack/dx/dex/file/StringDataItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/StringDataItem.java
@@ -26,74 +26,72 @@
  * Representation of string data for a particular string, in a Dalvik file.
  */
 public final class StringDataItem extends OffsettedItem {
-    /** {@code non-null;} the string value */
-    private final CstString value;
+  /** {@code non-null;} the string value */
+  private final CstString value;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param value {@code non-null;} the string value
-     */
-    public StringDataItem(CstString value) {
-        super(1, writeSize(value));
+  /**
+   * Constructs an instance.
+   *
+   * @param value {@code non-null;} the string value
+   */
+  public StringDataItem(CstString value) {
+    super(1, writeSize(value));
 
-        this.value = value;
+    this.value = value;
+  }
+
+  /**
+   * Gets the write size for a given value.
+   *
+   * @param value {@code non-null;} the string value
+   * @return {@code >= 2}; the write size, in bytes
+   */
+  private static int writeSize(CstString value) {
+    int utf16Size = value.getUtf16Size();
+
+    // The +1 is for the '\0' termination byte.
+    return Leb128Utils.unsignedLeb128Size(utf16Size) + value.getUtf8Size() + 1;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_STRING_DATA_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    // Nothing to do here.
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo0(DexFile file, AnnotatedOutput out) {
+    ByteArray bytes = value.getBytes();
+    int utf16Size = value.getUtf16Size();
+
+    if (out.annotates()) {
+      out.annotate(Leb128Utils.unsignedLeb128Size(utf16Size), "utf16_size: " + Hex.u4(utf16Size));
+      out.annotate(bytes.size() + 1, value.toQuoted());
     }
 
-    /**
-     * Gets the write size for a given value.
-     *
-     * @param value {@code non-null;} the string value
-     * @return {@code >= 2}; the write size, in bytes
-     */
-    private static int writeSize(CstString value) {
-        int utf16Size = value.getUtf16Size();
+    out.writeUleb128(utf16Size);
+    out.write(bytes);
+    out.writeByte(0);
+  }
 
-        // The +1 is for the '\0' termination byte.
-        return Leb128Utils.unsignedLeb128Size(utf16Size)
-            + value.getUtf8Size() + 1;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return value.toQuoted();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_STRING_DATA_ITEM;
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(OffsettedItem other) {
+    StringDataItem otherData = (StringDataItem) other;
 
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        // Nothing to do here.
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo0(DexFile file, AnnotatedOutput out) {
-        ByteArray bytes = value.getBytes();
-        int utf16Size = value.getUtf16Size();
-
-        if (out.annotates()) {
-            out.annotate(Leb128Utils.unsignedLeb128Size(utf16Size),
-                    "utf16_size: " + Hex.u4(utf16Size));
-            out.annotate(bytes.size() + 1, value.toQuoted());
-        }
-
-        out.writeUleb128(utf16Size);
-        out.write(bytes);
-        out.writeByte(0);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        return value.toQuoted();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(OffsettedItem other) {
-        StringDataItem otherData = (StringDataItem) other;
-
-        return value.compareTo(otherData.value);
-    }
+    return value.compareTo(otherData.value);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/StringIdItem.java b/dx/src/com/android/jack/dx/dex/file/StringIdItem.java
index ec2bc18..5d2e74a 100644
--- a/dx/src/com/android/jack/dx/dex/file/StringIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/StringIdItem.java
@@ -24,103 +24,103 @@
 /**
  * Representation of a string inside a Dalvik file.
  */
-public final class StringIdItem
-        extends IndexedItem implements Comparable {
-    /** {@code non-null;} the string value */
-    private final CstString value;
+public final class StringIdItem extends IndexedItem implements Comparable<StringIdItem> {
+  /** {@code non-null;} the string value */
+  private final CstString value;
 
-    /** {@code null-ok;} associated string data object, if known */
-    private StringDataItem data;
+  /** {@code null-ok;} associated string data object, if known */
+  private StringDataItem data;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param value {@code non-null;} the string value
-     */
-    public StringIdItem(CstString value) {
-        if (value == null) {
-            throw new NullPointerException("value == null");
-        }
-
-        this.value = value;
-        this.data = null;
+  /**
+   * Constructs an instance.
+   *
+   * @param value {@code non-null;} the string value
+   */
+  public StringIdItem(CstString value) {
+    if (value == null) {
+      throw new NullPointerException("value == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof StringIdItem)) {
-            return false;
-        }
+    this.value = value;
+    this.data = null;
+  }
 
-        StringIdItem otherString = (StringIdItem) other;
-        return value.equals(otherString.value);
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof StringIdItem)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return value.hashCode();
+    StringIdItem otherString = (StringIdItem) other;
+    return value.equals(otherString.value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return value.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(StringIdItem other) {
+    StringIdItem otherString = (StringIdItem) other;
+    return value.compareTo(otherString.value);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_STRING_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.STRING_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    if (data == null) {
+      // The string data hasn't yet been added, so add it.
+      MixedItemSection stringData = file.getStringData();
+      data = new StringDataItem(value);
+      stringData.add(data);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    int dataOff = data.getAbsoluteOffset();
+
+    if (out.annotates()) {
+      out.annotate(0, indexString() + ' ' + value.toQuoted(100));
+      out.annotate(4, "  string_data_off: " + Hex.u4(dataOff));
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(Object other) {
-        StringIdItem otherString = (StringIdItem) other;
-        return value.compareTo(otherString.value);
-    }
+    out.writeInt(dataOff);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_STRING_ID_ITEM;
-    }
+  /**
+   * Gets the string value.
+   *
+   * @return {@code non-null;} the value
+   */
+  public CstString getValue() {
+    return value;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.STRING_ID_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        if (data == null) {
-            // The string data hasn't yet been added, so add it.
-            MixedItemSection stringData = file.getStringData();
-            data = new StringDataItem(value);
-            stringData.add(data);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        int dataOff = data.getAbsoluteOffset();
-
-        if (out.annotates()) {
-            out.annotate(0, indexString() + ' ' + value.toQuoted(100));
-            out.annotate(4, "  string_data_off: " + Hex.u4(dataOff));
-        }
-
-        out.writeInt(dataOff);
-    }
-
-    /**
-     * Gets the string value.
-     *
-     * @return {@code non-null;} the value
-     */
-    public CstString getValue() {
-        return value;
-    }
-
-    /**
-     * Gets the associated data object for this instance, if known.
-     *
-     * @return {@code null-ok;} the associated data object or {@code null}
-     * if not yet known
-     */
-    public StringDataItem getData() {
-        return data;
-    }
+  /**
+   * Gets the associated data object for this instance, if known.
+   *
+   * @return {@code null-ok;} the associated data object or {@code null}
+   * if not yet known
+   */
+  public StringDataItem getData() {
+    return data;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/StringIdsSection.java b/dx/src/com/android/jack/dx/dex/file/StringIdsSection.java
index d09563e..b9d6c0d 100644
--- a/dx/src/com/android/jack/dx/dex/file/StringIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/StringIdsSection.java
@@ -28,155 +28,154 @@
 /**
  * Strings list section of a {@code .dex} file.
  */
-public final class StringIdsSection
-        extends UniformItemSection {
-    /**
-     * {@code non-null;} map from string constants to {@link
-     * StringIdItem} instances
-     */
-    private final TreeMap<CstString, StringIdItem> strings;
+public final class StringIdsSection extends UniformItemSection {
+  /**
+   * {@code non-null;} map from string constants to {@link
+   * StringIdItem} instances
+   */
+  private final TreeMap<CstString, StringIdItem> strings;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public StringIdsSection(DexFile file) {
-        super("string_ids", file, 4);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public StringIdsSection(DexFile file) {
+    super("string_ids", file, 4);
 
-        strings = new TreeMap<CstString, StringIdItem>();
+    strings = new TreeMap<CstString, StringIdItem>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return strings.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return strings.values();
+    throwIfNotPrepared();
+
+    IndexedItem result = strings.get(cst);
+
+    if (result == null) {
+      throw new IllegalArgumentException("not found");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
 
-        IndexedItem result = strings.get((CstString) cst);
+    int sz = strings.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
 
-        if (result == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return result;
+    if (out.annotates()) {
+      out.annotate(4, "string_ids_size: " + Hex.u4(sz));
+      out.annotate(4, "string_ids_off:  " + Hex.u4(offset));
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
 
-        int sz = strings.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
+  /**
+   * Interns an element into this instance.
+   *
+   * @param string {@code non-null;} the string to intern, as a regular Java
+   * {@code String}
+   * @return {@code non-null;} the interned string
+   */
+  public StringIdItem intern(String string) {
+    return intern(new StringIdItem(new CstString(string)));
+  }
 
-        if (out.annotates()) {
-            out.annotate(4, "string_ids_size: " + Hex.u4(sz));
-            out.annotate(4, "string_ids_off:  " + Hex.u4(offset));
-        }
+  /**
+   * Interns an element into this instance.
+   *
+   * @param string {@code non-null;} the string to intern, as a constant
+   * @return {@code non-null;} the interned string
+   */
+  public StringIdItem intern(CstString string) {
+    return intern(new StringIdItem(string));
+  }
 
-        out.writeInt(sz);
-        out.writeInt(offset);
+  /**
+   * Interns an element into this instance.
+   *
+   * @param string {@code non-null;} the string to intern
+   * @return {@code non-null;} the interned string
+   */
+  public StringIdItem intern(StringIdItem string) {
+    if (string == null) {
+      throw new NullPointerException("string == null");
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param string {@code non-null;} the string to intern, as a regular Java
-     * {@code String}
-     * @return {@code non-null;} the interned string
-     */
-    public StringIdItem intern(String string) {
-        return intern(new StringIdItem(new CstString(string)));
+    throwIfPrepared();
+
+    CstString value = string.getValue();
+    StringIdItem already = strings.get(value);
+
+    if (already != null) {
+      return already;
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param string {@code non-null;} the string to intern, as a constant
-     * @return {@code non-null;} the interned string
-     */
-    public StringIdItem intern(CstString string) {
-        return intern(new StringIdItem(string));
+    strings.put(value, string);
+    return string;
+  }
+
+  /**
+   * Interns the components of a name-and-type into this instance.
+   *
+   * @param nat {@code non-null;} the name-and-type
+   */
+  public void intern(CstNat nat) {
+    intern(nat.getName());
+    intern(nat.getDescriptor());
+  }
+
+  /**
+   * Gets the index of the given string, which must have been added
+   * to this instance.
+   *
+   * @param string {@code non-null;} the string to look up
+   * @return {@code >= 0;} the string's index
+   */
+  public int indexOf(CstString string) {
+    if (string == null) {
+      throw new NullPointerException("string == null");
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param string {@code non-null;} the string to intern
-     * @return {@code non-null;} the interned string
-     */
-    public StringIdItem intern(StringIdItem string) {
-        if (string == null) {
-            throw new NullPointerException("string == null");
-        }
+    throwIfNotPrepared();
 
-        throwIfPrepared();
+    StringIdItem s = strings.get(string);
 
-        CstString value = string.getValue();
-        StringIdItem already = strings.get(value);
-
-        if (already != null) {
-            return already;
-        }
-
-        strings.put(value, string);
-        return string;
+    if (s == null) {
+      throw new IllegalArgumentException("not found");
     }
 
-    /**
-     * Interns the components of a name-and-type into this instance.
-     *
-     * @param nat {@code non-null;} the name-and-type
-     */
-    public void intern(CstNat nat) {
-        intern(nat.getName());
-        intern(nat.getDescriptor());
+    return s.getIndex();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    int idx = 0;
+
+    for (StringIdItem s : strings.values()) {
+      s.setIndex(idx);
+      idx++;
     }
-
-    /**
-     * Gets the index of the given string, which must have been added
-     * to this instance.
-     *
-     * @param string {@code non-null;} the string to look up
-     * @return {@code >= 0;} the string's index
-     */
-    public int indexOf(CstString string) {
-        if (string == null) {
-            throw new NullPointerException("string == null");
-        }
-
-        throwIfNotPrepared();
-
-        StringIdItem s = strings.get(string);
-
-        if (s == null) {
-            throw new IllegalArgumentException("not found");
-        }
-
-        return s.getIndex();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        int idx = 0;
-
-        for (StringIdItem s : strings.values()) {
-            s.setIndex(idx);
-            idx++;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/TypeIdItem.java b/dx/src/com/android/jack/dx/dex/file/TypeIdItem.java
index cdbfb44..417afb5 100644
--- a/dx/src/com/android/jack/dx/dex/file/TypeIdItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/TypeIdItem.java
@@ -26,45 +26,45 @@
  * Representation of a type reference inside a Dalvik file.
  */
 public final class TypeIdItem extends IdItem {
-    /**
-     * Constructs an instance.
-     *
-     * @param type {@code non-null;} the constant for the type
-     */
-    public TypeIdItem(CstType type) {
-        super(type);
+  /**
+   * Constructs an instance.
+   *
+   * @param type {@code non-null;} the constant for the type
+   */
+  public TypeIdItem(CstType type) {
+    super(type);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_TYPE_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSize() {
+    return SizeOf.TYPE_ID_ITEM;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    file.getStringIds().intern(getDefiningClass().getDescriptor());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeTo(DexFile file, AnnotatedOutput out) {
+    CstType type = getDefiningClass();
+    CstString descriptor = type.getDescriptor();
+    int idx = file.getStringIds().indexOf(descriptor);
+
+    if (out.annotates()) {
+      out.annotate(0, indexString() + ' ' + descriptor.toHuman());
+      out.annotate(4, "  descriptor_idx: " + Hex.u4(idx));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_TYPE_ID_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int writeSize() {
-        return SizeOf.TYPE_ID_ITEM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        file.getStringIds().intern(getDefiningClass().getDescriptor());
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void writeTo(DexFile file, AnnotatedOutput out) {
-        CstType type = getDefiningClass();
-        CstString descriptor = type.getDescriptor();
-        int idx = file.getStringIds().indexOf(descriptor);
-
-        if (out.annotates()) {
-            out.annotate(0, indexString() + ' ' + descriptor.toHuman());
-            out.annotate(4, "  descriptor_idx: " + Hex.u4(idx));
-        }
-
-        out.writeInt(idx);
-    }
+    out.writeInt(idx);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/TypeIdsSection.java b/dx/src/com/android/jack/dx/dex/file/TypeIdsSection.java
index fede94e..34599c0 100644
--- a/dx/src/com/android/jack/dx/dex/file/TypeIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/TypeIdsSection.java
@@ -29,164 +29,164 @@
  * Type identifiers list section of a {@code .dex} file.
  */
 public final class TypeIdsSection extends UniformItemSection {
-    /**
-     * {@code non-null;} map from types to {@link TypeIdItem} instances
-     */
-    private final TreeMap<Type, TypeIdItem> typeIds;
+  /**
+   * {@code non-null;} map from types to {@link TypeIdItem} instances
+   */
+  private final TreeMap<Type, TypeIdItem> typeIds;
 
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param file {@code non-null;} file that this instance is part of
-     */
-    public TypeIdsSection(DexFile file) {
-        super("type_ids", file, 4);
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param file {@code non-null;} file that this instance is part of
+   */
+  public TypeIdsSection(DexFile file) {
+    super("type_ids", file, 4);
 
-        typeIds = new TreeMap<Type, TypeIdItem>();
+    typeIds = new TreeMap<Type, TypeIdItem>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Collection<? extends Item> items() {
+    return typeIds.values();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public IndexedItem get(Constant cst) {
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Collection<? extends Item> items() {
-        return typeIds.values();
+    throwIfNotPrepared();
+
+    Type type = ((CstType) cst).getClassType();
+    IndexedItem result = typeIds.get(type);
+
+    if (result == null) {
+      throw new IllegalArgumentException("not found: " + cst);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public IndexedItem get(Constant cst) {
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
+  /**
+   * Writes the portion of the file header that refers to this instance.
+   *
+   * @param out {@code non-null;} where to write
+   */
+  public void writeHeaderPart(AnnotatedOutput out) {
+    throwIfNotPrepared();
 
-        Type type = ((CstType) cst).getClassType();
-        IndexedItem result = typeIds.get(type);
+    int sz = typeIds.size();
+    int offset = (sz == 0) ? 0 : getFileOffset();
 
-        if (result == null) {
-            throw new IllegalArgumentException("not found: " + cst);
-        }
-
-        return result;
+    if (sz > 65536) {
+      throw new UnsupportedOperationException("too many type ids");
     }
 
-    /**
-     * Writes the portion of the file header that refers to this instance.
-     *
-     * @param out {@code non-null;} where to write
-     */
-    public void writeHeaderPart(AnnotatedOutput out) {
-        throwIfNotPrepared();
-
-        int sz = typeIds.size();
-        int offset = (sz == 0) ? 0 : getFileOffset();
-
-        if (sz > 65536) {
-            throw new UnsupportedOperationException("too many type ids");
-        }
-
-        if (out.annotates()) {
-            out.annotate(4, "type_ids_size:   " + Hex.u4(sz));
-            out.annotate(4, "type_ids_off:    " + Hex.u4(offset));
-        }
-
-        out.writeInt(sz);
-        out.writeInt(offset);
+    if (out.annotates()) {
+      out.annotate(4, "type_ids_size:   " + Hex.u4(sz));
+      out.annotate(4, "type_ids_off:    " + Hex.u4(offset));
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param type {@code non-null;} the type to intern
-     * @return {@code non-null;} the interned reference
-     */
-    public TypeIdItem intern(Type type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
+    out.writeInt(sz);
+    out.writeInt(offset);
+  }
 
-        throwIfPrepared();
-
-        TypeIdItem result = typeIds.get(type);
-
-        if (result == null) {
-            result = new TypeIdItem(new CstType(type));
-            typeIds.put(type, result);
-        }
-
-        return result;
+  /**
+   * Interns an element into this instance.
+   *
+   * @param type {@code non-null;} the type to intern
+   * @return {@code non-null;} the interned reference
+   */
+  public TypeIdItem intern(Type type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /**
-     * Interns an element into this instance.
-     *
-     * @param type {@code non-null;} the type to intern
-     * @return {@code non-null;} the interned reference
-     */
-    public TypeIdItem intern(CstType type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
+    throwIfPrepared();
 
-        throwIfPrepared();
+    TypeIdItem result = typeIds.get(type);
 
-        Type typePerSe = type.getClassType();
-        TypeIdItem result = typeIds.get(typePerSe);
-
-        if (result == null) {
-            result = new TypeIdItem(type);
-            typeIds.put(typePerSe, result);
-        }
-
-        return result;
+    if (result == null) {
+      result = new TypeIdItem(new CstType(type));
+      typeIds.put(type, result);
     }
 
-    /**
-     * Gets the index of the given type, which must have
-     * been added to this instance.
-     *
-     * @param type {@code non-null;} the type to look up
-     * @return {@code >= 0;} the reference's index
-     */
-    public int indexOf(Type type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
+    return result;
+  }
 
-        throwIfNotPrepared();
-
-        TypeIdItem item = typeIds.get(type);
-
-        if (item == null) {
-            throw new IllegalArgumentException("not found: " + type);
-        }
-
-        return item.getIndex();
+  /**
+   * Interns an element into this instance.
+   *
+   * @param type {@code non-null;} the type to intern
+   * @return {@code non-null;} the interned reference
+   */
+  public TypeIdItem intern(CstType type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /**
-     * Gets the index of the given type, which must have
-     * been added to this instance.
-     *
-     * @param type {@code non-null;} the type to look up
-     * @return {@code >= 0;} the reference's index
-     */
-    public int indexOf(CstType type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
+    throwIfPrepared();
 
-        return indexOf(type.getClassType());
+    Type typePerSe = type.getClassType();
+    TypeIdItem result = typeIds.get(typePerSe);
+
+    if (result == null) {
+      result = new TypeIdItem(type);
+      typeIds.put(typePerSe, result);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected void orderItems() {
-        int idx = 0;
+    return result;
+  }
 
-        for (Object i : items()) {
-            ((TypeIdItem) i).setIndex(idx);
-            idx++;
-        }
+  /**
+   * Gets the index of the given type, which must have
+   * been added to this instance.
+   *
+   * @param type {@code non-null;} the type to look up
+   * @return {@code >= 0;} the reference's index
+   */
+  public int indexOf(Type type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
+
+    throwIfNotPrepared();
+
+    TypeIdItem item = typeIds.get(type);
+
+    if (item == null) {
+      throw new IllegalArgumentException("not found: " + type);
+    }
+
+    return item.getIndex();
+  }
+
+  /**
+   * Gets the index of the given type, which must have
+   * been added to this instance.
+   *
+   * @param type {@code non-null;} the type to look up
+   * @return {@code >= 0;} the reference's index
+   */
+  public int indexOf(CstType type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
+    }
+
+    return indexOf(type.getClassType());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void orderItems() {
+    int idx = 0;
+
+    for (Object i : items()) {
+      ((TypeIdItem) i).setIndex(idx);
+      idx++;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/TypeListItem.java b/dx/src/com/android/jack/dx/dex/file/TypeListItem.java
index 42c1c5a..263d2b4 100644
--- a/dx/src/com/android/jack/dx/dex/file/TypeListItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/TypeListItem.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.dx.dex.file;
 
-import com.android.jack.dx.rop.cst.CstType;
 import com.android.jack.dx.rop.type.StdTypeList;
 import com.android.jack.dx.rop.type.Type;
 import com.android.jack.dx.rop.type.TypeList;
@@ -27,96 +26,96 @@
  * Representation of a list of class references.
  */
 public final class TypeListItem extends OffsettedItem {
-    /** alignment requirement */
-    private static final int ALIGNMENT = 4;
+  /** alignment requirement */
+  private static final int ALIGNMENT = 4;
 
-    /** element size in bytes */
-    private static final int ELEMENT_SIZE = 2;
+  /** element size in bytes */
+  private static final int ELEMENT_SIZE = 2;
 
-    /** header size in bytes */
-    private static final int HEADER_SIZE = 4;
+  /** header size in bytes */
+  private static final int HEADER_SIZE = 4;
 
-    /** {@code non-null;} the actual list */
-    private final TypeList list;
+  /** {@code non-null;} the actual list */
+  private final TypeList list;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param list {@code non-null;} the actual list
-     */
-    public TypeListItem(TypeList list) {
-        super(ALIGNMENT, (list.size() * ELEMENT_SIZE) + HEADER_SIZE);
+  /**
+   * Constructs an instance.
+   *
+   * @param list {@code non-null;} the actual list
+   */
+  public TypeListItem(TypeList list) {
+    super(ALIGNMENT, (list.size() * ELEMENT_SIZE) + HEADER_SIZE);
 
-        this.list = list;
+    this.list = list;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return StdTypeList.hashContents(list);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return ItemType.TYPE_TYPE_LIST;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    int sz = list.size();
+
+    for (int i = 0; i < sz; i++) {
+      typeIds.intern(list.getType(i));
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    throw new RuntimeException("unsupported");
+  }
+
+  /**
+   * Gets the underlying list.
+   *
+   * @return {@code non-null;} the list
+   */
+  public TypeList getList() {
+    return list;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    int sz = list.size();
+
+    if (out.annotates()) {
+      out.annotate(0, offsetString() + " type_list");
+      out.annotate(HEADER_SIZE, "  size: " + Hex.u4(sz));
+      for (int i = 0; i < sz; i++) {
+        Type one = list.getType(i);
+        int idx = typeIds.indexOf(one);
+        out.annotate(ELEMENT_SIZE, "  " + Hex.u2(idx) + " // " + one.toHuman());
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return StdTypeList.hashContents(list);
+    out.writeInt(sz);
+
+    for (int i = 0; i < sz; i++) {
+      out.writeShort(typeIds.indexOf(list.getType(i)));
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return ItemType.TYPE_TYPE_LIST;
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(OffsettedItem other) {
+    TypeList thisList = this.list;
+    TypeList otherList = ((TypeListItem) other).list;
 
-    /** {@inheritDoc} */
-    public void addContents(DexFile file) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        int sz = list.size();
-
-        for (int i = 0; i < sz; i++) {
-            typeIds.intern(list.getType(i));
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toHuman() {
-        throw new RuntimeException("unsupported");
-    }
-
-    /**
-     * Gets the underlying list.
-     *
-     * @return {@code non-null;} the list
-     */
-    public TypeList getList() {
-        return list;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        int sz = list.size();
-
-        if (out.annotates()) {
-            out.annotate(0, offsetString() + " type_list");
-            out.annotate(HEADER_SIZE, "  size: " + Hex.u4(sz));
-            for (int i = 0; i < sz; i++) {
-                Type one = list.getType(i);
-                int idx = typeIds.indexOf(one);
-                out.annotate(ELEMENT_SIZE,
-                             "  " + Hex.u2(idx) + " // " + one.toHuman());
-            }
-        }
-
-        out.writeInt(sz);
-
-        for (int i = 0; i < sz; i++) {
-            out.writeShort(typeIds.indexOf(list.getType(i)));
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(OffsettedItem other) {
-        TypeList thisList = this.list;
-        TypeList otherList = ((TypeListItem) other).list;
-
-        return StdTypeList.compareContents(thisList, otherList);
-    }
+    return StdTypeList.compareContents(thisList, otherList);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/UniformItemSection.java b/dx/src/com/android/jack/dx/dex/file/UniformItemSection.java
index 0e4502d..82fea3b 100644
--- a/dx/src/com/android/jack/dx/dex/file/UniformItemSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/UniformItemSection.java
@@ -27,86 +27,86 @@
  * the output.
  */
 public abstract class UniformItemSection extends Section {
-    /**
-     * Constructs an instance. The file offset is initially unknown.
-     *
-     * @param name {@code null-ok;} the name of this instance, for annotation
-     * purposes
-     * @param file {@code non-null;} file that this instance is part of
-     * @param alignment {@code > 0;} alignment requirement for the final output;
-     * must be a power of 2
+  /**
+   * Constructs an instance. The file offset is initially unknown.
+   *
+   * @param name {@code null-ok;} the name of this instance, for annotation
+   * purposes
+   * @param file {@code non-null;} file that this instance is part of
+   * @param alignment {@code > 0;} alignment requirement for the final output;
+   * must be a power of 2
+   */
+  public UniformItemSection(String name, DexFile file, int alignment) {
+    super(name, file, alignment);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int writeSize() {
+    Collection<? extends Item> items = items();
+    int sz = items.size();
+
+    if (sz == 0) {
+      return 0;
+    }
+
+    // Since each item has to be the same size, we can pick any.
+    return sz * items.iterator().next().writeSize();
+  }
+
+  /**
+   * Gets the item corresponding to the given {@link Constant}. This
+   * will throw an exception if the constant is not found, including
+   * if this instance isn't the sort that maps constants to {@link
+   * IndexedItem} instances.
+   *
+   * @param cst {@code non-null;} constant to look for
+   * @return {@code non-null;} the corresponding item found in this instance
+   */
+  public abstract IndexedItem get(Constant cst);
+
+  /** {@inheritDoc} */
+  @Override
+  protected final void prepare0() {
+    DexFile file = getFile();
+
+    orderItems();
+
+    for (Item one : items()) {
+      one.addContents(file);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected final void writeTo0(AnnotatedOutput out) {
+    DexFile file = getFile();
+    int alignment = getAlignment();
+
+    for (Item one : items()) {
+      one.writeTo(file, out);
+      out.alignTo(alignment);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int getAbsoluteItemOffset(Item item) {
+    /*
+     * Since all items must be the same size, we can use the size
+     * of the one we're given to calculate its offset.
      */
-    public UniformItemSection(String name, DexFile file, int alignment) {
-        super(name, file, alignment);
-    }
+    IndexedItem ii = (IndexedItem) item;
+    int relativeOffset = ii.getIndex() * ii.writeSize();
 
-    /** {@inheritDoc} */
-    @Override
-    public final int writeSize() {
-        Collection<? extends Item> items = items();
-        int sz = items.size();
+    return getAbsoluteOffset(relativeOffset);
+  }
 
-        if (sz == 0) {
-            return 0;
-        }
-
-        // Since each item has to be the same size, we can pick any.
-        return sz * items.iterator().next().writeSize();
-    }
-
-    /**
-     * Gets the item corresponding to the given {@link Constant}. This
-     * will throw an exception if the constant is not found, including
-     * if this instance isn't the sort that maps constants to {@link
-     * IndexedItem} instances.
-     *
-     * @param cst {@code non-null;} constant to look for
-     * @return {@code non-null;} the corresponding item found in this instance
-     */
-    public abstract IndexedItem get(Constant cst);
-
-    /** {@inheritDoc} */
-    @Override
-    protected final void prepare0() {
-        DexFile file = getFile();
-
-        orderItems();
-
-        for (Item one : items()) {
-            one.addContents(file);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected final void writeTo0(AnnotatedOutput out) {
-        DexFile file = getFile();
-        int alignment = getAlignment();
-
-        for (Item one : items()) {
-            one.writeTo(file, out);
-            out.alignTo(alignment);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final int getAbsoluteItemOffset(Item item) {
-        /*
-         * Since all items must be the same size, we can use the size
-         * of the one we're given to calculate its offset.
-         */
-        IndexedItem ii = (IndexedItem) item;
-        int relativeOffset = ii.getIndex() * ii.writeSize();
-
-        return getAbsoluteOffset(relativeOffset);
-    }
-
-    /**
-     * Alters or picks the order for items in this instance if desired,
-     * so that subsequent calls to {@link #items} will yield a
-     * so-ordered collection. If the items in this instance are indexed,
-     * then this method should also assign indices.
-     */
-    protected abstract void orderItems();
+  /**
+   * Alters or picks the order for items in this instance if desired,
+   * so that subsequent calls to {@link #items} will yield a
+   * so-ordered collection. If the items in this instance are indexed,
+   * then this method should also assign indices.
+   */
+  protected abstract void orderItems();
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/UniformListItem.java b/dx/src/com/android/jack/dx/dex/file/UniformListItem.java
index 1046c19..9eb36ae 100644
--- a/dx/src/com/android/jack/dx/dex/file/UniformListItem.java
+++ b/dx/src/com/android/jack/dx/dex/file/UniformListItem.java
@@ -19,7 +19,6 @@
 import com.android.jack.dx.util.AnnotatedOutput;
 import com.android.jack.dx.util.Hex;
 
-import java.util.HashMap;
 import java.util.List;
 
 /**
@@ -34,183 +33,180 @@
  *
  * @param <T> type of element contained in an instance
  */
-public final class UniformListItem<T extends OffsettedItem>
-        extends OffsettedItem {
-    /** the size of the list header */
-    private static final int HEADER_SIZE = 4;
+public final class UniformListItem<T extends OffsettedItem> extends OffsettedItem {
+  /** the size of the list header */
+  private static final int HEADER_SIZE = 4;
 
-    /** {@code non-null;} the item type */
-    private final ItemType itemType;
+  /** {@code non-null;} the item type */
+  private final ItemType itemType;
 
-    /** {@code non-null;} the contents */
-    private final List<T> items;
+  /** {@code non-null;} the contents */
+  private final List<T> items;
 
-    /**
-     * Constructs an instance. It is illegal to modify the given list once
-     * it is used to construct an instance of this class.
-     *
-     * @param itemType {@code non-null;} the type of the item
-     * @param items {@code non-null and non-empty;} list of items to represent
+  /**
+   * Constructs an instance. It is illegal to modify the given list once
+   * it is used to construct an instance of this class.
+   *
+   * @param itemType {@code non-null;} the type of the item
+   * @param items {@code non-null and non-empty;} list of items to represent
+   */
+  public UniformListItem(ItemType itemType, List<T> items) {
+    super(getAlignment(items), writeSize(items));
+
+    if (itemType == null) {
+      throw new NullPointerException("itemType == null");
+    }
+
+    this.items = items;
+    this.itemType = itemType;
+  }
+
+  /**
+   * Helper for {@link #UniformListItem}, which returns the alignment
+   * requirement implied by the given list. See the header comment for
+   * more details.
+   *
+   * @param items {@code non-null;} list of items being represented
+   * @return {@code >= 4;} the alignment requirement
+   */
+  private static int getAlignment(List<? extends OffsettedItem> items) {
+    try {
+      // Since they all must have the same alignment, any one will do.
+      return Math.max(HEADER_SIZE, items.get(0).getAlignment());
+    } catch (IndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("items.size() == 0");
+    } catch (NullPointerException ex) {
+      // Translate the exception.
+      throw new NullPointerException("items == null");
+    }
+  }
+
+  /**
+   * Calculates the write size for the given list.
+   *
+   * @param items {@code non-null;} the list in question
+   * @return {@code >= 0;} the write size
+   */
+  private static int writeSize(List<? extends OffsettedItem> items) {
+    /*
+     * This class assumes all included items are the same size,
+     * an assumption which is verified in place0().
      */
-    public UniformListItem(ItemType itemType, List<T> items) {
-        super(getAlignment(items), writeSize(items));
+    OffsettedItem first = items.get(0);
+    return (items.size() * first.writeSize()) + getAlignment(items);
+  }
 
-        if (itemType == null) {
-            throw new NullPointerException("itemType == null");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public ItemType itemType() {
+    return itemType;
+  }
 
-        this.items = items;
-        this.itemType = itemType;
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append(getClass().getName());
+    sb.append(items);
+
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addContents(DexFile file) {
+    for (OffsettedItem i : items) {
+      i.addContents(file);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final String toHuman() {
+    StringBuffer sb = new StringBuffer(100);
+    boolean first = true;
+
+    sb.append("{");
+
+    for (OffsettedItem i : items) {
+      if (first) {
+        first = false;
+      } else {
+        sb.append(", ");
+      }
+      sb.append(i.toHuman());
     }
 
-    /**
-     * Helper for {@link #UniformListItem}, which returns the alignment
-     * requirement implied by the given list. See the header comment for
-     * more details.
-     *
-     * @param items {@code non-null;} list of items being represented
-     * @return {@code >= 4;} the alignment requirement
+    sb.append("}");
+    return sb.toString();
+  }
+
+  /**
+   * Gets the underlying list of items.
+   *
+   * @return {@code non-null;} the list
+   */
+  public final List<T> getItems() {
+    return items;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void place0(Section addedTo, int offset) {
+    offset += headerSize();
+
+    boolean first = true;
+    int theSize = -1;
+    int theAlignment = -1;
+
+    for (OffsettedItem i : items) {
+      int size = i.writeSize();
+      if (first) {
+        theSize = size;
+        theAlignment = i.getAlignment();
+        first = false;
+      } else {
+        if (size != theSize) {
+          throw new UnsupportedOperationException("item size mismatch");
+        }
+        if (i.getAlignment() != theAlignment) {
+          throw new UnsupportedOperationException("item alignment mismatch");
+        }
+      }
+
+      offset = i.place(addedTo, offset) + size;
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected void writeTo0(DexFile file, AnnotatedOutput out) {
+    int size = items.size();
+
+    if (out.annotates()) {
+      out.annotate(0, offsetString() + " " + typeName());
+      out.annotate(4, "  size: " + Hex.u4(size));
+    }
+
+    out.writeInt(size);
+
+    for (OffsettedItem i : items) {
+      i.writeTo(file, out);
+    }
+  }
+
+  /**
+   * Get the size of the header of this list.
+   *
+   * @return {@code >= 0;} the header size
+   */
+  private int headerSize() {
+    /*
+     * Because of how this instance was set up, this is the same
+     * as the alignment.
      */
-    private static int getAlignment(List<? extends OffsettedItem> items) {
-        try {
-            // Since they all must have the same alignment, any one will do.
-            return Math.max(HEADER_SIZE, items.get(0).getAlignment());
-        } catch (IndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("items.size() == 0");
-        } catch (NullPointerException ex) {
-            // Translate the exception.
-            throw new NullPointerException("items == null");
-        }
-    }
-
-    /**
-     * Calculates the write size for the given list.
-     *
-     * @param items {@code non-null;} the list in question
-     * @return {@code >= 0;} the write size
-     */
-    private static int writeSize(List<? extends OffsettedItem> items) {
-        /*
-         * This class assumes all included items are the same size,
-         * an assumption which is verified in place0().
-         */
-        OffsettedItem first = items.get(0);
-        return (items.size() * first.writeSize()) + getAlignment(items);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public ItemType itemType() {
-        return itemType;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(100);
-
-        sb.append(getClass().getName());
-        sb.append(items);
-
-        return sb.toString();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void addContents(DexFile file) {
-        for (OffsettedItem i : items) {
-            i.addContents(file);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final String toHuman() {
-        StringBuffer sb = new StringBuffer(100);
-        boolean first = true;
-
-        sb.append("{");
-
-        for (OffsettedItem i : items) {
-            if (first) {
-                first = false;
-            } else {
-                sb.append(", ");
-            }
-            sb.append(i.toHuman());
-        }
-
-        sb.append("}");
-        return sb.toString();
-    }
-
-    /**
-     * Gets the underlying list of items.
-     *
-     * @return {@code non-null;} the list
-     */
-    public final List<T> getItems() {
-        return items;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void place0(Section addedTo, int offset) {
-        offset += headerSize();
-
-        boolean first = true;
-        int theSize = -1;
-        int theAlignment = -1;
-
-        for (OffsettedItem i : items) {
-            int size = i.writeSize();
-            if (first) {
-                theSize = size;
-                theAlignment = i.getAlignment();
-                first = false;
-            } else {
-                if (size != theSize) {
-                    throw new UnsupportedOperationException(
-                            "item size mismatch");
-                }
-                if (i.getAlignment() != theAlignment) {
-                    throw new UnsupportedOperationException(
-                            "item alignment mismatch");
-                }
-            }
-
-            offset = i.place(addedTo, offset) + size;
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected void writeTo0(DexFile file, AnnotatedOutput out) {
-        int size = items.size();
-
-        if (out.annotates()) {
-            out.annotate(0, offsetString() + " " + typeName());
-            out.annotate(4, "  size: " + Hex.u4(size));
-        }
-
-        out.writeInt(size);
-
-        for (OffsettedItem i : items) {
-            i.writeTo(file, out);
-        }
-    }
-
-    /**
-     * Get the size of the header of this list.
-     *
-     * @return {@code >= 0;} the header size
-     */
-    private int headerSize() {
-        /*
-         * Because of how this instance was set up, this is the same
-         * as the alignment.
-         */
-        return getAlignment();
-    }
+    return getAlignment();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/dex/file/ValueEncoder.java b/dx/src/com/android/jack/dx/dex/file/ValueEncoder.java
index c8a8019..d671ac9 100644
--- a/dx/src/com/android/jack/dx/dex/file/ValueEncoder.java
+++ b/dx/src/com/android/jack/dx/dex/file/ValueEncoder.java
@@ -46,483 +46,477 @@
  * thereof.
  */
 public final class ValueEncoder {
-    /** annotation value type constant: {@code byte} */
-    private static final int VALUE_BYTE = 0x00;
+  /** annotation value type constant: {@code byte} */
+  private static final int VALUE_BYTE = 0x00;
 
-    /** annotation value type constant: {@code short} */
-    private static final int VALUE_SHORT = 0x02;
+  /** annotation value type constant: {@code short} */
+  private static final int VALUE_SHORT = 0x02;
 
-    /** annotation value type constant: {@code char} */
-    private static final int VALUE_CHAR = 0x03;
+  /** annotation value type constant: {@code char} */
+  private static final int VALUE_CHAR = 0x03;
 
-    /** annotation value type constant: {@code int} */
-    private static final int VALUE_INT = 0x04;
+  /** annotation value type constant: {@code int} */
+  private static final int VALUE_INT = 0x04;
 
-    /** annotation value type constant: {@code long} */
-    private static final int VALUE_LONG = 0x06;
+  /** annotation value type constant: {@code long} */
+  private static final int VALUE_LONG = 0x06;
 
-    /** annotation value type constant: {@code float} */
-    private static final int VALUE_FLOAT = 0x10;
+  /** annotation value type constant: {@code float} */
+  private static final int VALUE_FLOAT = 0x10;
 
-    /** annotation value type constant: {@code double} */
-    private static final int VALUE_DOUBLE = 0x11;
+  /** annotation value type constant: {@code double} */
+  private static final int VALUE_DOUBLE = 0x11;
 
-    /** annotation value type constant: {@code string} */
-    private static final int VALUE_STRING = 0x17;
+  /** annotation value type constant: {@code string} */
+  private static final int VALUE_STRING = 0x17;
 
-    /** annotation value type constant: {@code type} */
-    private static final int VALUE_TYPE = 0x18;
+  /** annotation value type constant: {@code type} */
+  private static final int VALUE_TYPE = 0x18;
 
-    /** annotation value type constant: {@code field} */
-    private static final int VALUE_FIELD = 0x19;
+  /** annotation value type constant: {@code field} */
+  private static final int VALUE_FIELD = 0x19;
 
-    /** annotation value type constant: {@code method} */
-    private static final int VALUE_METHOD = 0x1a;
+  /** annotation value type constant: {@code method} */
+  private static final int VALUE_METHOD = 0x1a;
 
-    /** annotation value type constant: {@code enum} */
-    private static final int VALUE_ENUM = 0x1b;
+  /** annotation value type constant: {@code enum} */
+  private static final int VALUE_ENUM = 0x1b;
 
-    /** annotation value type constant: {@code array} */
-    private static final int VALUE_ARRAY = 0x1c;
+  /** annotation value type constant: {@code array} */
+  private static final int VALUE_ARRAY = 0x1c;
 
-    /** annotation value type constant: {@code annotation} */
-    private static final int VALUE_ANNOTATION = 0x1d;
+  /** annotation value type constant: {@code annotation} */
+  private static final int VALUE_ANNOTATION = 0x1d;
 
-    /** annotation value type constant: {@code null} */
-    private static final int VALUE_NULL = 0x1e;
+  /** annotation value type constant: {@code null} */
+  private static final int VALUE_NULL = 0x1e;
 
-    /** annotation value type constant: {@code boolean} */
-    private static final int VALUE_BOOLEAN = 0x1f;
+  /** annotation value type constant: {@code boolean} */
+  private static final int VALUE_BOOLEAN = 0x1f;
 
-    /** {@code non-null;} file being written */
-    private final DexFile file;
+  /** {@code non-null;} file being written */
+  private final DexFile file;
 
-    /** {@code non-null;} output stream to write to */
-    private final AnnotatedOutput out;
+  /** {@code non-null;} output stream to write to */
+  private final AnnotatedOutput out;
 
-    /**
-     * Construct an instance.
-     *
-     * @param file {@code non-null;} file being written
-     * @param out {@code non-null;} output stream to write to
-     */
-    public ValueEncoder(DexFile file, AnnotatedOutput out) {
-        if (file == null) {
-            throw new NullPointerException("file == null");
-        }
-
-        if (out == null) {
-            throw new NullPointerException("out == null");
-        }
-
-        this.file = file;
-        this.out = out;
+  /**
+   * Construct an instance.
+   *
+   * @param file {@code non-null;} file being written
+   * @param out {@code non-null;} output stream to write to
+   */
+  public ValueEncoder(DexFile file, AnnotatedOutput out) {
+    if (file == null) {
+      throw new NullPointerException("file == null");
     }
 
-    /**
-     * Writes out the encoded form of the given constant.
-     *
-     * @param cst {@code non-null;} the constant to write
-     */
-    public void writeConstant(Constant cst) {
-        int type = constantToValueType(cst);
-        int arg;
-
-        switch (type) {
-            case VALUE_BYTE:
-            case VALUE_SHORT:
-            case VALUE_INT:
-            case VALUE_LONG: {
-                long value = ((CstLiteralBits) cst).getLongBits();
-                writeSignedIntegralValue(type, value);
-                break;
-            }
-            case VALUE_CHAR: {
-                long value = ((CstLiteralBits) cst).getLongBits();
-                writeUnsignedIntegralValue(type, value);
-                break;
-            }
-            case VALUE_FLOAT: {
-                // Shift value left 32 so that right-zero-extension works.
-                long value = ((CstFloat) cst).getLongBits() << 32;
-                writeRightZeroExtendedValue(type, value);
-                break;
-            }
-            case VALUE_DOUBLE: {
-                long value = ((CstDouble) cst).getLongBits();
-                writeRightZeroExtendedValue(type, value);
-                break;
-            }
-            case VALUE_STRING: {
-                int index = file.getStringIds().indexOf((CstString) cst);
-                writeUnsignedIntegralValue(type, (long) index);
-                break;
-            }
-            case VALUE_TYPE: {
-                int index = file.getTypeIds().indexOf((CstType) cst);
-                writeUnsignedIntegralValue(type, (long) index);
-                break;
-            }
-            case VALUE_FIELD: {
-                int index = file.getFieldIds().indexOf((CstFieldRef) cst);
-                writeUnsignedIntegralValue(type, (long) index);
-                break;
-            }
-            case VALUE_METHOD: {
-                int index = file.getMethodIds().indexOf((CstMethodRef) cst);
-                writeUnsignedIntegralValue(type, (long) index);
-                break;
-            }
-            case VALUE_ENUM: {
-                CstFieldRef fieldRef = ((CstEnumRef) cst).getFieldRef();
-                int index = file.getFieldIds().indexOf(fieldRef);
-                writeUnsignedIntegralValue(type, (long) index);
-                break;
-            }
-            case VALUE_ARRAY: {
-                out.writeByte(type);
-                writeArray((CstArray) cst, false);
-                break;
-            }
-            case VALUE_ANNOTATION: {
-                out.writeByte(type);
-                writeAnnotation(((CstAnnotation) cst).getAnnotation(),
-                        false);
-                break;
-            }
-            case VALUE_NULL: {
-                out.writeByte(type);
-                break;
-            }
-            case VALUE_BOOLEAN: {
-                int value = ((CstBoolean) cst).getIntBits();
-                out.writeByte(type | (value << 5));
-                break;
-            }
-            default: {
-                throw new RuntimeException("Shouldn't happen");
-            }
-        }
+    if (out == null) {
+      throw new NullPointerException("out == null");
     }
 
-    /**
-     * Gets the value type for the given constant.
-     *
-     * @param cst {@code non-null;} the constant
-     * @return the value type; one of the {@code VALUE_*} constants
-     * defined by this class
+    this.file = file;
+    this.out = out;
+  }
+
+  /**
+   * Writes out the encoded form of the given constant.
+   *
+   * @param cst {@code non-null;} the constant to write
+   */
+  public void writeConstant(Constant cst) {
+    int type = constantToValueType(cst);
+
+    switch (type) {
+      case VALUE_BYTE:
+      case VALUE_SHORT:
+      case VALUE_INT:
+      case VALUE_LONG: {
+        long value = ((CstLiteralBits) cst).getLongBits();
+        writeSignedIntegralValue(type, value);
+        break;
+      }
+      case VALUE_CHAR: {
+        long value = ((CstLiteralBits) cst).getLongBits();
+        writeUnsignedIntegralValue(type, value);
+        break;
+      }
+      case VALUE_FLOAT: {
+        // Shift value left 32 so that right-zero-extension works.
+        long value = ((CstFloat) cst).getLongBits() << 32;
+        writeRightZeroExtendedValue(type, value);
+        break;
+      }
+      case VALUE_DOUBLE: {
+        long value = ((CstDouble) cst).getLongBits();
+        writeRightZeroExtendedValue(type, value);
+        break;
+      }
+      case VALUE_STRING: {
+        int index = file.getStringIds().indexOf((CstString) cst);
+        writeUnsignedIntegralValue(type, index);
+        break;
+      }
+      case VALUE_TYPE: {
+        int index = file.getTypeIds().indexOf((CstType) cst);
+        writeUnsignedIntegralValue(type, index);
+        break;
+      }
+      case VALUE_FIELD: {
+        int index = file.getFieldIds().indexOf((CstFieldRef) cst);
+        writeUnsignedIntegralValue(type, index);
+        break;
+      }
+      case VALUE_METHOD: {
+        int index = file.getMethodIds().indexOf((CstMethodRef) cst);
+        writeUnsignedIntegralValue(type, index);
+        break;
+      }
+      case VALUE_ENUM: {
+        CstFieldRef fieldRef = ((CstEnumRef) cst).getFieldRef();
+        int index = file.getFieldIds().indexOf(fieldRef);
+        writeUnsignedIntegralValue(type, index);
+        break;
+      }
+      case VALUE_ARRAY: {
+        out.writeByte(type);
+        writeArray((CstArray) cst, false);
+        break;
+      }
+      case VALUE_ANNOTATION: {
+        out.writeByte(type);
+        writeAnnotation(((CstAnnotation) cst).getAnnotation(), false);
+        break;
+      }
+      case VALUE_NULL: {
+        out.writeByte(type);
+        break;
+      }
+      case VALUE_BOOLEAN: {
+        int value = ((CstBoolean) cst).getIntBits();
+        out.writeByte(type | (value << 5));
+        break;
+      }
+      default: {
+        throw new RuntimeException("Shouldn't happen");
+      }
+    }
+  }
+
+  /**
+   * Gets the value type for the given constant.
+   *
+   * @param cst {@code non-null;} the constant
+   * @return the value type; one of the {@code VALUE_*} constants
+   * defined by this class
+   */
+  private static int constantToValueType(Constant cst) {
+    /*
+     * TODO(dx team): Constant should probable have an associated enum, so this
+     * can be a switch().
      */
-    private static int constantToValueType(Constant cst) {
-        /*
-         * TODO: Constant should probable have an associated enum, so this
-         * can be a switch().
-         */
-        if (cst instanceof CstByte) {
-            return VALUE_BYTE;
-        } else if (cst instanceof CstShort) {
-            return VALUE_SHORT;
-        } else if (cst instanceof CstChar) {
-            return VALUE_CHAR;
-        } else if (cst instanceof CstInteger) {
-            return VALUE_INT;
-        } else if (cst instanceof CstLong) {
-            return VALUE_LONG;
-        } else if (cst instanceof CstFloat) {
-            return VALUE_FLOAT;
-        } else if (cst instanceof CstDouble) {
-            return VALUE_DOUBLE;
-        } else if (cst instanceof CstString) {
-            return VALUE_STRING;
-        } else if (cst instanceof CstType) {
-            return VALUE_TYPE;
-        } else if (cst instanceof CstFieldRef) {
-            return VALUE_FIELD;
-        } else if (cst instanceof CstMethodRef) {
-            return VALUE_METHOD;
-        } else if (cst instanceof CstEnumRef) {
-            return VALUE_ENUM;
-        } else if (cst instanceof CstArray) {
-            return VALUE_ARRAY;
-        } else if (cst instanceof CstAnnotation) {
-            return VALUE_ANNOTATION;
-        } else if (cst instanceof CstKnownNull) {
-            return VALUE_NULL;
-        } else if (cst instanceof CstBoolean) {
-            return VALUE_BOOLEAN;
-        } else {
-            throw new RuntimeException("Shouldn't happen");
-        }
+    if (cst instanceof CstByte) {
+      return VALUE_BYTE;
+    } else if (cst instanceof CstShort) {
+      return VALUE_SHORT;
+    } else if (cst instanceof CstChar) {
+      return VALUE_CHAR;
+    } else if (cst instanceof CstInteger) {
+      return VALUE_INT;
+    } else if (cst instanceof CstLong) {
+      return VALUE_LONG;
+    } else if (cst instanceof CstFloat) {
+      return VALUE_FLOAT;
+    } else if (cst instanceof CstDouble) {
+      return VALUE_DOUBLE;
+    } else if (cst instanceof CstString) {
+      return VALUE_STRING;
+    } else if (cst instanceof CstType) {
+      return VALUE_TYPE;
+    } else if (cst instanceof CstFieldRef) {
+      return VALUE_FIELD;
+    } else if (cst instanceof CstMethodRef) {
+      return VALUE_METHOD;
+    } else if (cst instanceof CstEnumRef) {
+      return VALUE_ENUM;
+    } else if (cst instanceof CstArray) {
+      return VALUE_ARRAY;
+    } else if (cst instanceof CstAnnotation) {
+      return VALUE_ANNOTATION;
+    } else if (cst instanceof CstKnownNull) {
+      return VALUE_NULL;
+    } else if (cst instanceof CstBoolean) {
+      return VALUE_BOOLEAN;
+    } else {
+      throw new RuntimeException("Shouldn't happen");
+    }
+  }
+
+  /**
+   * Writes out the encoded form of the given array, that is, as
+   * an {@code encoded_array} and not including a
+   * {@code value_type} prefix. If the output stream keeps
+   * (debugging) annotations and {@code topLevel} is
+   * {@code true}, then this method will write (debugging)
+   * annotations.
+   *
+   * @param array {@code non-null;} array instance to write
+   * @param topLevel {@code true} iff the given annotation is the
+   * top-level annotation or {@code false} if it is a sub-annotation
+   * of some other annotation
+   */
+  public void writeArray(CstArray array, boolean topLevel) {
+    boolean annotates = topLevel && out.annotates();
+    CstArray.List list = array.getList();
+    int size = list.size();
+
+    if (annotates) {
+      out.annotate("  size: " + Hex.u4(size));
     }
 
-    /**
-     * Writes out the encoded form of the given array, that is, as
-     * an {@code encoded_array} and not including a
-     * {@code value_type} prefix. If the output stream keeps
-     * (debugging) annotations and {@code topLevel} is
-     * {@code true}, then this method will write (debugging)
-     * annotations.
-     *
-     * @param array {@code non-null;} array instance to write
-     * @param topLevel {@code true} iff the given annotation is the
-     * top-level annotation or {@code false} if it is a sub-annotation
-     * of some other annotation
-     */
-    public void writeArray(CstArray array, boolean topLevel) {
-        boolean annotates = topLevel && out.annotates();
-        CstArray.List list = ((CstArray) array).getList();
-        int size = list.size();
+    out.writeUleb128(size);
 
-        if (annotates) {
-            out.annotate("  size: " + Hex.u4(size));
-        }
-
-        out.writeUleb128(size);
-
-        for (int i = 0; i < size; i++) {
-            Constant cst = list.get(i);
-            if (annotates) {
-                out.annotate("  [" + Integer.toHexString(i) + "] " +
-                        constantToHuman(cst));
-            }
-            writeConstant(cst);
-        }
-
-        if (annotates) {
-            out.endAnnotation();
-        }
+    for (int i = 0; i < size; i++) {
+      Constant cst = list.get(i);
+      if (annotates) {
+        out.annotate("  [" + Integer.toHexString(i) + "] " + constantToHuman(cst));
+      }
+      writeConstant(cst);
     }
 
-    /**
-     * Writes out the encoded form of the given annotation, that is,
-     * as an {@code encoded_annotation} and not including a
-     * {@code value_type} prefix. If the output stream keeps
-     * (debugging) annotations and {@code topLevel} is
-     * {@code true}, then this method will write (debugging)
-     * annotations.
-     *
-     * @param annotation {@code non-null;} annotation instance to write
-     * @param topLevel {@code true} iff the given annotation is the
-     * top-level annotation or {@code false} if it is a sub-annotation
-     * of some other annotation
-     */
-    public void writeAnnotation(Annotation annotation, boolean topLevel) {
-        boolean annotates = topLevel && out.annotates();
-        StringIdsSection stringIds = file.getStringIds();
-        TypeIdsSection typeIds = file.getTypeIds();
+    if (annotates) {
+      out.endAnnotation();
+    }
+  }
 
-        CstType type = annotation.getType();
-        int typeIdx = typeIds.indexOf(type);
+  /**
+   * Writes out the encoded form of the given annotation, that is,
+   * as an {@code encoded_annotation} and not including a
+   * {@code value_type} prefix. If the output stream keeps
+   * (debugging) annotations and {@code topLevel} is
+   * {@code true}, then this method will write (debugging)
+   * annotations.
+   *
+   * @param annotation {@code non-null;} annotation instance to write
+   * @param topLevel {@code true} iff the given annotation is the
+   * top-level annotation or {@code false} if it is a sub-annotation
+   * of some other annotation
+   */
+  public void writeAnnotation(Annotation annotation, boolean topLevel) {
+    boolean annotates = topLevel && out.annotates();
+    StringIdsSection stringIds = file.getStringIds();
+    TypeIdsSection typeIds = file.getTypeIds();
 
-        if (annotates) {
-            out.annotate("  type_idx: " + Hex.u4(typeIdx) + " // " +
-                    type.toHuman());
-        }
+    CstType type = annotation.getType();
+    int typeIdx = typeIds.indexOf(type);
 
-        out.writeUleb128(typeIds.indexOf(annotation.getType()));
-
-        Collection<NameValuePair> pairs = annotation.getNameValuePairs();
-        int size = pairs.size();
-
-        if (annotates) {
-            out.annotate("  size: " + Hex.u4(size));
-        }
-
-        out.writeUleb128(size);
-
-        int at = 0;
-        for (NameValuePair pair : pairs) {
-            CstString name = pair.getName();
-            int nameIdx = stringIds.indexOf(name);
-            Constant value = pair.getValue();
-
-            if (annotates) {
-                out.annotate(0, "  elements[" + at + "]:");
-                at++;
-                out.annotate("    name_idx: " + Hex.u4(nameIdx) + " // " +
-                        name.toHuman());
-            }
-
-            out.writeUleb128(nameIdx);
-
-            if (annotates) {
-                out.annotate("    value: " + constantToHuman(value));
-            }
-
-            writeConstant(value);
-        }
-
-        if (annotates) {
-            out.endAnnotation();
-        }
+    if (annotates) {
+      out.annotate("  type_idx: " + Hex.u4(typeIdx) + " // " + type.toHuman());
     }
 
-    /**
-     * Gets the colloquial type name and human form of the type of the
-     * given constant, when used as an encoded value.
-     *
-     * @param cst {@code non-null;} the constant
-     * @return {@code non-null;} its type name and human form
-     */
-    public static String constantToHuman(Constant cst) {
-        int type = constantToValueType(cst);
+    out.writeUleb128(typeIds.indexOf(annotation.getType()));
 
-        if (type == VALUE_NULL) {
-            return "null";
-        }
+    Collection<NameValuePair> pairs = annotation.getNameValuePairs();
+    int size = pairs.size();
 
-        StringBuilder sb = new StringBuilder();
-
-        sb.append(cst.typeName());
-        sb.append(' ');
-        sb.append(cst.toHuman());
-
-        return sb.toString();
+    if (annotates) {
+      out.annotate("  size: " + Hex.u4(size));
     }
 
-    /**
-     * Helper for {@link #writeConstant}, which writes out the value
-     * for any signed integral type.
-     *
-     * @param type the type constant
-     * @param value {@code long} bits of the value
-     */
-    private void writeSignedIntegralValue(int type, long value) {
-        /*
-         * Figure out how many bits are needed to represent the value,
-         * including a sign bit: The bit count is subtracted from 65
-         * and not 64 to account for the sign bit. The xor operation
-         * has the effect of leaving non-negative values alone and
-         * unary complementing negative values (so that a leading zero
-         * count always returns a useful number for our present
-         * purpose).
-         */
-        int requiredBits =
-            65 - Long.numberOfLeadingZeros(value ^ (value >> 63));
+    out.writeUleb128(size);
 
-        // Round up the requiredBits to a number of bytes.
-        int requiredBytes = (requiredBits + 0x07) >> 3;
+    int at = 0;
+    for (NameValuePair pair : pairs) {
+      CstString name = pair.getName();
+      int nameIdx = stringIds.indexOf(name);
+      Constant value = pair.getValue();
 
-        /*
-         * Write the header byte, which includes the type and
-         * requiredBytes - 1.
-         */
-        out.writeByte(type | ((requiredBytes - 1) << 5));
+      if (annotates) {
+        out.annotate(0, "  elements[" + at + "]:");
+        at++;
+        out.annotate("    name_idx: " + Hex.u4(nameIdx) + " // " + name.toHuman());
+      }
 
-        // Write the value, per se.
-        while (requiredBytes > 0) {
-            out.writeByte((byte) value);
-            value >>= 8;
-            requiredBytes--;
-        }
+      out.writeUleb128(nameIdx);
+
+      if (annotates) {
+        out.annotate("    value: " + constantToHuman(value));
+      }
+
+      writeConstant(value);
     }
 
-    /**
-     * Helper for {@link #writeConstant}, which writes out the value
-     * for any unsigned integral type.
-     *
-     * @param type the type constant
-     * @param value {@code long} bits of the value
-     */
-    private void writeUnsignedIntegralValue(int type, long value) {
-        // Figure out how many bits are needed to represent the value.
-        int requiredBits = 64 - Long.numberOfLeadingZeros(value);
-        if (requiredBits == 0) {
-            requiredBits = 1;
-        }
+    if (annotates) {
+      out.endAnnotation();
+    }
+  }
 
-        // Round up the requiredBits to a number of bytes.
-        int requiredBytes = (requiredBits + 0x07) >> 3;
+  /**
+   * Gets the colloquial type name and human form of the type of the
+   * given constant, when used as an encoded value.
+   *
+   * @param cst {@code non-null;} the constant
+   * @return {@code non-null;} its type name and human form
+   */
+  public static String constantToHuman(Constant cst) {
+    int type = constantToValueType(cst);
 
-        /*
-         * Write the header byte, which includes the type and
-         * requiredBytes - 1.
-         */
-        out.writeByte(type | ((requiredBytes - 1) << 5));
-
-        // Write the value, per se.
-        while (requiredBytes > 0) {
-            out.writeByte((byte) value);
-            value >>= 8;
-            requiredBytes--;
-        }
+    if (type == VALUE_NULL) {
+      return "null";
     }
 
-    /**
-     * Helper for {@link #writeConstant}, which writes out a
-     * right-zero-extended value.
-     *
-     * @param type the type constant
-     * @param value {@code long} bits of the value
+    StringBuilder sb = new StringBuilder();
+
+    sb.append(cst.typeName());
+    sb.append(' ');
+    sb.append(cst.toHuman());
+
+    return sb.toString();
+  }
+
+  /**
+   * Helper for {@link #writeConstant}, which writes out the value
+   * for any signed integral type.
+   *
+   * @param type the type constant
+   * @param value {@code long} bits of the value
+   */
+  private void writeSignedIntegralValue(int type, long value) {
+    /*
+     * Figure out how many bits are needed to represent the value,
+     * including a sign bit: The bit count is subtracted from 65
+     * and not 64 to account for the sign bit. The xor operation
+     * has the effect of leaving non-negative values alone and
+     * unary complementing negative values (so that a leading zero
+     * count always returns a useful number for our present
+     * purpose).
      */
-    private void writeRightZeroExtendedValue(int type, long value) {
-        // Figure out how many bits are needed to represent the value.
-        int requiredBits = 64 - Long.numberOfTrailingZeros(value);
-        if (requiredBits == 0) {
-            requiredBits = 1;
-        }
+    int requiredBits = 65 - Long.numberOfLeadingZeros(value ^ (value >> 63));
 
-        // Round up the requiredBits to a number of bytes.
-        int requiredBytes = (requiredBits + 0x07) >> 3;
+    // Round up the requiredBits to a number of bytes.
+    int requiredBytes = (requiredBits + 0x07) >> 3;
 
-        // Scootch the first bits to be written down to the low-order bits.
-        value >>= 64 - (requiredBytes * 8);
+    /*
+     * Write the header byte, which includes the type and
+     * requiredBytes - 1.
+     */
+    out.writeByte(type | ((requiredBytes - 1) << 5));
 
-        /*
-         * Write the header byte, which includes the type and
-         * requiredBytes - 1.
-         */
-        out.writeByte(type | ((requiredBytes - 1) << 5));
+    // Write the value, per se.
+    while (requiredBytes > 0) {
+      out.writeByte((byte) value);
+      value >>= 8;
+      requiredBytes--;
+    }
+  }
 
-        // Write the value, per se.
-        while (requiredBytes > 0) {
-            out.writeByte((byte) value);
-            value >>= 8;
-            requiredBytes--;
-        }
+  /**
+   * Helper for {@link #writeConstant}, which writes out the value
+   * for any unsigned integral type.
+   *
+   * @param type the type constant
+   * @param value {@code long} bits of the value
+   */
+  private void writeUnsignedIntegralValue(int type, long value) {
+    // Figure out how many bits are needed to represent the value.
+    int requiredBits = 64 - Long.numberOfLeadingZeros(value);
+    if (requiredBits == 0) {
+      requiredBits = 1;
     }
 
+    // Round up the requiredBits to a number of bytes.
+    int requiredBytes = (requiredBits + 0x07) >> 3;
 
-    /**
-     * Helper for {@code addContents()} methods, which adds
-     * contents for a particular {@link Annotation}, calling itself
-     * recursively should it encounter a nested annotation.
-     *
-     * @param file {@code non-null;} the file to add to
-     * @param annotation {@code non-null;} the annotation to add contents for
+    /*
+     * Write the header byte, which includes the type and
+     * requiredBytes - 1.
      */
-    public static void addContents(DexFile file, Annotation annotation) {
-        TypeIdsSection typeIds = file.getTypeIds();
-        StringIdsSection stringIds = file.getStringIds();
+    out.writeByte(type | ((requiredBytes - 1) << 5));
 
-        typeIds.intern(annotation.getType());
+    // Write the value, per se.
+    while (requiredBytes > 0) {
+      out.writeByte((byte) value);
+      value >>= 8;
+      requiredBytes--;
+    }
+  }
 
-        for (NameValuePair pair : annotation.getNameValuePairs()) {
-            stringIds.intern(pair.getName());
-            addContents(file, pair.getValue());
-        }
+  /**
+   * Helper for {@link #writeConstant}, which writes out a
+   * right-zero-extended value.
+   *
+   * @param type the type constant
+   * @param value {@code long} bits of the value
+   */
+  private void writeRightZeroExtendedValue(int type, long value) {
+    // Figure out how many bits are needed to represent the value.
+    int requiredBits = 64 - Long.numberOfTrailingZeros(value);
+    if (requiredBits == 0) {
+      requiredBits = 1;
     }
 
-    /**
-     * Helper for {@code addContents()} methods, which adds
-     * contents for a particular constant, calling itself recursively
-     * should it encounter a {@link CstArray} and calling {@link
-     * #addContents(DexFile,Annotation)} recursively should it
-     * encounter a {@link CstAnnotation}.
-     *
-     * @param file {@code non-null;} the file to add to
-     * @param cst {@code non-null;} the constant to add contents for
+    // Round up the requiredBits to a number of bytes.
+    int requiredBytes = (requiredBits + 0x07) >> 3;
+
+    // Scootch the first bits to be written down to the low-order bits.
+    value >>= 64 - (requiredBytes * 8);
+
+    /*
+     * Write the header byte, which includes the type and
+     * requiredBytes - 1.
      */
-    public static void addContents(DexFile file, Constant cst) {
-        if (cst instanceof CstAnnotation) {
-            addContents(file, ((CstAnnotation) cst).getAnnotation());
-        } else if (cst instanceof CstArray) {
-            CstArray.List list = ((CstArray) cst).getList();
-            int size = list.size();
-            for (int i = 0; i < size; i++) {
-                addContents(file, list.get(i));
-            }
-        } else {
-            file.internIfAppropriate(cst);
-        }
+    out.writeByte(type | ((requiredBytes - 1) << 5));
+
+    // Write the value, per se.
+    while (requiredBytes > 0) {
+      out.writeByte((byte) value);
+      value >>= 8;
+      requiredBytes--;
     }
+  }
+
+
+  /**
+   * Helper for {@code addContents()} methods, which adds
+   * contents for a particular {@link Annotation}, calling itself
+   * recursively should it encounter a nested annotation.
+   *
+   * @param file {@code non-null;} the file to add to
+   * @param annotation {@code non-null;} the annotation to add contents for
+   */
+  public static void addContents(DexFile file, Annotation annotation) {
+    TypeIdsSection typeIds = file.getTypeIds();
+    StringIdsSection stringIds = file.getStringIds();
+
+    typeIds.intern(annotation.getType());
+
+    for (NameValuePair pair : annotation.getNameValuePairs()) {
+      stringIds.intern(pair.getName());
+      addContents(file, pair.getValue());
+    }
+  }
+
+  /**
+   * Helper for {@code addContents()} methods, which adds
+   * contents for a particular constant, calling itself recursively
+   * should it encounter a {@link CstArray} and calling {@link
+   * #addContents(DexFile,Annotation)} recursively should it
+   * encounter a {@link CstAnnotation}.
+   *
+   * @param file {@code non-null;} the file to add to
+   * @param cst {@code non-null;} the constant to add contents for
+   */
+  public static void addContents(DexFile file, Constant cst) {
+    if (cst instanceof CstAnnotation) {
+      addContents(file, ((CstAnnotation) cst).getAnnotation());
+    } else if (cst instanceof CstArray) {
+      CstArray.List list = ((CstArray) cst).getList();
+      int size = list.size();
+      for (int i = 0; i < size; i++) {
+        addContents(file, list.get(i));
+      }
+    } else {
+      file.internIfAppropriate(cst);
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/Annotation.java b/dx/src/com/android/jack/dx/io/Annotation.java
index 47987b1..5dfef2c 100644
--- a/dx/src/com/android/jack/dx/io/Annotation.java
+++ b/dx/src/com/android/jack/dx/io/Annotation.java
@@ -22,83 +22,85 @@
  * An annotation.
  */
 public final class Annotation implements Comparable<Annotation> {
-    private final DexBuffer buffer;
-    private final byte visibility;
-    private final int typeIndex;
-    private final int[] names;
-    private final EncodedValue[] values;
+  private final DexBuffer buffer;
+  private final byte visibility;
+  private final int typeIndex;
+  private final int[] names;
+  private final EncodedValue[] values;
 
-    public Annotation(DexBuffer buffer, byte visibility, int typeIndex, int[] names,
-            EncodedValue[] values) {
-        this.buffer = buffer;
-        this.visibility = visibility;
-        this.typeIndex = typeIndex;
-        this.names = names;
-        this.values = values;
+  public Annotation(DexBuffer buffer, byte visibility, int typeIndex, int[] names,
+      EncodedValue[] values) {
+    this.buffer = buffer;
+    this.visibility = visibility;
+    this.typeIndex = typeIndex;
+    this.names = names;
+    this.values = values;
+  }
+
+  public byte getVisibility() {
+    return visibility;
+  }
+
+  public int getTypeIndex() {
+    return typeIndex;
+  }
+
+  public int[] getNames() {
+    return names;
+  }
+
+  public EncodedValue[] getValues() {
+    return values;
+  }
+
+  public void writeTo(DexBuffer.Section out) {
+    out.writeByte(visibility);
+    out.writeUleb128(typeIndex);
+    out.writeUleb128(names.length);
+    for (int i = 0; i < names.length; i++) {
+      out.writeUleb128(names[i]);
+      values[i].writeTo(out);
+    }
+  }
+
+  @Override
+  public int compareTo(Annotation other) {
+    if (typeIndex != other.typeIndex) {
+      return Unsigned.compare(typeIndex, other.typeIndex);
+    }
+    int size = Math.min(names.length, other.names.length);
+    for (int i = 0; i < size; i++) {
+      if (names[i] != other.names[i]) {
+        return Unsigned.compare(names[i], other.names[i]);
+      }
+      int compare = values[i].compareTo(other.values[i]);
+      if (compare != 0) {
+        return compare;
+      }
+    }
+    return names.length - other.names.length;
+  }
+
+  @Override
+  public String toString() {
+    if (buffer == null) {
+      return visibility + " " + typeIndex;
     }
 
-    public byte getVisibility() {
-        return visibility;
+    StringBuilder result = new StringBuilder();
+    result.append(visibility);
+    result.append(" ");
+    result.append(buffer.typeNames().get(typeIndex));
+    result.append("[");
+    for (int i = 0; i < names.length; i++) {
+      if (i > 0) {
+        result.append(", ");
+      }
+      result.append(buffer.strings().get(names[i]));
+      result.append("=");
+      result.append(values[i]);
     }
-
-    public int getTypeIndex() {
-        return typeIndex;
-    }
-
-    public int[] getNames() {
-        return names;
-    }
-
-    public EncodedValue[] getValues() {
-        return values;
-    }
-
-    public void writeTo(DexBuffer.Section out) {
-        out.writeByte(visibility);
-        out.writeUleb128(typeIndex);
-        out.writeUleb128(names.length);
-        for (int i = 0; i < names.length; i++) {
-            out.writeUleb128(names[i]);
-            values[i].writeTo(out);
-        }
-    }
-
-    @Override public int compareTo(Annotation other) {
-        if (typeIndex != other.typeIndex) {
-            return Unsigned.compare(typeIndex, other.typeIndex);
-        }
-        int size = Math.min(names.length, other.names.length);
-        for (int i = 0; i < size; i++) {
-            if (names[i] != other.names[i]) {
-                return Unsigned.compare(names[i], other.names[i]);
-            }
-            int compare = values[i].compareTo(other.values[i]);
-            if (compare != 0) {
-                return compare;
-            }
-        }
-        return names.length - other.names.length;
-    }
-
-    @Override public String toString() {
-        if (buffer == null) {
-            return visibility + " " + typeIndex;
-        }
-
-        StringBuilder result = new StringBuilder();
-        result.append(visibility);
-        result.append(" ");
-        result.append(buffer.typeNames().get(typeIndex));
-        result.append("[");
-        for (int i = 0; i < names.length; i++) {
-            if (i > 0) {
-                result.append(", ");
-            }
-            result.append(buffer.strings().get(names[i]));
-            result.append("=");
-            result.append(values[i]);
-        }
-        result.append("]");
-        return result.toString();
-    }
+    result.append("]");
+    return result.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/ClassData.java b/dx/src/com/android/jack/dx/io/ClassData.java
index c51a651..ee9d133 100644
--- a/dx/src/com/android/jack/dx/io/ClassData.java
+++ b/dx/src/com/android/jack/dx/io/ClassData.java
@@ -16,89 +16,98 @@
 
 package com.android.jack.dx.io;
 
+/**
+ * TODO(jack team)
+ */
 public final class ClassData {
-    private final Field[] staticFields;
-    private final Field[] instanceFields;
-    private final Method[] directMethods;
-    private final Method[] virtualMethods;
+  private final Field[] staticFields;
+  private final Field[] instanceFields;
+  private final Method[] directMethods;
+  private final Method[] virtualMethods;
 
-    public ClassData(Field[] staticFields, Field[] instanceFields,
-            Method[] directMethods, Method[] virtualMethods) {
-        this.staticFields = staticFields;
-        this.instanceFields = instanceFields;
-        this.directMethods = directMethods;
-        this.virtualMethods = virtualMethods;
+  public ClassData(Field[] staticFields, Field[] instanceFields, Method[] directMethods,
+      Method[] virtualMethods) {
+    this.staticFields = staticFields;
+    this.instanceFields = instanceFields;
+    this.directMethods = directMethods;
+    this.virtualMethods = virtualMethods;
+  }
+
+  public Field[] getStaticFields() {
+    return staticFields;
+  }
+
+  public Field[] getInstanceFields() {
+    return instanceFields;
+  }
+
+  public Method[] getDirectMethods() {
+    return directMethods;
+  }
+
+  public Method[] getVirtualMethods() {
+    return virtualMethods;
+  }
+
+  public Field[] allFields() {
+    Field[] result = new Field[staticFields.length + instanceFields.length];
+    System.arraycopy(staticFields, 0, result, 0, staticFields.length);
+    System.arraycopy(instanceFields, 0, result, staticFields.length, instanceFields.length);
+    return result;
+  }
+
+  public Method[] allMethods() {
+    Method[] result = new Method[directMethods.length + virtualMethods.length];
+    System.arraycopy(directMethods, 0, result, 0, directMethods.length);
+    System.arraycopy(virtualMethods, 0, result, directMethods.length, virtualMethods.length);
+    return result;
+  }
+
+  /**
+   * TODO(jack team)
+   */
+  public static class Field {
+    private final int fieldIndex;
+    private final int accessFlags;
+
+    public Field(int fieldIndex, int accessFlags) {
+      this.fieldIndex = fieldIndex;
+      this.accessFlags = accessFlags;
     }
 
-    public Field[] getStaticFields() {
-        return staticFields;
+    public int getFieldIndex() {
+      return fieldIndex;
     }
 
-    public Field[] getInstanceFields() {
-        return instanceFields;
+    public int getAccessFlags() {
+      return accessFlags;
+    }
+  }
+
+  /**
+   * TODO(jack team)
+   */
+  public static class Method {
+    private final int methodIndex;
+    private final int accessFlags;
+    private final int codeOffset;
+
+    public Method(int methodIndex, int accessFlags, int codeOffset) {
+      this.methodIndex = methodIndex;
+      this.accessFlags = accessFlags;
+      this.codeOffset = codeOffset;
     }
 
-    public Method[] getDirectMethods() {
-        return directMethods;
+    public int getMethodIndex() {
+      return methodIndex;
     }
 
-    public Method[] getVirtualMethods() {
-        return virtualMethods;
+    public int getAccessFlags() {
+      return accessFlags;
     }
 
-    public Field[] allFields() {
-        Field[] result = new Field[staticFields.length + instanceFields.length];
-        System.arraycopy(staticFields, 0, result, 0, staticFields.length);
-        System.arraycopy(instanceFields, 0, result, staticFields.length, instanceFields.length);
-        return result;
+    public int getCodeOffset() {
+      return codeOffset;
     }
-
-    public Method[] allMethods() {
-        Method[] result = new Method[directMethods.length + virtualMethods.length];
-        System.arraycopy(directMethods, 0, result, 0, directMethods.length);
-        System.arraycopy(virtualMethods, 0, result, directMethods.length, virtualMethods.length);
-        return result;
-    }
-
-    public static class Field {
-        private final int fieldIndex;
-        private final int accessFlags;
-
-        public Field(int fieldIndex, int accessFlags) {
-            this.fieldIndex = fieldIndex;
-            this.accessFlags = accessFlags;
-        }
-
-        public int getFieldIndex() {
-            return fieldIndex;
-        }
-
-        public int getAccessFlags() {
-            return accessFlags;
-        }
-    }
-
-    public static class Method {
-        private final int methodIndex;
-        private final int accessFlags;
-        private final int codeOffset;
-
-        public Method(int methodIndex, int accessFlags, int codeOffset) {
-            this.methodIndex = methodIndex;
-            this.accessFlags = accessFlags;
-            this.codeOffset = codeOffset;
-        }
-
-        public int getMethodIndex() {
-            return methodIndex;
-        }
-
-        public int getAccessFlags() {
-            return accessFlags;
-        }
-
-        public int getCodeOffset() {
-            return codeOffset;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/ClassDef.java b/dx/src/com/android/jack/dx/io/ClassDef.java
index 60f15e3..7128905 100644
--- a/dx/src/com/android/jack/dx/io/ClassDef.java
+++ b/dx/src/com/android/jack/dx/io/ClassDef.java
@@ -20,83 +20,91 @@
  * A type definition.
  */
 public final class ClassDef {
-    public static final int NO_INDEX = -1;
-    private final DexBuffer buffer;
-    private final int offset;
-    private final int typeIndex;
-    private final int accessFlags;
-    private final int supertypeIndex;
-    private final int interfacesOffset;
-    private final int sourceFileIndex;
-    private final int annotationsOffset;
-    private final int classDataOffset;
-    private final int staticValuesOffset;
+  public static final int NO_INDEX = -1;
+  private final DexBuffer buffer;
+  private final int offset;
+  private final int typeIndex;
+  private final int accessFlags;
+  private final int supertypeIndex;
+  private final int interfacesOffset;
+  private final int sourceFileIndex;
+  private final int annotationsOffset;
+  private final int classDataOffset;
+  private final int staticValuesOffset;
 
-    public ClassDef(DexBuffer buffer, int offset, int typeIndex, int accessFlags,
-            int supertypeIndex, int interfacesOffset, int sourceFileIndex,
-            int annotationsOffset, int classDataOffset, int staticValuesOffset) {
-        this.buffer = buffer;
-        this.offset = offset;
-        this.typeIndex = typeIndex;
-        this.accessFlags = accessFlags;
-        this.supertypeIndex = supertypeIndex;
-        this.interfacesOffset = interfacesOffset;
-        this.sourceFileIndex = sourceFileIndex;
-        this.annotationsOffset = annotationsOffset;
-        this.classDataOffset = classDataOffset;
-        this.staticValuesOffset = staticValuesOffset;
+  public ClassDef(DexBuffer buffer,
+      int offset,
+      int typeIndex,
+      int accessFlags,
+      int supertypeIndex,
+      int interfacesOffset,
+      int sourceFileIndex,
+      int annotationsOffset,
+      int classDataOffset,
+      int staticValuesOffset) {
+    this.buffer = buffer;
+    this.offset = offset;
+    this.typeIndex = typeIndex;
+    this.accessFlags = accessFlags;
+    this.supertypeIndex = supertypeIndex;
+    this.interfacesOffset = interfacesOffset;
+    this.sourceFileIndex = sourceFileIndex;
+    this.annotationsOffset = annotationsOffset;
+    this.classDataOffset = classDataOffset;
+    this.staticValuesOffset = staticValuesOffset;
+  }
+
+  public int getOffset() {
+    return offset;
+  }
+
+  public int getTypeIndex() {
+    return typeIndex;
+  }
+
+  public int getSupertypeIndex() {
+    return supertypeIndex;
+  }
+
+  public int getInterfacesOffset() {
+    return interfacesOffset;
+  }
+
+  public short[] getInterfaces() {
+    return buffer.readTypeList(interfacesOffset).getTypes();
+  }
+
+  public int getAccessFlags() {
+    return accessFlags;
+  }
+
+  public int getSourceFileIndex() {
+    return sourceFileIndex;
+  }
+
+  public int getAnnotationsOffset() {
+    return annotationsOffset;
+  }
+
+  public int getClassDataOffset() {
+    return classDataOffset;
+  }
+
+  public int getStaticValuesOffset() {
+    return staticValuesOffset;
+  }
+
+  @Override
+  public String toString() {
+    if (buffer == null) {
+      return typeIndex + " " + supertypeIndex;
     }
 
-    public int getOffset() {
-        return offset;
+    StringBuilder result = new StringBuilder();
+    result.append(buffer.typeNames().get(typeIndex));
+    if (supertypeIndex != NO_INDEX) {
+      result.append(" extends ").append(buffer.typeNames().get(supertypeIndex));
     }
-
-    public int getTypeIndex() {
-        return typeIndex;
-    }
-
-    public int getSupertypeIndex() {
-        return supertypeIndex;
-    }
-
-    public int getInterfacesOffset() {
-        return interfacesOffset;
-    }
-
-    public short[] getInterfaces() {
-        return buffer.readTypeList(interfacesOffset).getTypes();
-    }
-
-    public int getAccessFlags() {
-        return accessFlags;
-    }
-
-    public int getSourceFileIndex() {
-        return sourceFileIndex;
-    }
-
-    public int getAnnotationsOffset() {
-        return annotationsOffset;
-    }
-
-    public int getClassDataOffset() {
-        return classDataOffset;
-    }
-
-    public int getStaticValuesOffset() {
-        return staticValuesOffset;
-    }
-
-    @Override public String toString() {
-        if (buffer == null) {
-            return typeIndex + " " + supertypeIndex;
-        }
-
-        StringBuilder result = new StringBuilder();
-        result.append(buffer.typeNames().get(typeIndex));
-        if (supertypeIndex != NO_INDEX) {
-            result.append(" extends ").append(buffer.typeNames().get(supertypeIndex));
-        }
-        return result.toString();
-    }
+    return result.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/Code.java b/dx/src/com/android/jack/dx/io/Code.java
index 865369b..376d72e 100644
--- a/dx/src/com/android/jack/dx/io/Code.java
+++ b/dx/src/com/android/jack/dx/io/Code.java
@@ -16,109 +16,123 @@
 
 package com.android.jack.dx.io;
 
+/**
+ * TODO(jack team)
+ */
 public final class Code {
-    private final int registersSize;
-    private final int insSize;
-    private final int outsSize;
-    private final int debugInfoOffset;
-    private final short[] instructions;
-    private final Try[] tries;
-    private final CatchHandler[] catchHandlers;
+  private final int registersSize;
+  private final int insSize;
+  private final int outsSize;
+  private final int debugInfoOffset;
+  private final short[] instructions;
+  private final Try[] tries;
+  private final CatchHandler[] catchHandlers;
 
-    public Code(int registersSize, int insSize, int outsSize, int debugInfoOffset,
-            short[] instructions, Try[] tries, CatchHandler[] catchHandlers) {
-        this.registersSize = registersSize;
-        this.insSize = insSize;
-        this.outsSize = outsSize;
-        this.debugInfoOffset = debugInfoOffset;
-        this.instructions = instructions;
-        this.tries = tries;
-        this.catchHandlers = catchHandlers;
+  public Code(int registersSize,
+      int insSize,
+      int outsSize,
+      int debugInfoOffset,
+      short[] instructions,
+      Try[] tries,
+      CatchHandler[] catchHandlers) {
+    this.registersSize = registersSize;
+    this.insSize = insSize;
+    this.outsSize = outsSize;
+    this.debugInfoOffset = debugInfoOffset;
+    this.instructions = instructions;
+    this.tries = tries;
+    this.catchHandlers = catchHandlers;
+  }
+
+  public int getRegistersSize() {
+    return registersSize;
+  }
+
+  public int getInsSize() {
+    return insSize;
+  }
+
+  public int getOutsSize() {
+    return outsSize;
+  }
+
+  public int getDebugInfoOffset() {
+    return debugInfoOffset;
+  }
+
+  public short[] getInstructions() {
+    return instructions;
+  }
+
+  public Try[] getTries() {
+    return tries;
+  }
+
+  public CatchHandler[] getCatchHandlers() {
+    return catchHandlers;
+  }
+
+  /**
+   * TODO(jack team)
+   */
+  public static class Try {
+    final int startAddress;
+    final int instructionCount;
+    final int catchHandlerIndex;
+
+    Try(int startAddress, int instructionCount, int catchHandlerIndex) {
+      this.startAddress = startAddress;
+      this.instructionCount = instructionCount;
+      this.catchHandlerIndex = catchHandlerIndex;
     }
 
-    public int getRegistersSize() {
-        return registersSize;
+    public int getStartAddress() {
+      return startAddress;
     }
 
-    public int getInsSize() {
-        return insSize;
+    public int getInstructionCount() {
+      return instructionCount;
     }
 
-    public int getOutsSize() {
-        return outsSize;
+    /**
+     * Returns this try's catch handler <strong>index</strong>. Note that
+     * this is distinct from the its catch handler <strong>offset</strong>.
+     */
+    public int getCatchHandlerIndex() {
+      return catchHandlerIndex;
+    }
+  }
+
+  /**
+   * TODO(jack team)
+   */
+  public static class CatchHandler {
+    final int[] typeIndexes;
+    final int[] addresses;
+    final int catchAllAddress;
+    final int offset;
+
+    public CatchHandler(int[] typeIndexes, int[] addresses, int catchAllAddress, int offset) {
+      this.typeIndexes = typeIndexes;
+      this.addresses = addresses;
+      this.catchAllAddress = catchAllAddress;
+      this.offset = offset;
     }
 
-    public int getDebugInfoOffset() {
-        return debugInfoOffset;
+    public int[] getTypeIndexes() {
+      return typeIndexes;
     }
 
-    public short[] getInstructions() {
-        return instructions;
+    public int[] getAddresses() {
+      return addresses;
     }
 
-    public Try[] getTries() {
-        return tries;
+    public int getCatchAllAddress() {
+      return catchAllAddress;
     }
 
-    public CatchHandler[] getCatchHandlers() {
-        return catchHandlers;
+    public int getOffset() {
+      return offset;
     }
-
-    public static class Try {
-        final int startAddress;
-        final int instructionCount;
-        final int catchHandlerIndex;
-
-        Try(int startAddress, int instructionCount, int catchHandlerIndex) {
-            this.startAddress = startAddress;
-            this.instructionCount = instructionCount;
-            this.catchHandlerIndex = catchHandlerIndex;
-        }
-
-        public int getStartAddress() {
-            return startAddress;
-        }
-
-        public int getInstructionCount() {
-            return instructionCount;
-        }
-
-        /**
-         * Returns this try's catch handler <strong>index</strong>. Note that
-         * this is distinct from the its catch handler <strong>offset</strong>.
-         */
-        public int getCatchHandlerIndex() {
-            return catchHandlerIndex;
-        }
-    }
-
-    public static class CatchHandler {
-        final int[] typeIndexes;
-        final int[] addresses;
-        final int catchAllAddress;
-        final int offset;
-
-        public CatchHandler(int[] typeIndexes, int[] addresses, int catchAllAddress, int offset) {
-            this.typeIndexes = typeIndexes;
-            this.addresses = addresses;
-            this.catchAllAddress = catchAllAddress;
-            this.offset = offset;
-        }
-
-        public int[] getTypeIndexes() {
-            return typeIndexes;
-        }
-
-        public int[] getAddresses() {
-            return addresses;
-        }
-
-        public int getCatchAllAddress() {
-            return catchAllAddress;
-        }
-
-        public int getOffset() {
-            return offset;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/CodeReader.java b/dx/src/com/android/jack/dx/io/CodeReader.java
index 0b791b1..b1c1d4d 100644
--- a/dx/src/com/android/jack/dx/io/CodeReader.java
+++ b/dx/src/com/android/jack/dx/io/CodeReader.java
@@ -23,99 +23,110 @@
  * Walks through a block of code and calls visitor call backs.
  */
 public final class CodeReader {
-    private Visitor fallbackVisitor = null;
-    private Visitor stringVisitor = null;
-    private Visitor typeVisitor = null;
-    private Visitor fieldVisitor = null;
-    private Visitor methodVisitor = null;
+  private Visitor fallbackVisitor = null;
+  private Visitor stringVisitor = null;
+  private Visitor typeVisitor = null;
+  private Visitor fieldVisitor = null;
+  private Visitor methodVisitor = null;
 
-    /**
-     * Sets {@code visitor} as the visitor for all instructions.
-     */
-    public void setAllVisitors(Visitor visitor) {
-        fallbackVisitor = visitor;
-        stringVisitor = visitor;
-        typeVisitor = visitor;
-        fieldVisitor = visitor;
-        methodVisitor = visitor;
+  /**
+   * Sets {@code visitor} as the visitor for all instructions.
+   */
+  public void setAllVisitors(Visitor visitor) {
+    fallbackVisitor = visitor;
+    stringVisitor = visitor;
+    typeVisitor = visitor;
+    fieldVisitor = visitor;
+    methodVisitor = visitor;
+  }
+
+  /**
+   * Sets {@code visitor} as the visitor for all instructions not
+   * otherwise handled.
+   */
+  public void setFallbackVisitor(Visitor visitor) {
+    fallbackVisitor = visitor;
+  }
+
+  /**
+   * Sets {@code visitor} as the visitor for all string instructions.
+   */
+  public void setStringVisitor(Visitor visitor) {
+    stringVisitor = visitor;
+  }
+
+  /**
+   * Sets {@code visitor} as the visitor for all type instructions.
+   */
+  public void setTypeVisitor(Visitor visitor) {
+    typeVisitor = visitor;
+  }
+
+  /**
+   * Sets {@code visitor} as the visitor for all field instructions.
+   */
+  public void setFieldVisitor(Visitor visitor) {
+    fieldVisitor = visitor;
+  }
+
+  /**
+   * Sets {@code visitor} as the visitor for all method instructions.
+   */
+  public void setMethodVisitor(Visitor visitor) {
+    methodVisitor = visitor;
+  }
+
+  public void visitAll(DecodedInstruction[] decodedInstructions) throws DexException {
+    int size = decodedInstructions.length;
+
+    for (int i = 0; i < size; i++) {
+      DecodedInstruction one = decodedInstructions[i];
+      if (one == null) {
+        continue;
+      }
+
+      callVisit(decodedInstructions, one);
+    }
+  }
+
+  public void visitAll(short[] encodedInstructions) throws DexException {
+    DecodedInstruction[] decodedInstructions = DecodedInstruction.decodeAll(encodedInstructions);
+    visitAll(decodedInstructions);
+  }
+
+  private void callVisit(DecodedInstruction[] all, DecodedInstruction one) {
+    Visitor visitor = null;
+
+    switch (OpcodeInfo.getIndexType(one.getOpcode())) {
+      case STRING_REF:
+        visitor = stringVisitor;
+        break;
+      case TYPE_REF:
+        visitor = typeVisitor;
+        break;
+      case FIELD_REF:
+        visitor = fieldVisitor;
+        break;
+      case METHOD_REF:
+        visitor = methodVisitor;
+        break;
+      default:
+        /* continue */
     }
 
-    /**
-     * Sets {@code visitor} as the visitor for all instructions not
-     * otherwise handled.
-     */
-    public void setFallbackVisitor(Visitor visitor) {
-        fallbackVisitor = visitor;
+    if (visitor == null) {
+      visitor = fallbackVisitor;
     }
 
-    /**
-     * Sets {@code visitor} as the visitor for all string instructions.
-     */
-    public void setStringVisitor(Visitor visitor) {
-        stringVisitor = visitor;
+    if (visitor != null) {
+      visitor.visit(all, one);
     }
+  }
 
-    /**
-     * Sets {@code visitor} as the visitor for all type instructions.
-     */
-    public void setTypeVisitor(Visitor visitor) {
-        typeVisitor = visitor;
-    }
-
-    /**
-     * Sets {@code visitor} as the visitor for all field instructions.
-     */
-    public void setFieldVisitor(Visitor visitor) {
-        fieldVisitor = visitor;
-    }
-
-    /**
-     * Sets {@code visitor} as the visitor for all method instructions.
-     */
-    public void setMethodVisitor(Visitor visitor) {
-        methodVisitor = visitor;
-    }
-
-    public void visitAll(DecodedInstruction[] decodedInstructions)
-            throws DexException {
-        int size = decodedInstructions.length;
-
-        for (int i = 0; i < size; i++) {
-            DecodedInstruction one = decodedInstructions[i];
-            if (one == null) {
-                continue;
-            }
-
-            callVisit(decodedInstructions, one);
-        }
-    }
-
-    public void visitAll(short[] encodedInstructions) throws DexException {
-        DecodedInstruction[] decodedInstructions =
-            DecodedInstruction.decodeAll(encodedInstructions);
-        visitAll(decodedInstructions);
-    }
-
-    private void callVisit(DecodedInstruction[] all, DecodedInstruction one) {
-        Visitor visitor = null;
-
-        switch (OpcodeInfo.getIndexType(one.getOpcode())) {
-            case STRING_REF: visitor = stringVisitor; break;
-            case TYPE_REF:   visitor = typeVisitor;   break;
-            case FIELD_REF:  visitor = fieldVisitor;  break;
-            case METHOD_REF: visitor = methodVisitor; break;
-        }
-
-        if (visitor == null) {
-            visitor = fallbackVisitor;
-        }
-
-        if (visitor != null) {
-            visitor.visit(all, one);
-        }
-    }
-
-    public interface Visitor {
-        void visit(DecodedInstruction[] all, DecodedInstruction one);
-    }
+  /**
+   * TODO(jack team)
+   */
+  public interface Visitor {
+    void visit(DecodedInstruction[] all, DecodedInstruction one);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/DexBuffer.java b/dx/src/com/android/jack/dx/io/DexBuffer.java
index 2e8299c..e273f4b 100644
--- a/dx/src/com/android/jack/dx/io/DexBuffer.java
+++ b/dx/src/com/android/jack/dx/io/DexBuffer.java
@@ -51,660 +51,694 @@
  * are unsigned.
  */
 public final class DexBuffer {
-    private byte[] data;
-    private final TableOfContents tableOfContents = new TableOfContents();
-    private int length = 0;
+  private byte[] data;
+  private final TableOfContents tableOfContents = new TableOfContents();
+  private int length = 0;
 
-    private final List<String> strings = new AbstractList<String>() {
-        @Override public String get(int index) {
-            checkBounds(index, tableOfContents.stringIds.size);
-            return open(tableOfContents.stringIds.off + (index * SizeOf.STRING_ID_ITEM))
-                    .readString();
-        }
-        @Override public int size() {
-            return tableOfContents.stringIds.size;
-        }
-    };
-
-    private final List<Integer> typeIds = new AbstractList<Integer>() {
-        @Override public Integer get(int index) {
-            checkBounds(index, tableOfContents.typeIds.size);
-            return open(tableOfContents.typeIds.off + (index * SizeOf.TYPE_ID_ITEM)).readInt();
-        }
-        @Override public int size() {
-            return tableOfContents.typeIds.size;
-        }
-    };
-
-    private final List<String> typeNames = new AbstractList<String>() {
-        @Override public String get(int index) {
-            checkBounds(index, tableOfContents.typeIds.size);
-            return strings.get(typeIds.get(index));
-        }
-        @Override public int size() {
-            return tableOfContents.typeIds.size;
-        }
-    };
-
-    private final List<ProtoId> protoIds = new AbstractList<ProtoId>() {
-        @Override public ProtoId get(int index) {
-            checkBounds(index, tableOfContents.protoIds.size);
-            return open(tableOfContents.protoIds.off + (SizeOf.PROTO_ID_ITEM * index))
-                    .readProtoId();
-        }
-        @Override public int size() {
-            return tableOfContents.protoIds.size;
-        }
-    };
-
-    private final List<FieldId> fieldIds = new AbstractList<FieldId>() {
-        @Override public FieldId get(int index) {
-            checkBounds(index, tableOfContents.fieldIds.size);
-            return open(tableOfContents.fieldIds.off + (SizeOf.MEMBER_ID_ITEM * index))
-                    .readFieldId();
-        }
-        @Override public int size() {
-            return tableOfContents.fieldIds.size;
-        }
-    };
-
-    private final List<MethodId> methodIds = new AbstractList<MethodId>() {
-        @Override public MethodId get(int index) {
-            checkBounds(index, tableOfContents.methodIds.size);
-            return open(tableOfContents.methodIds.off + (SizeOf.MEMBER_ID_ITEM * index))
-                    .readMethodId();
-        }
-        @Override public int size() {
-            return tableOfContents.methodIds.size;
-        }
-    };
-
-    /**
-     * Creates a new dex buffer defining no classes.
-     */
-    public DexBuffer() {
-        this.data = new byte[0];
+  private final List<String> strings = new AbstractList<String>() {
+    @Override
+    public String get(int index) {
+      checkBounds(index, tableOfContents.stringIds.size);
+      return open(tableOfContents.stringIds.off + (index * SizeOf.STRING_ID_ITEM)).readString();
     }
 
-    /**
-     * Creates a new dex buffer that reads from {@code data}. It is an error to
-     * modify {@code data} after using it to create a dex buffer.
-     */
-    public DexBuffer(byte[] data) throws IOException {
-        this.data = data;
-        this.length = data.length;
-        this.tableOfContents.readFrom(this);
+    @Override
+    public int size() {
+      return tableOfContents.stringIds.size;
+    }
+  };
+
+  private final List<Integer> typeIds = new AbstractList<Integer>() {
+    @Override
+    public Integer get(int index) {
+      checkBounds(index, tableOfContents.typeIds.size);
+      return open(tableOfContents.typeIds.off + (index * SizeOf.TYPE_ID_ITEM)).readInt();
     }
 
-    /**
-     * Creates a new dex buffer of the dex in {@code in}, and closes {@code in}.
-     */
-    public DexBuffer(InputStream in) throws IOException {
-        loadFrom(in);
+    @Override
+    public int size() {
+      return tableOfContents.typeIds.size;
+    }
+  };
+
+  private final List<String> typeNames = new AbstractList<String>() {
+    @Override
+    public String get(int index) {
+      checkBounds(index, tableOfContents.typeIds.size);
+      return strings.get(typeIds.get(index));
     }
 
-    /**
-     * Creates a new dex buffer from the dex file {@code file}.
-     */
-    public DexBuffer(File file) throws IOException {
-        if (FileUtils.hasArchiveSuffix(file.getName())) {
-            ZipFile zipFile = new ZipFile(file);
-            ZipEntry entry = zipFile.getEntry(DexFormat.DEX_IN_JAR_NAME);
-            if (entry != null) {
-                loadFrom(zipFile.getInputStream(entry));
-                zipFile.close();
-            } else {
-                throw new DexException("Expected " + DexFormat.DEX_IN_JAR_NAME + " in " + file);
+    @Override
+    public int size() {
+      return tableOfContents.typeIds.size;
+    }
+  };
+
+  private final List<ProtoId> protoIds = new AbstractList<ProtoId>() {
+    @Override
+    public ProtoId get(int index) {
+      checkBounds(index, tableOfContents.protoIds.size);
+      return open(tableOfContents.protoIds.off + (SizeOf.PROTO_ID_ITEM * index)).readProtoId();
+    }
+
+    @Override
+    public int size() {
+      return tableOfContents.protoIds.size;
+    }
+  };
+
+  private final List<FieldId> fieldIds = new AbstractList<FieldId>() {
+    @Override
+    public FieldId get(int index) {
+      checkBounds(index, tableOfContents.fieldIds.size);
+      return open(tableOfContents.fieldIds.off + (SizeOf.MEMBER_ID_ITEM * index)).readFieldId();
+    }
+
+    @Override
+    public int size() {
+      return tableOfContents.fieldIds.size;
+    }
+  };
+
+  private final List<MethodId> methodIds = new AbstractList<MethodId>() {
+    @Override
+    public MethodId get(int index) {
+      checkBounds(index, tableOfContents.methodIds.size);
+      return open(tableOfContents.methodIds.off + (SizeOf.MEMBER_ID_ITEM * index)).readMethodId();
+    }
+
+    @Override
+    public int size() {
+      return tableOfContents.methodIds.size;
+    }
+  };
+
+  /**
+   * Creates a new dex buffer defining no classes.
+   */
+  public DexBuffer() {
+    this.data = new byte[0];
+  }
+
+  /**
+   * Creates a new dex buffer that reads from {@code data}. It is an error to
+   * modify {@code data} after using it to create a dex buffer.
+   */
+  public DexBuffer(byte[] data) throws IOException {
+    this.data = data;
+    this.length = data.length;
+    this.tableOfContents.readFrom(this);
+  }
+
+  /**
+   * Creates a new dex buffer of the dex in {@code in}, and closes {@code in}.
+   */
+  public DexBuffer(InputStream in) throws IOException {
+    loadFrom(in);
+  }
+
+  /**
+   * Creates a new dex buffer from the dex file {@code file}.
+   */
+  public DexBuffer(File file) throws IOException {
+    if (FileUtils.hasArchiveSuffix(file.getName())) {
+      ZipFile zipFile = new ZipFile(file);
+      ZipEntry entry = zipFile.getEntry(DexFormat.DEX_IN_JAR_NAME);
+      if (entry != null) {
+        loadFrom(zipFile.getInputStream(entry));
+        zipFile.close();
+      } else {
+        throw new DexException("Expected " + DexFormat.DEX_IN_JAR_NAME + " in " + file);
+      }
+    } else if (file.getName().endsWith(".dex")) {
+      loadFrom(new FileInputStream(file));
+    } else {
+      throw new DexException("unknown output extension: " + file);
+    }
+  }
+
+  private void loadFrom(InputStream in) throws IOException {
+    ByteArrayOutputStream bytesOut = new ByteArrayOutputStream();
+    byte[] buffer = new byte[8192];
+
+    int count;
+    while ((count = in.read(buffer)) != -1) {
+      bytesOut.write(buffer, 0, count);
+    }
+    in.close();
+
+    this.data = bytesOut.toByteArray();
+    this.length = data.length;
+    this.tableOfContents.readFrom(this);
+  }
+
+  private static void checkBounds(int index, int length) {
+    if (index < 0 || index >= length) {
+      throw new IndexOutOfBoundsException("index:" + index + ", length=" + length);
+    }
+  }
+
+  public void writeTo(OutputStream out) throws IOException {
+    out.write(data);
+  }
+
+  public void writeTo(File dexOut) throws IOException {
+    OutputStream out = new FileOutputStream(dexOut);
+    writeTo(out);
+    out.close();
+  }
+
+  public TableOfContents getTableOfContents() {
+    return tableOfContents;
+  }
+
+  public Section open(int position) {
+    if (position < 0 || position > length) {
+      throw new IllegalArgumentException("position=" + position + " length=" + length);
+    }
+    return new Section(position);
+  }
+
+  public Section appendSection(int maxByteCount, String name) {
+    int limit = fourByteAlign(length + maxByteCount);
+    Section result = new Section(name, length, limit);
+    length = limit;
+    return result;
+  }
+
+  public void noMoreSections() {
+    data = new byte[length];
+  }
+
+  public int getLength() {
+    return length;
+  }
+
+  public static int fourByteAlign(int position) {
+    return (position + 3) & ~3;
+  }
+
+  public byte[] getBytes() {
+    return data;
+  }
+
+  public List<String> strings() {
+    return strings;
+  }
+
+  public List<Integer> typeIds() {
+    return typeIds;
+  }
+
+  public List<String> typeNames() {
+    return typeNames;
+  }
+
+  public List<ProtoId> protoIds() {
+    return protoIds;
+  }
+
+  public List<FieldId> fieldIds() {
+    return fieldIds;
+  }
+
+  public List<MethodId> methodIds() {
+    return methodIds;
+  }
+
+  public Iterable<ClassDef> classDefs() {
+    return new Iterable<ClassDef>() {
+      @Override
+      public Iterator<ClassDef> iterator() {
+        if (!tableOfContents.classDefs.exists()) {
+          return Collections.<ClassDef>emptySet().iterator();
+        }
+        return new Iterator<ClassDef>() {
+          private DexBuffer.Section in = open(tableOfContents.classDefs.off);
+          private int count = 0;
+
+          @Override
+          public boolean hasNext() {
+            return count < tableOfContents.classDefs.size;
+          }
+
+          @Override
+          public ClassDef next() {
+            if (!hasNext()) {
+              throw new NoSuchElementException();
             }
-        } else if (file.getName().endsWith(".dex")) {
-            loadFrom(new FileInputStream(file));
-        } else {
-            throw new DexException("unknown output extension: " + file);
-        }
-    }
+            count++;
+            return in.readClassDef();
+          }
 
-    private void loadFrom(InputStream in) throws IOException {
-        ByteArrayOutputStream bytesOut = new ByteArrayOutputStream();
-        byte[] buffer = new byte[8192];
-
-        int count;
-        while ((count = in.read(buffer)) != -1) {
-            bytesOut.write(buffer, 0, count);
-        }
-        in.close();
-
-        this.data = bytesOut.toByteArray();
-        this.length = data.length;
-        this.tableOfContents.readFrom(this);
-    }
-
-    private static void checkBounds(int index, int length) {
-        if (index < 0 || index >= length) {
-            throw new IndexOutOfBoundsException("index:" + index + ", length=" + length);
-        }
-    }
-
-    public void writeTo(OutputStream out) throws IOException {
-        out.write(data);
-    }
-
-    public void writeTo(File dexOut) throws IOException {
-        OutputStream out = new FileOutputStream(dexOut);
-        writeTo(out);
-        out.close();
-    }
-
-    public TableOfContents getTableOfContents() {
-        return tableOfContents;
-    }
-
-    public Section open(int position) {
-        if (position < 0 || position > length) {
-            throw new IllegalArgumentException("position=" + position + " length=" + length);
-        }
-        return new Section(position);
-    }
-
-    public Section appendSection(int maxByteCount, String name) {
-        int limit = fourByteAlign(length + maxByteCount);
-        Section result = new Section(name, length, limit);
-        length = limit;
-        return result;
-    }
-
-    public void noMoreSections() {
-        data = new byte[length];
-    }
-
-    public int getLength() {
-        return length;
-    }
-
-    public static int fourByteAlign(int position) {
-        return (position + 3) & ~3;
-    }
-
-    public byte[] getBytes() {
-        return data;
-    }
-
-    public List<String> strings() {
-        return strings;
-    }
-
-    public List<Integer> typeIds() {
-        return typeIds;
-    }
-
-    public List<String> typeNames() {
-        return typeNames;
-    }
-
-    public List<ProtoId> protoIds() {
-        return protoIds;
-    }
-
-    public List<FieldId> fieldIds() {
-        return fieldIds;
-    }
-
-    public List<MethodId> methodIds() {
-        return methodIds;
-    }
-
-    public Iterable<ClassDef> classDefs() {
-        return new Iterable<ClassDef>() {
-            public Iterator<ClassDef> iterator() {
-                if (!tableOfContents.classDefs.exists()) {
-                    return Collections.<ClassDef>emptySet().iterator();
-                }
-                return new Iterator<ClassDef>() {
-                    private DexBuffer.Section in = open(tableOfContents.classDefs.off);
-                    private int count = 0;
-
-                    public boolean hasNext() {
-                        return count < tableOfContents.classDefs.size;
-                    }
-                    public ClassDef next() {
-                        if (!hasNext()) {
-                            throw new NoSuchElementException();
-                        }
-                        count++;
-                        return in.readClassDef();
-                    }
-                    public void remove() {
-                        throw new UnsupportedOperationException();
-                    }
-                };
-            }
+          @Override
+          public void remove() {
+            throw new UnsupportedOperationException();
+          }
         };
+      }
+    };
+  }
+
+  public TypeList readTypeList(int offset) {
+    if (offset == 0) {
+      return TypeList.EMPTY;
+    }
+    return open(offset).readTypeList();
+  }
+
+  public ClassData readClassData(ClassDef classDef) {
+    int offset = classDef.getClassDataOffset();
+    if (offset == 0) {
+      throw new IllegalArgumentException("offset == 0");
+    }
+    return open(offset).readClassData();
+  }
+
+  public Code readCode(ClassData.Method method) {
+    int offset = method.getCodeOffset();
+    if (offset == 0) {
+      throw new IllegalArgumentException("offset == 0");
+    }
+    return open(offset).readCode();
+  }
+
+  /**
+   * TODO(jack team)
+   */
+  public final class Section implements ByteInput, ByteOutput {
+    private final String name;
+    private int position;
+    private final int limit;
+    private final int initialPosition;
+
+    private Section(String name, int position, int limit) {
+      this.name = name;
+      this.position = this.initialPosition = position;
+      this.limit = limit;
     }
 
-    public TypeList readTypeList(int offset) {
-        if (offset == 0) {
-            return TypeList.EMPTY;
-        }
-        return open(offset).readTypeList();
+    private Section(int position) {
+      this("section", position, data.length);
     }
 
-    public ClassData readClassData(ClassDef classDef) {
-        int offset = classDef.getClassDataOffset();
-        if (offset == 0) {
-            throw new IllegalArgumentException("offset == 0");
-        }
-        return open(offset).readClassData();
+    public int getPosition() {
+      return position;
     }
 
-    public Code readCode(ClassData.Method method) {
-        int offset = method.getCodeOffset();
-        if (offset == 0) {
-            throw new IllegalArgumentException("offset == 0");
-        }
-        return open(offset).readCode();
+    public int readInt() {
+      int result = (data[position] & 0xff) | (data[position + 1] & 0xff) << 8
+          | (data[position + 2] & 0xff) << 16 | (data[position + 3] & 0xff) << 24;
+      position += 4;
+      return result;
     }
 
-    public final class Section implements ByteInput, ByteOutput {
-        private final String name;
-        private int position;
-        private final int limit;
-        private final int initialPosition;
+    public short readShort() {
+      int result = (data[position] & 0xff) | (data[position + 1] & 0xff) << 8;
+      position += 2;
+      return (short) result;
+    }
 
-        private Section(String name, int position, int limit) {
-            this.name = name;
-            this.position = this.initialPosition = position;
-            this.limit = limit;
+    public int readUnsignedShort() {
+      return readShort() & 0xffff;
+    }
+
+    @Override
+    public byte readByte() {
+      return (byte) (data[position++] & 0xff);
+    }
+
+    public byte[] readByteArray(int length) {
+      byte[] result = Arrays.copyOfRange(data, position, position + length);
+      position += length;
+      return result;
+    }
+
+    public short[] readShortArray(int length) {
+      short[] result = new short[length];
+      for (int i = 0; i < length; i++) {
+        result[i] = readShort();
+      }
+      return result;
+    }
+
+    public int readUleb128() {
+      return Leb128Utils.readUnsignedLeb128(this);
+    }
+
+    public int readUleb128p1() {
+      return Leb128Utils.readUnsignedLeb128(this) - 1;
+    }
+
+    public int readSleb128() {
+      return Leb128Utils.readSignedLeb128(this);
+    }
+
+    public TypeList readTypeList() {
+      assertFourByteAligned();
+      int size = readInt();
+      short[] types = new short[size];
+      for (int i = 0; i < size; i++) {
+        types[i] = readShort();
+      }
+      position = DexBuffer.fourByteAlign(position);
+      return new TypeList(DexBuffer.this, types);
+    }
+
+    public String readString() {
+      int offset = readInt();
+      int savedPosition = position;
+      position = offset;
+      try {
+        int expectedLength = readUleb128();
+        String result = Mutf8.decode(this, new char[expectedLength]);
+        if (result.length() != expectedLength) {
+          throw new DexException("Declared length " + expectedLength
+              + " doesn't match decoded length of " + result.length());
+        }
+        return result;
+      } catch (UTFDataFormatException e) {
+        throw new DexException(e);
+      } finally {
+        position = savedPosition;
+      }
+    }
+
+    public FieldId readFieldId() {
+      int declaringClassIndex = readUnsignedShort();
+      int typeIndex = readUnsignedShort();
+      int nameIndex = readInt();
+      return new FieldId(DexBuffer.this, declaringClassIndex, typeIndex, nameIndex);
+    }
+
+    public MethodId readMethodId() {
+      int declaringClassIndex = readUnsignedShort();
+      int protoIndex = readUnsignedShort();
+      int nameIndex = readInt();
+      return new MethodId(DexBuffer.this, declaringClassIndex, protoIndex, nameIndex);
+    }
+
+    public ProtoId readProtoId() {
+      int shortyIndex = readInt();
+      int returnTypeIndex = readInt();
+      int parametersOffset = readInt();
+      return new ProtoId(DexBuffer.this, shortyIndex, returnTypeIndex, parametersOffset);
+    }
+
+    public ClassDef readClassDef() {
+      int offset = getPosition();
+      int type = readInt();
+      int accessFlags = readInt();
+      int supertype = readInt();
+      int interfacesOffset = readInt();
+      int sourceFileIndex = readInt();
+      int annotationsOffset = readInt();
+      int classDataOffset = readInt();
+      int staticValuesOffset = readInt();
+      return new ClassDef(DexBuffer.this,
+          offset,
+          type,
+          accessFlags,
+          supertype,
+          interfacesOffset,
+          sourceFileIndex,
+          annotationsOffset,
+          classDataOffset,
+          staticValuesOffset);
+    }
+
+    private Code readCode() {
+      int registersSize = readUnsignedShort();
+      int insSize = readUnsignedShort();
+      int outsSize = readUnsignedShort();
+      int triesSize = readUnsignedShort();
+      int debugInfoOffset = readInt();
+      int instructionsSize = readInt();
+      short[] instructions = readShortArray(instructionsSize);
+      Try[] tries;
+      CatchHandler[] catchHandlers;
+      if (triesSize > 0) {
+        if (instructions.length % 2 == 1) {
+          readShort(); // padding
         }
 
-        private Section(int position) {
-            this("section", position, data.length);
-        }
-
-        public int getPosition() {
-            return position;
-        }
-
-        public int readInt() {
-            int result = (data[position] & 0xff)
-                    | (data[position + 1] & 0xff) << 8
-                    | (data[position + 2] & 0xff) << 16
-                    | (data[position + 3] & 0xff) << 24;
-            position += 4;
-            return result;
-        }
-
-        public short readShort() {
-            int result = (data[position] & 0xff)
-                    | (data[position + 1] & 0xff) << 8;
-            position += 2;
-            return (short) result;
-        }
-
-        public int readUnsignedShort() {
-            return readShort() & 0xffff;
-        }
-
-        public byte readByte() {
-            return (byte) (data[position++] & 0xff);
-        }
-
-        public byte[] readByteArray(int length) {
-            byte[] result = Arrays.copyOfRange(data, position, position + length);
-            position += length;
-            return result;
-        }
-
-        public short[] readShortArray(int length) {
-            short[] result = new short[length];
-            for (int i = 0; i < length; i++) {
-                result[i] = readShort();
-            }
-            return result;
-        }
-
-        public int readUleb128() {
-            return Leb128Utils.readUnsignedLeb128(this);
-        }
-
-        public int readUleb128p1() {
-            return Leb128Utils.readUnsignedLeb128(this) - 1;
-        }
-
-        public int readSleb128() {
-            return Leb128Utils.readSignedLeb128(this);
-        }
-
-        public TypeList readTypeList() {
-            assertFourByteAligned();
-            int size = readInt();
-            short[] types = new short[size];
-            for (int i = 0; i < size; i++) {
-                types[i] = readShort();
-            }
-            position = DexBuffer.fourByteAlign(position);
-            return new TypeList(DexBuffer.this, types);
-        }
-
-        public String readString() {
-            int offset = readInt();
-            int savedPosition = position;
-            position = offset;
-            try {
-                int expectedLength = readUleb128();
-                String result = Mutf8.decode(this, new char[expectedLength]);
-                if (result.length() != expectedLength) {
-                    throw new DexException("Declared length " + expectedLength
-                            + " doesn't match decoded length of " + result.length());
-                }
-                return result;
-            } catch (UTFDataFormatException e) {
-                throw new DexException(e);
-            } finally {
-                position = savedPosition;
-            }
-        }
-
-        public FieldId readFieldId() {
-            int declaringClassIndex = readUnsignedShort();
-            int typeIndex = readUnsignedShort();
-            int nameIndex = readInt();
-            return new FieldId(DexBuffer.this, declaringClassIndex, typeIndex, nameIndex);
-        }
-
-        public MethodId readMethodId() {
-            int declaringClassIndex = readUnsignedShort();
-            int protoIndex = readUnsignedShort();
-            int nameIndex = readInt();
-            return new MethodId(DexBuffer.this, declaringClassIndex, protoIndex, nameIndex);
-        }
-
-        public ProtoId readProtoId() {
-            int shortyIndex = readInt();
-            int returnTypeIndex = readInt();
-            int parametersOffset = readInt();
-            return new ProtoId(DexBuffer.this, shortyIndex, returnTypeIndex, parametersOffset);
-        }
-
-        public ClassDef readClassDef() {
-            int offset = getPosition();
-            int type = readInt();
-            int accessFlags = readInt();
-            int supertype = readInt();
-            int interfacesOffset = readInt();
-            int sourceFileIndex = readInt();
-            int annotationsOffset = readInt();
-            int classDataOffset = readInt();
-            int staticValuesOffset = readInt();
-            return new ClassDef(DexBuffer.this, offset, type, accessFlags, supertype,
-                    interfacesOffset, sourceFileIndex, annotationsOffset, classDataOffset,
-                    staticValuesOffset);
-        }
-
-        private Code readCode() {
-            int registersSize = readUnsignedShort();
-            int insSize = readUnsignedShort();
-            int outsSize = readUnsignedShort();
-            int triesSize = readUnsignedShort();
-            int debugInfoOffset = readInt();
-            int instructionsSize = readInt();
-            short[] instructions = readShortArray(instructionsSize);
-            Try[] tries;
-            CatchHandler[] catchHandlers;
-            if (triesSize > 0) {
-                if (instructions.length % 2 == 1) {
-                    readShort(); // padding
-                }
-
-                /*
-                 * We can't read the tries until we've read the catch handlers.
-                 * Unfortunately they're in the opposite order in the dex file
-                 * so we need to read them out-of-order.
-                 */
-                Section triesSection = open(position);
-                skip(triesSize * SizeOf.TRY_ITEM);
-                catchHandlers = readCatchHandlers();
-                tries = triesSection.readTries(triesSize, catchHandlers);
-            } else {
-                tries = new Try[0];
-                catchHandlers = new CatchHandler[0];
-            }
-            return new Code(registersSize, insSize, outsSize, debugInfoOffset, instructions,
-                    tries, catchHandlers);
-        }
-
-        private CatchHandler[] readCatchHandlers() {
-            int baseOffset = position;
-            int catchHandlersSize = readUleb128();
-            CatchHandler[] result = new CatchHandler[catchHandlersSize];
-            for (int i = 0; i < catchHandlersSize; i++) {
-                int offset = position - baseOffset;
-                result[i] = readCatchHandler(offset);
-            }
-            return result;
-        }
-
-        private Try[] readTries(int triesSize, CatchHandler[] catchHandlers) {
-            Try[] result = new Try[triesSize];
-            for (int i = 0; i < triesSize; i++) {
-                int startAddress = readInt();
-                int instructionCount = readUnsignedShort();
-                int handlerOffset = readUnsignedShort();
-                int catchHandlerIndex = findCatchHandlerIndex(catchHandlers, handlerOffset);
-                result[i] = new Try(startAddress, instructionCount, catchHandlerIndex);
-            }
-            return result;
-        }
-
-        private int findCatchHandlerIndex(CatchHandler[] catchHandlers, int offset) {
-            for (int i = 0; i < catchHandlers.length; i++) {
-                CatchHandler catchHandler = catchHandlers[i];
-                if (catchHandler.getOffset() == offset) {
-                    return i;
-                }
-            }
-            throw new IllegalArgumentException();
-        }
-
-        private CatchHandler readCatchHandler(int offset) {
-            int size = readSleb128();
-            int handlersCount = Math.abs(size);
-            int[] typeIndexes = new int[handlersCount];
-            int[] addresses = new int[handlersCount];
-            for (int i = 0; i < handlersCount; i++) {
-                typeIndexes[i] = readUleb128();
-                addresses[i] = readUleb128();
-            }
-            int catchAllAddress = size <= 0 ? readUleb128() : -1;
-            return new CatchHandler(typeIndexes, addresses, catchAllAddress, offset);
-        }
-
-        private ClassData readClassData() {
-            int staticFieldsSize = readUleb128();
-            int instanceFieldsSize = readUleb128();
-            int directMethodsSize = readUleb128();
-            int virtualMethodsSize = readUleb128();
-            ClassData.Field[] staticFields = readFields(staticFieldsSize);
-            ClassData.Field[] instanceFields = readFields(instanceFieldsSize);
-            ClassData.Method[] directMethods = readMethods(directMethodsSize);
-            ClassData.Method[] virtualMethods = readMethods(virtualMethodsSize);
-            return new ClassData(staticFields, instanceFields, directMethods, virtualMethods);
-        }
-
-        private ClassData.Field[] readFields(int count) {
-            ClassData.Field[] result = new ClassData.Field[count];
-            int fieldIndex = 0;
-            for (int i = 0; i < count; i++) {
-                fieldIndex += readUleb128(); // field index diff
-                int accessFlags = readUleb128();
-                result[i] = new ClassData.Field(fieldIndex, accessFlags);
-            }
-            return result;
-        }
-
-        private ClassData.Method[] readMethods(int count) {
-            ClassData.Method[] result = new ClassData.Method[count];
-            int methodIndex = 0;
-            for (int i = 0; i < count; i++) {
-                methodIndex += readUleb128(); // method index diff
-                int accessFlags = readUleb128();
-                int codeOff = readUleb128();
-                result[i] = new ClassData.Method(methodIndex, accessFlags, codeOff);
-            }
-            return result;
-        }
-
-        public Annotation readAnnotation() {
-            byte visibility = readByte();
-            int typeIndex = readUleb128();
-            int size = readUleb128();
-            int[] names = new int[size];
-            EncodedValue[] values = new EncodedValue[size];
-            for (int i = 0; i < size; i++) {
-                names[i] = readUleb128();
-                values[i] = readEncodedValue();
-            }
-            return new Annotation(DexBuffer.this, visibility, typeIndex, names, values);
-        }
-
-        public EncodedValue readEncodedValue() {
-            int start = position;
-            new EncodedValueReader(this).readValue();
-            int end = position;
-            return new EncodedValue(Arrays.copyOfRange(data, start, end));
-        }
-
-        public EncodedValue readEncodedArray() {
-            int start = position;
-            new EncodedValueReader(this).readArray();
-            int end = position;
-            return new EncodedValue(Arrays.copyOfRange(data, start, end));
-        }
-
-        private void ensureCapacity(int size) {
-            if (position + size > limit) {
-                throw new DexException("Section limit " + limit + " exceeded by " + name);
-            }
-        }
-
-        public void skip(int count) {
-            if (count < 0) {
-                throw new IllegalArgumentException();
-            }
-            ensureCapacity(count);
-            position += count;
-        }
-
-        /**
-         * Writes 0x00 until the position is aligned to a multiple of 4.
+        /*
+         * We can't read the tries until we've read the catch handlers.
+         * Unfortunately they're in the opposite order in the dex file
+         * so we need to read them out-of-order.
          */
-        public void alignToFourBytes() {
-            int unalignedCount = position;
-            position = DexBuffer.fourByteAlign(position);
-            for (int i = unalignedCount; i < position; i++) {
-                data[i] = 0;
-            }
-        }
-
-        public void assertFourByteAligned() {
-            if ((position & 3) != 0) {
-                throw new IllegalStateException("Not four byte aligned!");
-            }
-        }
-
-        public void write(byte[] bytes) {
-            ensureCapacity(bytes.length);
-            System.arraycopy(bytes, 0, data, position, bytes.length);
-            position += bytes.length;
-        }
-
-        public void writeByte(int b) {
-            ensureCapacity(1);
-            data[position++] = (byte) b;
-        }
-
-        public void writeShort(short i) {
-            ensureCapacity(2);
-            data[position    ] = (byte) i;
-            data[position + 1] = (byte) (i >>> 8);
-            position += 2;
-        }
-
-        public void writeUnsignedShort(int i) {
-            short s = (short) i;
-            if (i != (s & 0xffff)) {
-                throw new IllegalArgumentException("Expected an unsigned short: " + i);
-            }
-            writeShort(s);
-        }
-
-        public void write(short[] shorts) {
-            for (short s : shorts) {
-                writeShort(s);
-            }
-        }
-
-        public void writeInt(int i) {
-            ensureCapacity(4);
-            data[position    ] = (byte) i;
-            data[position + 1] = (byte) (i >>>  8);
-            data[position + 2] = (byte) (i >>> 16);
-            data[position + 3] = (byte) (i >>> 24);
-            position += 4;
-        }
-
-        public void writeUleb128(int i) {
-            try {
-                Leb128Utils.writeUnsignedLeb128(this, i);
-                ensureCapacity(0);
-            } catch (ArrayIndexOutOfBoundsException e) {
-                throw new DexException("Section limit " + limit + " exceeded by " + name);
-            }
-        }
-
-        public void writeUleb128p1(int i) {
-            writeUleb128(i + 1);
-        }
-
-        public void writeSleb128(int i) {
-            try {
-                Leb128Utils.writeSignedLeb128(this, i);
-                ensureCapacity(0);
-            } catch (ArrayIndexOutOfBoundsException e) {
-                throw new DexException("Section limit " + limit + " exceeded by " + name);
-            }
-        }
-
-        public void writeStringData(String value) {
-            try {
-                int length = value.length();
-                writeUleb128(length);
-                write(Mutf8.encode(value));
-                writeByte(0);
-            } catch (UTFDataFormatException e) {
-                throw new AssertionError();
-            }
-        }
-
-        public void writeTypeList(TypeList typeList) {
-            short[] types = typeList.getTypes();
-            writeInt(types.length);
-            for (short type : types) {
-                writeShort(type);
-            }
-            alignToFourBytes();
-        }
-
-        /**
-         * Returns the number of bytes remaining in this section.
-         */
-        public int remaining() {
-            return limit - position;
-        }
-
-        /**
-         * Returns the number of bytes used by this section.
-         */
-        public int used () {
-            return position - initialPosition;
-        }
+        Section triesSection = open(position);
+        skip(triesSize * SizeOf.TRY_ITEM);
+        catchHandlers = readCatchHandlers();
+        tries = triesSection.readTries(triesSize, catchHandlers);
+      } else {
+        tries = new Try[0];
+        catchHandlers = new CatchHandler[0];
+      }
+      return new Code(registersSize,
+          insSize,
+          outsSize,
+          debugInfoOffset,
+          instructions,
+          tries,
+          catchHandlers);
     }
+
+    private CatchHandler[] readCatchHandlers() {
+      int baseOffset = position;
+      int catchHandlersSize = readUleb128();
+      CatchHandler[] result = new CatchHandler[catchHandlersSize];
+      for (int i = 0; i < catchHandlersSize; i++) {
+        int offset = position - baseOffset;
+        result[i] = readCatchHandler(offset);
+      }
+      return result;
+    }
+
+    private Try[] readTries(int triesSize, CatchHandler[] catchHandlers) {
+      Try[] result = new Try[triesSize];
+      for (int i = 0; i < triesSize; i++) {
+        int startAddress = readInt();
+        int instructionCount = readUnsignedShort();
+        int handlerOffset = readUnsignedShort();
+        int catchHandlerIndex = findCatchHandlerIndex(catchHandlers, handlerOffset);
+        result[i] = new Try(startAddress, instructionCount, catchHandlerIndex);
+      }
+      return result;
+    }
+
+    private int findCatchHandlerIndex(CatchHandler[] catchHandlers, int offset) {
+      for (int i = 0; i < catchHandlers.length; i++) {
+        CatchHandler catchHandler = catchHandlers[i];
+        if (catchHandler.getOffset() == offset) {
+          return i;
+        }
+      }
+      throw new IllegalArgumentException();
+    }
+
+    private CatchHandler readCatchHandler(int offset) {
+      int size = readSleb128();
+      int handlersCount = Math.abs(size);
+      int[] typeIndexes = new int[handlersCount];
+      int[] addresses = new int[handlersCount];
+      for (int i = 0; i < handlersCount; i++) {
+        typeIndexes[i] = readUleb128();
+        addresses[i] = readUleb128();
+      }
+      int catchAllAddress = size <= 0 ? readUleb128() : -1;
+      return new CatchHandler(typeIndexes, addresses, catchAllAddress, offset);
+    }
+
+    private ClassData readClassData() {
+      int staticFieldsSize = readUleb128();
+      int instanceFieldsSize = readUleb128();
+      int directMethodsSize = readUleb128();
+      int virtualMethodsSize = readUleb128();
+      ClassData.Field[] staticFields = readFields(staticFieldsSize);
+      ClassData.Field[] instanceFields = readFields(instanceFieldsSize);
+      ClassData.Method[] directMethods = readMethods(directMethodsSize);
+      ClassData.Method[] virtualMethods = readMethods(virtualMethodsSize);
+      return new ClassData(staticFields, instanceFields, directMethods, virtualMethods);
+    }
+
+    private ClassData.Field[] readFields(int count) {
+      ClassData.Field[] result = new ClassData.Field[count];
+      int fieldIndex = 0;
+      for (int i = 0; i < count; i++) {
+        fieldIndex += readUleb128(); // field index diff
+        int accessFlags = readUleb128();
+        result[i] = new ClassData.Field(fieldIndex, accessFlags);
+      }
+      return result;
+    }
+
+    private ClassData.Method[] readMethods(int count) {
+      ClassData.Method[] result = new ClassData.Method[count];
+      int methodIndex = 0;
+      for (int i = 0; i < count; i++) {
+        methodIndex += readUleb128(); // method index diff
+        int accessFlags = readUleb128();
+        int codeOff = readUleb128();
+        result[i] = new ClassData.Method(methodIndex, accessFlags, codeOff);
+      }
+      return result;
+    }
+
+    public Annotation readAnnotation() {
+      byte visibility = readByte();
+      int typeIndex = readUleb128();
+      int size = readUleb128();
+      int[] names = new int[size];
+      EncodedValue[] values = new EncodedValue[size];
+      for (int i = 0; i < size; i++) {
+        names[i] = readUleb128();
+        values[i] = readEncodedValue();
+      }
+      return new Annotation(DexBuffer.this, visibility, typeIndex, names, values);
+    }
+
+    public EncodedValue readEncodedValue() {
+      int start = position;
+      new EncodedValueReader(this).readValue();
+      int end = position;
+      return new EncodedValue(Arrays.copyOfRange(data, start, end));
+    }
+
+    public EncodedValue readEncodedArray() {
+      int start = position;
+      new EncodedValueReader(this).readArray();
+      int end = position;
+      return new EncodedValue(Arrays.copyOfRange(data, start, end));
+    }
+
+    private void ensureCapacity(int size) {
+      if (position + size > limit) {
+        throw new DexException("Section limit " + limit + " exceeded by " + name);
+      }
+    }
+
+    public void skip(int count) {
+      if (count < 0) {
+        throw new IllegalArgumentException();
+      }
+      ensureCapacity(count);
+      position += count;
+    }
+
+    /**
+     * Writes 0x00 until the position is aligned to a multiple of 4.
+     */
+    public void alignToFourBytes() {
+      int unalignedCount = position;
+      position = DexBuffer.fourByteAlign(position);
+      for (int i = unalignedCount; i < position; i++) {
+        data[i] = 0;
+      }
+    }
+
+    public void assertFourByteAligned() {
+      if ((position & 3) != 0) {
+        throw new IllegalStateException("Not four byte aligned!");
+      }
+    }
+
+    public void write(byte[] bytes) {
+      ensureCapacity(bytes.length);
+      System.arraycopy(bytes, 0, data, position, bytes.length);
+      position += bytes.length;
+    }
+
+    @Override
+    public void writeByte(int b) {
+      ensureCapacity(1);
+      data[position++] = (byte) b;
+    }
+
+    public void writeShort(short i) {
+      ensureCapacity(2);
+      data[position] = (byte) i;
+      data[position + 1] = (byte) (i >>> 8);
+      position += 2;
+    }
+
+    public void writeUnsignedShort(int i) {
+      short s = (short) i;
+      if (i != (s & 0xffff)) {
+        throw new IllegalArgumentException("Expected an unsigned short: " + i);
+      }
+      writeShort(s);
+    }
+
+    public void write(short[] shorts) {
+      for (short s : shorts) {
+        writeShort(s);
+      }
+    }
+
+    public void writeInt(int i) {
+      ensureCapacity(4);
+      data[position] = (byte) i;
+      data[position + 1] = (byte) (i >>> 8);
+      data[position + 2] = (byte) (i >>> 16);
+      data[position + 3] = (byte) (i >>> 24);
+      position += 4;
+    }
+
+    public void writeUleb128(int i) {
+      try {
+        Leb128Utils.writeUnsignedLeb128(this, i);
+        ensureCapacity(0);
+      } catch (ArrayIndexOutOfBoundsException e) {
+        throw new DexException("Section limit " + limit + " exceeded by " + name);
+      }
+    }
+
+    public void writeUleb128p1(int i) {
+      writeUleb128(i + 1);
+    }
+
+    public void writeSleb128(int i) {
+      try {
+        Leb128Utils.writeSignedLeb128(this, i);
+        ensureCapacity(0);
+      } catch (ArrayIndexOutOfBoundsException e) {
+        throw new DexException("Section limit " + limit + " exceeded by " + name);
+      }
+    }
+
+    public void writeStringData(String value) {
+      try {
+        int length = value.length();
+        writeUleb128(length);
+        write(Mutf8.encode(value));
+        writeByte(0);
+      } catch (UTFDataFormatException e) {
+        throw new AssertionError();
+      }
+    }
+
+    public void writeTypeList(TypeList typeList) {
+      short[] types = typeList.getTypes();
+      writeInt(types.length);
+      for (short type : types) {
+        writeShort(type);
+      }
+      alignToFourBytes();
+    }
+
+    /**
+     * Returns the number of bytes remaining in this section.
+     */
+    public int remaining() {
+      return limit - position;
+    }
+
+    /**
+     * Returns the number of bytes used by this section.
+     */
+    public int used() {
+      return position - initialPosition;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/DexHasher.java b/dx/src/com/android/jack/dx/io/DexHasher.java
index 301dd37..3a9b3ba 100644
--- a/dx/src/com/android/jack/dx/io/DexHasher.java
+++ b/dx/src/com/android/jack/dx/io/DexHasher.java
@@ -25,51 +25,51 @@
  * Generates and stores the checksum and signature of a dex file.
  */
 public final class DexHasher {
-    private static final int CHECKSUM_OFFSET = 8;
-    private static final int CHECKSUM_SIZE = 4;
-    private static final int SIGNATURE_OFFSET = CHECKSUM_OFFSET + CHECKSUM_SIZE;
-    private static final int SIGNATURE_SIZE = 20;
+  private static final int CHECKSUM_OFFSET = 8;
+  private static final int CHECKSUM_SIZE = 4;
+  private static final int SIGNATURE_OFFSET = CHECKSUM_OFFSET + CHECKSUM_SIZE;
+  private static final int SIGNATURE_SIZE = 20;
 
-    /**
-     * Returns the signature of all but the first 32 bytes of {@code dex}. The
-     * first 32 bytes of dex files are not specified to be included in the
-     * signature.
-     */
-    public byte[] computeSignature(DexBuffer dex) throws IOException {
-        MessageDigest digest;
-        try {
-            digest = MessageDigest.getInstance("SHA-1");
-        } catch (NoSuchAlgorithmException e) {
-            throw new AssertionError();
-        }
-        int offset = SIGNATURE_OFFSET + SIGNATURE_SIZE;
-
-        byte[] bytes = dex.getBytes();
-        digest.update(bytes, offset, bytes.length - offset);
-        return digest.digest();
+  /**
+   * Returns the signature of all but the first 32 bytes of {@code dex}. The
+   * first 32 bytes of dex files are not specified to be included in the
+   * signature.
+   */
+  public byte[] computeSignature(DexBuffer dex) throws IOException {
+    MessageDigest digest;
+    try {
+      digest = MessageDigest.getInstance("SHA-1");
+    } catch (NoSuchAlgorithmException e) {
+      throw new AssertionError();
     }
+    int offset = SIGNATURE_OFFSET + SIGNATURE_SIZE;
 
-    /**
-     * Returns the checksum of all but the first 12 bytes of {@code dex}.
-     */
-    public int computeChecksum(DexBuffer dex) throws IOException {
-        Adler32 adler32 = new Adler32();
-        int offset = CHECKSUM_OFFSET + CHECKSUM_SIZE;
+    byte[] bytes = dex.getBytes();
+    digest.update(bytes, offset, bytes.length - offset);
+    return digest.digest();
+  }
 
-        byte[] bytes = dex.getBytes();
-        adler32.update(bytes, offset, bytes.length - offset);
-        return (int) adler32.getValue();
-    }
+  /**
+   * Returns the checksum of all but the first 12 bytes of {@code dex}.
+   */
+  public int computeChecksum(DexBuffer dex) throws IOException {
+    Adler32 adler32 = new Adler32();
+    int offset = CHECKSUM_OFFSET + CHECKSUM_SIZE;
 
-    /**
-     * Generates the signature and checksum of the dex file {@code out} and
-     * writes them to the file.
-     */
-    public void writeHashes(DexBuffer dex) throws IOException {
-        byte[] signature = computeSignature(dex);
-        dex.open(SIGNATURE_OFFSET).write(signature);
+    byte[] bytes = dex.getBytes();
+    adler32.update(bytes, offset, bytes.length - offset);
+    return (int) adler32.getValue();
+  }
 
-        int checksum = computeChecksum(dex);
-        dex.open(CHECKSUM_OFFSET).writeInt(checksum);
-    }
+  /**
+   * Generates the signature and checksum of the dex file {@code out} and
+   * writes them to the file.
+   */
+  public void writeHashes(DexBuffer dex) throws IOException {
+    byte[] signature = computeSignature(dex);
+    dex.open(SIGNATURE_OFFSET).write(signature);
+
+    int checksum = computeChecksum(dex);
+    dex.open(CHECKSUM_OFFSET).writeInt(checksum);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/DexIndexPrinter.java b/dx/src/com/android/jack/dx/io/DexIndexPrinter.java
index 952649c..89dc385 100644
--- a/dx/src/com/android/jack/dx/io/DexIndexPrinter.java
+++ b/dx/src/com/android/jack/dx/io/DexIndexPrinter.java
@@ -25,101 +25,100 @@
  * Executable that prints all indices of a dex file.
  */
 public final class DexIndexPrinter {
-    private final DexBuffer dexBuffer;
-    private final TableOfContents tableOfContents;
+  private final DexBuffer dexBuffer;
+  private final TableOfContents tableOfContents;
 
-    public DexIndexPrinter(File file) throws IOException {
-        this.dexBuffer = new DexBuffer(file);
-        this.tableOfContents = dexBuffer.getTableOfContents();
-    }
+  public DexIndexPrinter(File file) throws IOException {
+    this.dexBuffer = new DexBuffer(file);
+    this.tableOfContents = dexBuffer.getTableOfContents();
+  }
 
-    private void printMap() {
-        for (TableOfContents.Section section : tableOfContents.sections) {
-            if (section.off != -1) {
-                System.out.println("section " + Integer.toHexString(section.type)
-                        + " off=" + Integer.toHexString(section.off)
-                        + " size=" + Integer.toHexString(section.size)
-                        + " byteCount=" + Integer.toHexString(section.byteCount));
-            }
-        }
+  private void printMap() {
+    for (TableOfContents.Section section : tableOfContents.sections) {
+      if (section.off != -1) {
+        System.out.println("section " + Integer.toHexString(section.type) + " off="
+            + Integer.toHexString(section.off) + " size=" + Integer.toHexString(section.size)
+            + " byteCount=" + Integer.toHexString(section.byteCount));
+      }
     }
+  }
 
-    private void printStrings() throws IOException {
-        int index = 0;
-        for (String string : dexBuffer.strings()) {
-            System.out.println("string " + index + ": " + string);
-            index++;
-        }
+  private void printStrings() throws IOException {
+    int index = 0;
+    for (String string : dexBuffer.strings()) {
+      System.out.println("string " + index + ": " + string);
+      index++;
     }
+  }
 
-    private void printTypeIds() throws IOException {
-        int index = 0;
-        for (Integer type : dexBuffer.typeIds()) {
-            System.out.println("type " + index + ": " + dexBuffer.strings().get(type));
-            index++;
-        }
+  private void printTypeIds() throws IOException {
+    int index = 0;
+    for (Integer type : dexBuffer.typeIds()) {
+      System.out.println("type " + index + ": " + dexBuffer.strings().get(type));
+      index++;
     }
+  }
 
-    private void printProtoIds() throws IOException {
-        int index = 0;
-        for (ProtoId protoId : dexBuffer.protoIds()) {
-            System.out.println("proto " + index + ": " + protoId);
-            index++;
-        }
+  private void printProtoIds() throws IOException {
+    int index = 0;
+    for (ProtoId protoId : dexBuffer.protoIds()) {
+      System.out.println("proto " + index + ": " + protoId);
+      index++;
     }
+  }
 
-    private void printFieldIds() throws IOException {
-        int index = 0;
-        for (FieldId fieldId : dexBuffer.fieldIds()) {
-            System.out.println("field " + index + ": " + fieldId);
-            index++;
-        }
+  private void printFieldIds() throws IOException {
+    int index = 0;
+    for (FieldId fieldId : dexBuffer.fieldIds()) {
+      System.out.println("field " + index + ": " + fieldId);
+      index++;
     }
+  }
 
-    private void printMethodIds() throws IOException {
-        int index = 0;
-        for (MethodId methodId : dexBuffer.methodIds()) {
-            System.out.println("methodId " + index + ": " + methodId);
-            index++;
-        }
+  private void printMethodIds() throws IOException {
+    int index = 0;
+    for (MethodId methodId : dexBuffer.methodIds()) {
+      System.out.println("methodId " + index + ": " + methodId);
+      index++;
     }
+  }
 
-    private void printTypeLists() throws IOException {
-        if (tableOfContents.typeLists.off == -1) {
-            System.out.println("No type lists");
-            return;
-        }
-        DexBuffer.Section in = dexBuffer.open(tableOfContents.typeLists.off);
-        for (int i = 0; i < tableOfContents.typeLists.size; i++) {
-            int size = in.readInt();
-            System.out.print("Type list i=" + i + ", size=" + size + ", elements=");
-            for (int t = 0; t < size; t++) {
-                System.out.print(" " + dexBuffer.typeNames().get((int) in.readShort()));
-            }
-            if (size % 2 == 1) {
-                in.readShort(); // retain alignment
-            }
-            System.out.println();
-        }
+  private void printTypeLists() throws IOException {
+    if (tableOfContents.typeLists.off == -1) {
+      System.out.println("No type lists");
+      return;
     }
+    DexBuffer.Section in = dexBuffer.open(tableOfContents.typeLists.off);
+    for (int i = 0; i < tableOfContents.typeLists.size; i++) {
+      int size = in.readInt();
+      System.out.print("Type list i=" + i + ", size=" + size + ", elements=");
+      for (int t = 0; t < size; t++) {
+        System.out.print(" " + dexBuffer.typeNames().get(in.readShort()));
+      }
+      if (size % 2 == 1) {
+        in.readShort(); // retain alignment
+      }
+      System.out.println();
+    }
+  }
 
-    private void printClassDefs() {
-        int index = 0;
-        for (ClassDef classDef : dexBuffer.classDefs()) {
-            System.out.println("class def " + index + ": " + classDef);
-            index++;
-        }
+  private void printClassDefs() {
+    int index = 0;
+    for (ClassDef classDef : dexBuffer.classDefs()) {
+      System.out.println("class def " + index + ": " + classDef);
+      index++;
     }
+  }
 
-    public static void main(String[] args) throws IOException {
-        DexIndexPrinter indexPrinter = new DexIndexPrinter(new File(args[0]));
-        indexPrinter.printMap();
-        indexPrinter.printStrings();
-        indexPrinter.printTypeIds();
-        indexPrinter.printProtoIds();
-        indexPrinter.printFieldIds();
-        indexPrinter.printMethodIds();
-        indexPrinter.printTypeLists();
-        indexPrinter.printClassDefs();
-    }
+  public static void main(String[] args) throws IOException {
+    DexIndexPrinter indexPrinter = new DexIndexPrinter(new File(args[0]));
+    indexPrinter.printMap();
+    indexPrinter.printStrings();
+    indexPrinter.printTypeIds();
+    indexPrinter.printProtoIds();
+    indexPrinter.printFieldIds();
+    indexPrinter.printMethodIds();
+    indexPrinter.printTypeLists();
+    indexPrinter.printClassDefs();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/EncodedValue.java b/dx/src/com/android/jack/dx/io/EncodedValue.java
index 861dfcf..604c80c 100644
--- a/dx/src/com/android/jack/dx/io/EncodedValue.java
+++ b/dx/src/com/android/jack/dx/io/EncodedValue.java
@@ -23,35 +23,37 @@
  * An encoded value or array.
  */
 public final class EncodedValue implements Comparable<EncodedValue> {
-    private final byte[] data;
+  private final byte[] data;
 
-    public EncodedValue(byte[] data) {
-        this.data = data;
-    }
+  public EncodedValue(byte[] data) {
+    this.data = data;
+  }
 
-    public ByteInput asByteInput() {
-        return new ByteArrayByteInput(data);
-    }
+  public ByteInput asByteInput() {
+    return new ByteArrayByteInput(data);
+  }
 
-    public byte[] getBytes() {
-        return data;
-    }
+  public byte[] getBytes() {
+    return data;
+  }
 
-    public void writeTo(DexBuffer.Section out) {
-        out.write(data);
-    }
+  public void writeTo(DexBuffer.Section out) {
+    out.write(data);
+  }
 
-    @Override public int compareTo(EncodedValue other) {
-        int size = Math.min(data.length, other.data.length);
-        for (int i = 0; i < size; i++) {
-            if (data[i] != other.data[i]) {
-                return (data[i] & 0xff) - (other.data[i] & 0xff);
-            }
-        }
-        return data.length - other.data.length;
+  @Override
+  public int compareTo(EncodedValue other) {
+    int size = Math.min(data.length, other.data.length);
+    for (int i = 0; i < size; i++) {
+      if (data[i] != other.data[i]) {
+        return (data[i] & 0xff) - (other.data[i] & 0xff);
+      }
     }
+    return data.length - other.data.length;
+  }
 
-    @Override public String toString() {
-        return Integer.toHexString(data[0] & 0xff) + "...(" + data.length + ")";
-    }
+  @Override
+  public String toString() {
+    return Integer.toHexString(data[0] & 0xff) + "...(" + data.length + ")";
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/EncodedValueReader.java b/dx/src/com/android/jack/dx/io/EncodedValueReader.java
index 694d736..d7eade0 100644
--- a/dx/src/com/android/jack/dx/io/EncodedValueReader.java
+++ b/dx/src/com/android/jack/dx/io/EncodedValueReader.java
@@ -21,126 +21,137 @@
 
 /**
  * SAX-style reader for encoded values.
- * TODO: convert this to a pull-style reader
+ * TODO(dx team): convert this to a pull-style reader
  */
 public class EncodedValueReader {
-    public static final int ENCODED_BYTE = 0x00;
-    public static final int ENCODED_SHORT = 0x02;
-    public static final int ENCODED_CHAR = 0x03;
-    public static final int ENCODED_INT = 0x04;
-    public static final int ENCODED_LONG = 0x06;
-    public static final int ENCODED_FLOAT = 0x10;
-    public static final int ENCODED_DOUBLE = 0x11;
-    public static final int ENCODED_STRING = 0x17;
-    public static final int ENCODED_TYPE = 0x18;
-    public static final int ENCODED_FIELD = 0x19;
-    public static final int ENCODED_ENUM = 0x1b;
-    public static final int ENCODED_METHOD = 0x1a;
-    public static final int ENCODED_ARRAY = 0x1c;
-    public static final int ENCODED_ANNOTATION = 0x1d;
-    public static final int ENCODED_NULL = 0x1e;
-    public static final int ENCODED_BOOLEAN = 0x1f;
+  public static final int ENCODED_BYTE = 0x00;
+  public static final int ENCODED_SHORT = 0x02;
+  public static final int ENCODED_CHAR = 0x03;
+  public static final int ENCODED_INT = 0x04;
+  public static final int ENCODED_LONG = 0x06;
+  public static final int ENCODED_FLOAT = 0x10;
+  public static final int ENCODED_DOUBLE = 0x11;
+  public static final int ENCODED_STRING = 0x17;
+  public static final int ENCODED_TYPE = 0x18;
+  public static final int ENCODED_FIELD = 0x19;
+  public static final int ENCODED_ENUM = 0x1b;
+  public static final int ENCODED_METHOD = 0x1a;
+  public static final int ENCODED_ARRAY = 0x1c;
+  public static final int ENCODED_ANNOTATION = 0x1d;
+  public static final int ENCODED_NULL = 0x1e;
+  public static final int ENCODED_BOOLEAN = 0x1f;
 
-    protected final ByteInput in;
+  protected final ByteInput in;
 
-    public EncodedValueReader(ByteInput in) {
-        this.in = in;
+  public EncodedValueReader(ByteInput in) {
+    this.in = in;
+  }
+
+  public EncodedValueReader(EncodedValue in) {
+    this(in.asByteInput());
+  }
+
+  public final void readArray() {
+    int size = Leb128Utils.readUnsignedLeb128(in);
+    visitArray(size);
+
+    for (int i = 0; i < size; i++) {
+      readValue();
     }
+  }
 
-    public EncodedValueReader(EncodedValue in) {
-        this(in.asByteInput());
+  public final void readAnnotation() {
+    int typeIndex = Leb128Utils.readUnsignedLeb128(in);
+    int size = Leb128Utils.readUnsignedLeb128(in);
+    visitAnnotation(typeIndex, size);
+
+    for (int i = 0; i < size; i++) {
+      visitAnnotationName(Leb128Utils.readUnsignedLeb128(in));
+      readValue();
     }
+  }
 
-    public final void readArray() {
-        int size = Leb128Utils.readUnsignedLeb128(in);
-        visitArray(size);
+  public final void readValue() {
+    int argAndType = in.readByte() & 0xff;
+    int type = argAndType & 0x1f;
+    int arg = (argAndType & 0xe0) >> 5;
+    int size = arg + 1;
 
-        for (int i = 0; i < size; i++) {
-            readValue();
-        }
+    switch (type) {
+      case ENCODED_BYTE:
+      case ENCODED_SHORT:
+      case ENCODED_CHAR:
+      case ENCODED_INT:
+      case ENCODED_LONG:
+      case ENCODED_FLOAT:
+      case ENCODED_DOUBLE:
+        visitPrimitive(argAndType, type, arg, size);
+        break;
+      case ENCODED_STRING:
+        visitString(type, readIndex(in, size));
+        break;
+      case ENCODED_TYPE:
+        visitType(type, readIndex(in, size));
+        break;
+      case ENCODED_FIELD:
+      case ENCODED_ENUM:
+        visitField(type, readIndex(in, size));
+        break;
+      case ENCODED_METHOD:
+        visitMethod(type, readIndex(in, size));
+        break;
+      case ENCODED_ARRAY:
+        visitArrayValue(argAndType);
+        readArray();
+        break;
+      case ENCODED_ANNOTATION:
+        visitAnnotationValue(argAndType);
+        readAnnotation();
+        break;
+      case ENCODED_NULL:
+        visitEncodedNull(argAndType);
+        break;
+      case ENCODED_BOOLEAN:
+        visitEncodedBoolean(argAndType);
+        break;
     }
+  }
 
-    public final void readAnnotation() {
-        int typeIndex = Leb128Utils.readUnsignedLeb128(in);
-        int size = Leb128Utils.readUnsignedLeb128(in);
-        visitAnnotation(typeIndex, size);
+  protected void visitArray(int size) {}
 
-        for (int i = 0; i < size; i++) {
-            visitAnnotationName(Leb128Utils.readUnsignedLeb128(in));
-            readValue();
-        }
+  protected void visitAnnotation(int typeIndex, int size) {}
+
+  protected void visitAnnotationName(int nameIndex) {}
+
+  protected void visitPrimitive(int argAndType, int type, int arg, int size) {
+    for (int i = 0; i < size; i++) {
+      in.readByte();
     }
+  }
 
-    public final void readValue() {
-        int argAndType = in.readByte() & 0xff;
-        int type = argAndType & 0x1f;
-        int arg = (argAndType & 0xe0) >> 5;
-        int size = arg + 1;
+  protected void visitString(int type, int index) {}
 
-        switch (type) {
-        case ENCODED_BYTE:
-        case ENCODED_SHORT:
-        case ENCODED_CHAR:
-        case ENCODED_INT:
-        case ENCODED_LONG:
-        case ENCODED_FLOAT:
-        case ENCODED_DOUBLE:
-            visitPrimitive(argAndType, type, arg, size);
-            break;
-        case ENCODED_STRING:
-            visitString(type, readIndex(in, size));
-            break;
-        case ENCODED_TYPE:
-            visitType(type, readIndex(in, size));
-            break;
-        case ENCODED_FIELD:
-        case ENCODED_ENUM:
-            visitField(type, readIndex(in, size));
-            break;
-        case ENCODED_METHOD:
-            visitMethod(type, readIndex(in, size));
-            break;
-        case ENCODED_ARRAY:
-            visitArrayValue(argAndType);
-            readArray();
-            break;
-        case ENCODED_ANNOTATION:
-            visitAnnotationValue(argAndType);
-            readAnnotation();
-            break;
-        case ENCODED_NULL:
-            visitEncodedNull(argAndType);
-            break;
-        case ENCODED_BOOLEAN:
-            visitEncodedBoolean(argAndType);
-            break;
-        }
+  protected void visitType(int type, int index) {}
+
+  protected void visitField(int type, int index) {}
+
+  protected void visitMethod(int type, int index) {}
+
+  protected void visitArrayValue(int argAndType) {}
+
+  protected void visitAnnotationValue(int argAndType) {}
+
+  protected void visitEncodedBoolean(int argAndType) {}
+
+  protected void visitEncodedNull(int argAndType) {}
+
+  private int readIndex(ByteInput in, int byteCount) {
+    int result = 0;
+    int shift = 0;
+    for (int i = 0; i < byteCount; i++) {
+      result += (in.readByte() & 0xff) << shift;
+      shift += 8;
     }
-
-    protected void visitArray(int size) {}
-    protected void visitAnnotation(int typeIndex, int size) {}
-    protected void visitAnnotationName(int nameIndex) {}
-    protected void visitPrimitive(int argAndType, int type, int arg, int size) {
-        for (int i = 0; i < size; i++) {
-            in.readByte();
-        }
-    }
-    protected void visitString(int type, int index) {}
-    protected void visitType(int type, int index) {}
-    protected void visitField(int type, int index) {}
-    protected void visitMethod(int type, int index) {}
-    protected void visitArrayValue(int argAndType) {}
-    protected void visitAnnotationValue(int argAndType) {}
-    protected void visitEncodedBoolean(int argAndType) {}
-    protected void visitEncodedNull(int argAndType) {}
-
-    private int readIndex(ByteInput in, int byteCount) {
-        int result = 0;
-        int shift = 0;
-        for (int i = 0; i < byteCount; i++) {
-            result += (in.readByte() & 0xff) << shift;
-            shift += 8;
-        }
-        return result;
-    }
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/FieldId.java b/dx/src/com/android/jack/dx/io/FieldId.java
index 73c749c..a0802a3 100644
--- a/dx/src/com/android/jack/dx/io/FieldId.java
+++ b/dx/src/com/android/jack/dx/io/FieldId.java
@@ -18,51 +18,56 @@
 
 import com.android.jack.dx.util.Unsigned;
 
+/**
+ * TODO(jack team)
+ */
 public final class FieldId implements Comparable<FieldId> {
-    private final DexBuffer buffer;
-    private final int declaringClassIndex;
-    private final int typeIndex;
-    private final int nameIndex;
+  private final DexBuffer buffer;
+  private final int declaringClassIndex;
+  private final int typeIndex;
+  private final int nameIndex;
 
-    public FieldId(DexBuffer buffer, int declaringClassIndex, int typeIndex, int nameIndex) {
-        this.buffer = buffer;
-        this.declaringClassIndex = declaringClassIndex;
-        this.typeIndex = typeIndex;
-        this.nameIndex = nameIndex;
-    }
+  public FieldId(DexBuffer buffer, int declaringClassIndex, int typeIndex, int nameIndex) {
+    this.buffer = buffer;
+    this.declaringClassIndex = declaringClassIndex;
+    this.typeIndex = typeIndex;
+    this.nameIndex = nameIndex;
+  }
 
-    public int getDeclaringClassIndex() {
-        return declaringClassIndex;
-    }
+  public int getDeclaringClassIndex() {
+    return declaringClassIndex;
+  }
 
-    public int getTypeIndex() {
-        return typeIndex;
-    }
+  public int getTypeIndex() {
+    return typeIndex;
+  }
 
-    public int getNameIndex() {
-        return nameIndex;
-    }
+  public int getNameIndex() {
+    return nameIndex;
+  }
 
-    public int compareTo(FieldId other) {
-        if (declaringClassIndex != other.declaringClassIndex) {
-            return Unsigned.compare(declaringClassIndex, other.declaringClassIndex);
-        }
-        if (nameIndex != other.nameIndex) {
-            return Unsigned.compare(nameIndex, other.nameIndex);
-        }
-        return Unsigned.compare(typeIndex, other.typeIndex); // should always be 0
+  @Override
+  public int compareTo(FieldId other) {
+    if (declaringClassIndex != other.declaringClassIndex) {
+      return Unsigned.compare(declaringClassIndex, other.declaringClassIndex);
     }
+    if (nameIndex != other.nameIndex) {
+      return Unsigned.compare(nameIndex, other.nameIndex);
+    }
+    return Unsigned.compare(typeIndex, other.typeIndex); // should always be 0
+  }
 
-    public void writeTo(DexBuffer.Section out) {
-        out.writeUnsignedShort(declaringClassIndex);
-        out.writeUnsignedShort(typeIndex);
-        out.writeInt(nameIndex);
-    }
+  public void writeTo(DexBuffer.Section out) {
+    out.writeUnsignedShort(declaringClassIndex);
+    out.writeUnsignedShort(typeIndex);
+    out.writeInt(nameIndex);
+  }
 
-    @Override public String toString() {
-        if (buffer == null) {
-            return declaringClassIndex + " " + typeIndex + " " + nameIndex;
-        }
-        return buffer.typeNames().get(typeIndex) + "." + buffer.strings().get(nameIndex);
+  @Override
+  public String toString() {
+    if (buffer == null) {
+      return declaringClassIndex + " " + typeIndex + " " + nameIndex;
     }
+    return buffer.typeNames().get(typeIndex) + "." + buffer.strings().get(nameIndex);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/IndexType.java b/dx/src/com/android/jack/dx/io/IndexType.java
index 0538966..515af59 100644
--- a/dx/src/com/android/jack/dx/io/IndexType.java
+++ b/dx/src/com/android/jack/dx/io/IndexType.java
@@ -20,33 +20,33 @@
  * The various types that an index in a Dalvik instruction might refer to.
  */
 public enum IndexType {
-    /** "Unknown." Used for undefined opcodes. */
-    UNKNOWN,
+  /** "Unknown." Used for undefined opcodes. */
+  UNKNOWN,
 
-    /** no index used */
-    NONE,
+  /** no index used */
+  NONE,
 
-    /** "It depends." Used for {@code throw-verification-error}. */
-    VARIES,
+  /** "It depends." Used for {@code throw-verification-error}. */
+  VARIES,
 
-    /** type reference index */
-    TYPE_REF,
+  /** type reference index */
+  TYPE_REF,
 
-    /** string reference index */
-    STRING_REF,
+  /** string reference index */
+  STRING_REF,
 
-    /** method reference index */
-    METHOD_REF,
+  /** method reference index */
+  METHOD_REF,
 
-    /** field reference index */
-    FIELD_REF,
+  /** field reference index */
+  FIELD_REF,
 
-    /** inline method index (for inline linked method invocations) */
-    INLINE_METHOD,
+  /** inline method index (for inline linked method invocations) */
+  INLINE_METHOD,
 
-    /** direct vtable offset (for static linked method invocations) */
-    VTABLE_OFFSET,
+  /** direct vtable offset (for static linked method invocations) */
+  VTABLE_OFFSET,
 
-    /** direct field offset (for static linked field accesses) */
-    FIELD_OFFSET;
+  /** direct field offset (for static linked field accesses) */
+  FIELD_OFFSET;
 }
diff --git a/dx/src/com/android/jack/dx/io/MethodId.java b/dx/src/com/android/jack/dx/io/MethodId.java
index 172c02f..da2a683 100644
--- a/dx/src/com/android/jack/dx/io/MethodId.java
+++ b/dx/src/com/android/jack/dx/io/MethodId.java
@@ -18,53 +18,57 @@
 
 import com.android.jack.dx.util.Unsigned;
 
+/**
+ * TODO(jack team)
+ */
 public final class MethodId implements Comparable<MethodId> {
-    private final DexBuffer buffer;
-    private final int declaringClassIndex;
-    private final int protoIndex;
-    private final int nameIndex;
+  private final DexBuffer buffer;
+  private final int declaringClassIndex;
+  private final int protoIndex;
+  private final int nameIndex;
 
-    public MethodId(DexBuffer buffer, int declaringClassIndex, int protoIndex, int nameIndex) {
-        this.buffer = buffer;
-        this.declaringClassIndex = declaringClassIndex;
-        this.protoIndex = protoIndex;
-        this.nameIndex = nameIndex;
-    }
+  public MethodId(DexBuffer buffer, int declaringClassIndex, int protoIndex, int nameIndex) {
+    this.buffer = buffer;
+    this.declaringClassIndex = declaringClassIndex;
+    this.protoIndex = protoIndex;
+    this.nameIndex = nameIndex;
+  }
 
-    public int getDeclaringClassIndex() {
-        return declaringClassIndex;
-    }
+  public int getDeclaringClassIndex() {
+    return declaringClassIndex;
+  }
 
-    public int getProtoIndex() {
-        return protoIndex;
-    }
+  public int getProtoIndex() {
+    return protoIndex;
+  }
 
-    public int getNameIndex() {
-        return nameIndex;
-    }
+  public int getNameIndex() {
+    return nameIndex;
+  }
 
-    public int compareTo(MethodId other) {
-        if (declaringClassIndex != other.declaringClassIndex) {
-            return Unsigned.compare(declaringClassIndex, other.declaringClassIndex);
-        }
-        if (nameIndex != other.nameIndex) {
-            return Unsigned.compare(nameIndex, other.nameIndex);
-        }
-        return Unsigned.compare(protoIndex, other.protoIndex);
+  @Override
+  public int compareTo(MethodId other) {
+    if (declaringClassIndex != other.declaringClassIndex) {
+      return Unsigned.compare(declaringClassIndex, other.declaringClassIndex);
     }
+    if (nameIndex != other.nameIndex) {
+      return Unsigned.compare(nameIndex, other.nameIndex);
+    }
+    return Unsigned.compare(protoIndex, other.protoIndex);
+  }
 
-    public void writeTo(DexBuffer.Section out) {
-        out.writeUnsignedShort(declaringClassIndex);
-        out.writeUnsignedShort(protoIndex);
-        out.writeInt(nameIndex);
-    }
+  public void writeTo(DexBuffer.Section out) {
+    out.writeUnsignedShort(declaringClassIndex);
+    out.writeUnsignedShort(protoIndex);
+    out.writeInt(nameIndex);
+  }
 
-    @Override public String toString() {
-        if (buffer == null) {
-            return declaringClassIndex + " " + protoIndex + " " + nameIndex;
-        }
-        return buffer.typeNames().get(declaringClassIndex)
-                + "." + buffer.strings().get(nameIndex)
-                + buffer.readTypeList(buffer.protoIds().get(protoIndex).getParametersOffset());
+  @Override
+  public String toString() {
+    if (buffer == null) {
+      return declaringClassIndex + " " + protoIndex + " " + nameIndex;
     }
+    return buffer.typeNames().get(declaringClassIndex) + "." + buffer.strings().get(nameIndex)
+        + buffer.readTypeList(buffer.protoIds().get(protoIndex).getParametersOffset());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/OpcodeInfo.java b/dx/src/com/android/jack/dx/io/OpcodeInfo.java
index 069784a..655e528 100644
--- a/dx/src/com/android/jack/dx/io/OpcodeInfo.java
+++ b/dx/src/com/android/jack/dx/io/OpcodeInfo.java
@@ -23,1243 +23,1016 @@
  * Information about each Dalvik opcode.
  */
 public final class OpcodeInfo {
-    /*
-     * TODO: Merge at least most of the info from the Dops class into
-     * this one.
-     */
+  /*
+   * TODO(dx team): Merge at least most of the info from the Dops class into
+   * this one.
+   */
 
-    /** non-null; array containing all the information */
-    private static final Info[] INFO;
+  /** non-null; array containing all the information */
+  private static final Info[] INFO;
 
-    /**
-     * pseudo-opcode used for nonstandard formatted "instructions"
-     * (which are mostly not actually instructions, though they do
-     * appear in instruction lists). TODO: Retire the usage of this
-     * constant.
-     */
-    public static final Info SPECIAL_FORMAT =
-        new Info(Opcodes.SPECIAL_FORMAT, "<special>",
-                InstructionCodec.FORMAT_00X, IndexType.NONE);
+  /**
+   * pseudo-opcode used for nonstandard formatted "instructions"
+   * (which are mostly not actually instructions, though they do
+   * appear in instruction lists). TODO(dx team): Retire the usage of this
+   * constant.
+   */
+  public static final Info SPECIAL_FORMAT =
+      new Info(Opcodes.SPECIAL_FORMAT, "<special>", InstructionCodec.FORMAT_00X, IndexType.NONE);
 
-    // TODO: These payload opcodes should be generated by opcode-gen.
+  // TODO(dx team): These payload opcodes should be generated by opcode-gen.
 
-    public static final Info PACKED_SWITCH_PAYLOAD =
-        new Info(Opcodes.PACKED_SWITCH_PAYLOAD, "packed-switch-payload",
-                InstructionCodec.FORMAT_PACKED_SWITCH_PAYLOAD,
-                IndexType.NONE);
+  public static final Info PACKED_SWITCH_PAYLOAD = new Info(Opcodes.PACKED_SWITCH_PAYLOAD,
+      "packed-switch-payload", InstructionCodec.FORMAT_PACKED_SWITCH_PAYLOAD, IndexType.NONE);
 
-    public static final Info SPARSE_SWITCH_PAYLOAD =
-        new Info(Opcodes.SPARSE_SWITCH_PAYLOAD, "sparse-switch-payload",
-                InstructionCodec.FORMAT_SPARSE_SWITCH_PAYLOAD,
-                IndexType.NONE);
+  public static final Info SPARSE_SWITCH_PAYLOAD = new Info(Opcodes.SPARSE_SWITCH_PAYLOAD,
+      "sparse-switch-payload", InstructionCodec.FORMAT_SPARSE_SWITCH_PAYLOAD, IndexType.NONE);
 
-    public static final Info FILL_ARRAY_DATA_PAYLOAD =
-        new Info(Opcodes.FILL_ARRAY_DATA_PAYLOAD, "fill-array-data-payload",
-                InstructionCodec.FORMAT_FILL_ARRAY_DATA_PAYLOAD,
-                IndexType.NONE);
+  public static final Info FILL_ARRAY_DATA_PAYLOAD = new Info(Opcodes.FILL_ARRAY_DATA_PAYLOAD,
+      "fill-array-data-payload", InstructionCodec.FORMAT_FILL_ARRAY_DATA_PAYLOAD, IndexType.NONE);
 
-    // BEGIN(opcode-info-defs); GENERATED AUTOMATICALLY BY opcode-gen
-    public static final Info NOP =
-        new Info(Opcodes.NOP, "nop",
-            InstructionCodec.FORMAT_10X, IndexType.NONE);
+  // BEGIN(opcode-info-defs); GENERATED AUTOMATICALLY BY opcode-gen
+  public static final Info NOP =
+      new Info(Opcodes.NOP, "nop", InstructionCodec.FORMAT_10X, IndexType.NONE);
 
-    public static final Info MOVE =
-        new Info(Opcodes.MOVE, "move",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MOVE =
+      new Info(Opcodes.MOVE, "move", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MOVE_FROM16 =
-        new Info(Opcodes.MOVE_FROM16, "move/from16",
-            InstructionCodec.FORMAT_22X, IndexType.NONE);
+  public static final Info MOVE_FROM16 =
+      new Info(Opcodes.MOVE_FROM16, "move/from16", InstructionCodec.FORMAT_22X, IndexType.NONE);
 
-    public static final Info MOVE_16 =
-        new Info(Opcodes.MOVE_16, "move/16",
-            InstructionCodec.FORMAT_32X, IndexType.NONE);
+  public static final Info MOVE_16 =
+      new Info(Opcodes.MOVE_16, "move/16", InstructionCodec.FORMAT_32X, IndexType.NONE);
 
-    public static final Info MOVE_WIDE =
-        new Info(Opcodes.MOVE_WIDE, "move-wide",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MOVE_WIDE =
+      new Info(Opcodes.MOVE_WIDE, "move-wide", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MOVE_WIDE_FROM16 =
-        new Info(Opcodes.MOVE_WIDE_FROM16, "move-wide/from16",
-            InstructionCodec.FORMAT_22X, IndexType.NONE);
+  public static final Info MOVE_WIDE_FROM16 = new Info(Opcodes.MOVE_WIDE_FROM16, "move-wide/from16",
+      InstructionCodec.FORMAT_22X, IndexType.NONE);
 
-    public static final Info MOVE_WIDE_16 =
-        new Info(Opcodes.MOVE_WIDE_16, "move-wide/16",
-            InstructionCodec.FORMAT_32X, IndexType.NONE);
+  public static final Info MOVE_WIDE_16 =
+      new Info(Opcodes.MOVE_WIDE_16, "move-wide/16", InstructionCodec.FORMAT_32X, IndexType.NONE);
 
-    public static final Info MOVE_OBJECT =
-        new Info(Opcodes.MOVE_OBJECT, "move-object",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MOVE_OBJECT =
+      new Info(Opcodes.MOVE_OBJECT, "move-object", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MOVE_OBJECT_FROM16 =
-        new Info(Opcodes.MOVE_OBJECT_FROM16, "move-object/from16",
-            InstructionCodec.FORMAT_22X, IndexType.NONE);
+  public static final Info MOVE_OBJECT_FROM16 = new Info(Opcodes.MOVE_OBJECT_FROM16,
+      "move-object/from16", InstructionCodec.FORMAT_22X, IndexType.NONE);
 
-    public static final Info MOVE_OBJECT_16 =
-        new Info(Opcodes.MOVE_OBJECT_16, "move-object/16",
-            InstructionCodec.FORMAT_32X, IndexType.NONE);
+  public static final Info MOVE_OBJECT_16 = new Info(Opcodes.MOVE_OBJECT_16, "move-object/16",
+      InstructionCodec.FORMAT_32X, IndexType.NONE);
 
-    public static final Info MOVE_RESULT =
-        new Info(Opcodes.MOVE_RESULT, "move-result",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MOVE_RESULT =
+      new Info(Opcodes.MOVE_RESULT, "move-result", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info MOVE_RESULT_WIDE =
-        new Info(Opcodes.MOVE_RESULT_WIDE, "move-result-wide",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MOVE_RESULT_WIDE = new Info(Opcodes.MOVE_RESULT_WIDE, "move-result-wide",
+      InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info MOVE_RESULT_OBJECT =
-        new Info(Opcodes.MOVE_RESULT_OBJECT, "move-result-object",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MOVE_RESULT_OBJECT = new Info(Opcodes.MOVE_RESULT_OBJECT,
+      "move-result-object", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info MOVE_EXCEPTION =
-        new Info(Opcodes.MOVE_EXCEPTION, "move-exception",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MOVE_EXCEPTION = new Info(Opcodes.MOVE_EXCEPTION, "move-exception",
+      InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info RETURN_VOID =
-        new Info(Opcodes.RETURN_VOID, "return-void",
-            InstructionCodec.FORMAT_10X, IndexType.NONE);
+  public static final Info RETURN_VOID =
+      new Info(Opcodes.RETURN_VOID, "return-void", InstructionCodec.FORMAT_10X, IndexType.NONE);
 
-    public static final Info RETURN =
-        new Info(Opcodes.RETURN, "return",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info RETURN =
+      new Info(Opcodes.RETURN, "return", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info RETURN_WIDE =
-        new Info(Opcodes.RETURN_WIDE, "return-wide",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info RETURN_WIDE =
+      new Info(Opcodes.RETURN_WIDE, "return-wide", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info RETURN_OBJECT =
-        new Info(Opcodes.RETURN_OBJECT, "return-object",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info RETURN_OBJECT =
+      new Info(Opcodes.RETURN_OBJECT, "return-object", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info CONST_4 =
-        new Info(Opcodes.CONST_4, "const/4",
-            InstructionCodec.FORMAT_11N, IndexType.NONE);
+  public static final Info CONST_4 =
+      new Info(Opcodes.CONST_4, "const/4", InstructionCodec.FORMAT_11N, IndexType.NONE);
 
-    public static final Info CONST_16 =
-        new Info(Opcodes.CONST_16, "const/16",
-            InstructionCodec.FORMAT_21S, IndexType.NONE);
+  public static final Info CONST_16 =
+      new Info(Opcodes.CONST_16, "const/16", InstructionCodec.FORMAT_21S, IndexType.NONE);
 
-    public static final Info CONST =
-        new Info(Opcodes.CONST, "const",
-            InstructionCodec.FORMAT_31I, IndexType.NONE);
+  public static final Info CONST =
+      new Info(Opcodes.CONST, "const", InstructionCodec.FORMAT_31I, IndexType.NONE);
 
-    public static final Info CONST_HIGH16 =
-        new Info(Opcodes.CONST_HIGH16, "const/high16",
-            InstructionCodec.FORMAT_21H, IndexType.NONE);
+  public static final Info CONST_HIGH16 =
+      new Info(Opcodes.CONST_HIGH16, "const/high16", InstructionCodec.FORMAT_21H, IndexType.NONE);
 
-    public static final Info CONST_WIDE_16 =
-        new Info(Opcodes.CONST_WIDE_16, "const-wide/16",
-            InstructionCodec.FORMAT_21S, IndexType.NONE);
+  public static final Info CONST_WIDE_16 =
+      new Info(Opcodes.CONST_WIDE_16, "const-wide/16", InstructionCodec.FORMAT_21S, IndexType.NONE);
 
-    public static final Info CONST_WIDE_32 =
-        new Info(Opcodes.CONST_WIDE_32, "const-wide/32",
-            InstructionCodec.FORMAT_31I, IndexType.NONE);
+  public static final Info CONST_WIDE_32 =
+      new Info(Opcodes.CONST_WIDE_32, "const-wide/32", InstructionCodec.FORMAT_31I, IndexType.NONE);
 
-    public static final Info CONST_WIDE =
-        new Info(Opcodes.CONST_WIDE, "const-wide",
-            InstructionCodec.FORMAT_51L, IndexType.NONE);
+  public static final Info CONST_WIDE =
+      new Info(Opcodes.CONST_WIDE, "const-wide", InstructionCodec.FORMAT_51L, IndexType.NONE);
 
-    public static final Info CONST_WIDE_HIGH16 =
-        new Info(Opcodes.CONST_WIDE_HIGH16, "const-wide/high16",
-            InstructionCodec.FORMAT_21H, IndexType.NONE);
+  public static final Info CONST_WIDE_HIGH16 = new Info(Opcodes.CONST_WIDE_HIGH16,
+      "const-wide/high16", InstructionCodec.FORMAT_21H, IndexType.NONE);
 
-    public static final Info CONST_STRING =
-        new Info(Opcodes.CONST_STRING, "const-string",
-            InstructionCodec.FORMAT_21C, IndexType.STRING_REF);
+  public static final Info CONST_STRING = new Info(Opcodes.CONST_STRING, "const-string",
+      InstructionCodec.FORMAT_21C, IndexType.STRING_REF);
 
-    public static final Info CONST_STRING_JUMBO =
-        new Info(Opcodes.CONST_STRING_JUMBO, "const-string/jumbo",
-            InstructionCodec.FORMAT_31C, IndexType.STRING_REF);
+  public static final Info CONST_STRING_JUMBO = new Info(Opcodes.CONST_STRING_JUMBO,
+      "const-string/jumbo", InstructionCodec.FORMAT_31C, IndexType.STRING_REF);
 
-    public static final Info CONST_CLASS =
-        new Info(Opcodes.CONST_CLASS, "const-class",
-            InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
+  public static final Info CONST_CLASS =
+      new Info(Opcodes.CONST_CLASS, "const-class", InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
 
-    public static final Info MONITOR_ENTER =
-        new Info(Opcodes.MONITOR_ENTER, "monitor-enter",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MONITOR_ENTER =
+      new Info(Opcodes.MONITOR_ENTER, "monitor-enter", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info MONITOR_EXIT =
-        new Info(Opcodes.MONITOR_EXIT, "monitor-exit",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info MONITOR_EXIT =
+      new Info(Opcodes.MONITOR_EXIT, "monitor-exit", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info CHECK_CAST =
-        new Info(Opcodes.CHECK_CAST, "check-cast",
-            InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
+  public static final Info CHECK_CAST =
+      new Info(Opcodes.CHECK_CAST, "check-cast", InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
 
-    public static final Info INSTANCE_OF =
-        new Info(Opcodes.INSTANCE_OF, "instance-of",
-            InstructionCodec.FORMAT_22C, IndexType.TYPE_REF);
+  public static final Info INSTANCE_OF =
+      new Info(Opcodes.INSTANCE_OF, "instance-of", InstructionCodec.FORMAT_22C, IndexType.TYPE_REF);
 
-    public static final Info ARRAY_LENGTH =
-        new Info(Opcodes.ARRAY_LENGTH, "array-length",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info ARRAY_LENGTH =
+      new Info(Opcodes.ARRAY_LENGTH, "array-length", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NEW_INSTANCE =
-        new Info(Opcodes.NEW_INSTANCE, "new-instance",
-            InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
+  public static final Info NEW_INSTANCE = new Info(Opcodes.NEW_INSTANCE, "new-instance",
+      InstructionCodec.FORMAT_21C, IndexType.TYPE_REF);
 
-    public static final Info NEW_ARRAY =
-        new Info(Opcodes.NEW_ARRAY, "new-array",
-            InstructionCodec.FORMAT_22C, IndexType.TYPE_REF);
+  public static final Info NEW_ARRAY =
+      new Info(Opcodes.NEW_ARRAY, "new-array", InstructionCodec.FORMAT_22C, IndexType.TYPE_REF);
 
-    public static final Info FILLED_NEW_ARRAY =
-        new Info(Opcodes.FILLED_NEW_ARRAY, "filled-new-array",
-            InstructionCodec.FORMAT_35C, IndexType.TYPE_REF);
+  public static final Info FILLED_NEW_ARRAY = new Info(Opcodes.FILLED_NEW_ARRAY, "filled-new-array",
+      InstructionCodec.FORMAT_35C, IndexType.TYPE_REF);
 
-    public static final Info FILLED_NEW_ARRAY_RANGE =
-        new Info(Opcodes.FILLED_NEW_ARRAY_RANGE, "filled-new-array/range",
-            InstructionCodec.FORMAT_3RC, IndexType.TYPE_REF);
+  public static final Info FILLED_NEW_ARRAY_RANGE = new Info(Opcodes.FILLED_NEW_ARRAY_RANGE,
+      "filled-new-array/range", InstructionCodec.FORMAT_3RC, IndexType.TYPE_REF);
 
-    public static final Info FILL_ARRAY_DATA =
-        new Info(Opcodes.FILL_ARRAY_DATA, "fill-array-data",
-            InstructionCodec.FORMAT_31T, IndexType.NONE);
+  public static final Info FILL_ARRAY_DATA = new Info(Opcodes.FILL_ARRAY_DATA, "fill-array-data",
+      InstructionCodec.FORMAT_31T, IndexType.NONE);
 
-    public static final Info THROW =
-        new Info(Opcodes.THROW, "throw",
-            InstructionCodec.FORMAT_11X, IndexType.NONE);
+  public static final Info THROW =
+      new Info(Opcodes.THROW, "throw", InstructionCodec.FORMAT_11X, IndexType.NONE);
 
-    public static final Info GOTO =
-        new Info(Opcodes.GOTO, "goto",
-            InstructionCodec.FORMAT_10T, IndexType.NONE);
+  public static final Info GOTO =
+      new Info(Opcodes.GOTO, "goto", InstructionCodec.FORMAT_10T, IndexType.NONE);
 
-    public static final Info GOTO_16 =
-        new Info(Opcodes.GOTO_16, "goto/16",
-            InstructionCodec.FORMAT_20T, IndexType.NONE);
+  public static final Info GOTO_16 =
+      new Info(Opcodes.GOTO_16, "goto/16", InstructionCodec.FORMAT_20T, IndexType.NONE);
 
-    public static final Info GOTO_32 =
-        new Info(Opcodes.GOTO_32, "goto/32",
-            InstructionCodec.FORMAT_30T, IndexType.NONE);
+  public static final Info GOTO_32 =
+      new Info(Opcodes.GOTO_32, "goto/32", InstructionCodec.FORMAT_30T, IndexType.NONE);
 
-    public static final Info PACKED_SWITCH =
-        new Info(Opcodes.PACKED_SWITCH, "packed-switch",
-            InstructionCodec.FORMAT_31T, IndexType.NONE);
+  public static final Info PACKED_SWITCH =
+      new Info(Opcodes.PACKED_SWITCH, "packed-switch", InstructionCodec.FORMAT_31T, IndexType.NONE);
 
-    public static final Info SPARSE_SWITCH =
-        new Info(Opcodes.SPARSE_SWITCH, "sparse-switch",
-            InstructionCodec.FORMAT_31T, IndexType.NONE);
+  public static final Info SPARSE_SWITCH =
+      new Info(Opcodes.SPARSE_SWITCH, "sparse-switch", InstructionCodec.FORMAT_31T, IndexType.NONE);
 
-    public static final Info CMPL_FLOAT =
-        new Info(Opcodes.CMPL_FLOAT, "cmpl-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info CMPL_FLOAT =
+      new Info(Opcodes.CMPL_FLOAT, "cmpl-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info CMPG_FLOAT =
-        new Info(Opcodes.CMPG_FLOAT, "cmpg-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info CMPG_FLOAT =
+      new Info(Opcodes.CMPG_FLOAT, "cmpg-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info CMPL_DOUBLE =
-        new Info(Opcodes.CMPL_DOUBLE, "cmpl-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info CMPL_DOUBLE =
+      new Info(Opcodes.CMPL_DOUBLE, "cmpl-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info CMPG_DOUBLE =
-        new Info(Opcodes.CMPG_DOUBLE, "cmpg-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info CMPG_DOUBLE =
+      new Info(Opcodes.CMPG_DOUBLE, "cmpg-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info CMP_LONG =
-        new Info(Opcodes.CMP_LONG, "cmp-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info CMP_LONG =
+      new Info(Opcodes.CMP_LONG, "cmp-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info IF_EQ =
-        new Info(Opcodes.IF_EQ, "if-eq",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_EQ =
+      new Info(Opcodes.IF_EQ, "if-eq", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_NE =
-        new Info(Opcodes.IF_NE, "if-ne",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_NE =
+      new Info(Opcodes.IF_NE, "if-ne", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_LT =
-        new Info(Opcodes.IF_LT, "if-lt",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_LT =
+      new Info(Opcodes.IF_LT, "if-lt", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_GE =
-        new Info(Opcodes.IF_GE, "if-ge",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_GE =
+      new Info(Opcodes.IF_GE, "if-ge", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_GT =
-        new Info(Opcodes.IF_GT, "if-gt",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_GT =
+      new Info(Opcodes.IF_GT, "if-gt", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_LE =
-        new Info(Opcodes.IF_LE, "if-le",
-            InstructionCodec.FORMAT_22T, IndexType.NONE);
+  public static final Info IF_LE =
+      new Info(Opcodes.IF_LE, "if-le", InstructionCodec.FORMAT_22T, IndexType.NONE);
 
-    public static final Info IF_EQZ =
-        new Info(Opcodes.IF_EQZ, "if-eqz",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_EQZ =
+      new Info(Opcodes.IF_EQZ, "if-eqz", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info IF_NEZ =
-        new Info(Opcodes.IF_NEZ, "if-nez",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_NEZ =
+      new Info(Opcodes.IF_NEZ, "if-nez", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info IF_LTZ =
-        new Info(Opcodes.IF_LTZ, "if-ltz",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_LTZ =
+      new Info(Opcodes.IF_LTZ, "if-ltz", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info IF_GEZ =
-        new Info(Opcodes.IF_GEZ, "if-gez",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_GEZ =
+      new Info(Opcodes.IF_GEZ, "if-gez", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info IF_GTZ =
-        new Info(Opcodes.IF_GTZ, "if-gtz",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_GTZ =
+      new Info(Opcodes.IF_GTZ, "if-gtz", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info IF_LEZ =
-        new Info(Opcodes.IF_LEZ, "if-lez",
-            InstructionCodec.FORMAT_21T, IndexType.NONE);
+  public static final Info IF_LEZ =
+      new Info(Opcodes.IF_LEZ, "if-lez", InstructionCodec.FORMAT_21T, IndexType.NONE);
 
-    public static final Info AGET =
-        new Info(Opcodes.AGET, "aget",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET =
+      new Info(Opcodes.AGET, "aget", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_WIDE =
-        new Info(Opcodes.AGET_WIDE, "aget-wide",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_WIDE =
+      new Info(Opcodes.AGET_WIDE, "aget-wide", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_OBJECT =
-        new Info(Opcodes.AGET_OBJECT, "aget-object",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_OBJECT =
+      new Info(Opcodes.AGET_OBJECT, "aget-object", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_BOOLEAN =
-        new Info(Opcodes.AGET_BOOLEAN, "aget-boolean",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_BOOLEAN =
+      new Info(Opcodes.AGET_BOOLEAN, "aget-boolean", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_BYTE =
-        new Info(Opcodes.AGET_BYTE, "aget-byte",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_BYTE =
+      new Info(Opcodes.AGET_BYTE, "aget-byte", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_CHAR =
-        new Info(Opcodes.AGET_CHAR, "aget-char",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_CHAR =
+      new Info(Opcodes.AGET_CHAR, "aget-char", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AGET_SHORT =
-        new Info(Opcodes.AGET_SHORT, "aget-short",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AGET_SHORT =
+      new Info(Opcodes.AGET_SHORT, "aget-short", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT =
-        new Info(Opcodes.APUT, "aput",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT =
+      new Info(Opcodes.APUT, "aput", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_WIDE =
-        new Info(Opcodes.APUT_WIDE, "aput-wide",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_WIDE =
+      new Info(Opcodes.APUT_WIDE, "aput-wide", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_OBJECT =
-        new Info(Opcodes.APUT_OBJECT, "aput-object",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_OBJECT =
+      new Info(Opcodes.APUT_OBJECT, "aput-object", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_BOOLEAN =
-        new Info(Opcodes.APUT_BOOLEAN, "aput-boolean",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_BOOLEAN =
+      new Info(Opcodes.APUT_BOOLEAN, "aput-boolean", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_BYTE =
-        new Info(Opcodes.APUT_BYTE, "aput-byte",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_BYTE =
+      new Info(Opcodes.APUT_BYTE, "aput-byte", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_CHAR =
-        new Info(Opcodes.APUT_CHAR, "aput-char",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_CHAR =
+      new Info(Opcodes.APUT_CHAR, "aput-char", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info APUT_SHORT =
-        new Info(Opcodes.APUT_SHORT, "aput-short",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info APUT_SHORT =
+      new Info(Opcodes.APUT_SHORT, "aput-short", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info IGET =
-        new Info(Opcodes.IGET, "iget",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET =
+      new Info(Opcodes.IGET, "iget", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_WIDE =
-        new Info(Opcodes.IGET_WIDE, "iget-wide",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_WIDE =
+      new Info(Opcodes.IGET_WIDE, "iget-wide", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_OBJECT =
-        new Info(Opcodes.IGET_OBJECT, "iget-object",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_OBJECT = new Info(Opcodes.IGET_OBJECT, "iget-object",
+      InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_BOOLEAN =
-        new Info(Opcodes.IGET_BOOLEAN, "iget-boolean",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_BOOLEAN = new Info(Opcodes.IGET_BOOLEAN, "iget-boolean",
+      InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_BYTE =
-        new Info(Opcodes.IGET_BYTE, "iget-byte",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_BYTE =
+      new Info(Opcodes.IGET_BYTE, "iget-byte", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_CHAR =
-        new Info(Opcodes.IGET_CHAR, "iget-char",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_CHAR =
+      new Info(Opcodes.IGET_CHAR, "iget-char", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IGET_SHORT =
-        new Info(Opcodes.IGET_SHORT, "iget-short",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IGET_SHORT =
+      new Info(Opcodes.IGET_SHORT, "iget-short", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT =
-        new Info(Opcodes.IPUT, "iput",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT =
+      new Info(Opcodes.IPUT, "iput", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_WIDE =
-        new Info(Opcodes.IPUT_WIDE, "iput-wide",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_WIDE =
+      new Info(Opcodes.IPUT_WIDE, "iput-wide", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_OBJECT =
-        new Info(Opcodes.IPUT_OBJECT, "iput-object",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_OBJECT = new Info(Opcodes.IPUT_OBJECT, "iput-object",
+      InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_BOOLEAN =
-        new Info(Opcodes.IPUT_BOOLEAN, "iput-boolean",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_BOOLEAN = new Info(Opcodes.IPUT_BOOLEAN, "iput-boolean",
+      InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_BYTE =
-        new Info(Opcodes.IPUT_BYTE, "iput-byte",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_BYTE =
+      new Info(Opcodes.IPUT_BYTE, "iput-byte", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_CHAR =
-        new Info(Opcodes.IPUT_CHAR, "iput-char",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_CHAR =
+      new Info(Opcodes.IPUT_CHAR, "iput-char", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info IPUT_SHORT =
-        new Info(Opcodes.IPUT_SHORT, "iput-short",
-            InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
+  public static final Info IPUT_SHORT =
+      new Info(Opcodes.IPUT_SHORT, "iput-short", InstructionCodec.FORMAT_22C, IndexType.FIELD_REF);
 
-    public static final Info SGET =
-        new Info(Opcodes.SGET, "sget",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET =
+      new Info(Opcodes.SGET, "sget", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_WIDE =
-        new Info(Opcodes.SGET_WIDE, "sget-wide",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_WIDE =
+      new Info(Opcodes.SGET_WIDE, "sget-wide", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_OBJECT =
-        new Info(Opcodes.SGET_OBJECT, "sget-object",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_OBJECT = new Info(Opcodes.SGET_OBJECT, "sget-object",
+      InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_BOOLEAN =
-        new Info(Opcodes.SGET_BOOLEAN, "sget-boolean",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_BOOLEAN = new Info(Opcodes.SGET_BOOLEAN, "sget-boolean",
+      InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_BYTE =
-        new Info(Opcodes.SGET_BYTE, "sget-byte",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_BYTE =
+      new Info(Opcodes.SGET_BYTE, "sget-byte", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_CHAR =
-        new Info(Opcodes.SGET_CHAR, "sget-char",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_CHAR =
+      new Info(Opcodes.SGET_CHAR, "sget-char", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SGET_SHORT =
-        new Info(Opcodes.SGET_SHORT, "sget-short",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SGET_SHORT =
+      new Info(Opcodes.SGET_SHORT, "sget-short", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT =
-        new Info(Opcodes.SPUT, "sput",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT =
+      new Info(Opcodes.SPUT, "sput", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_WIDE =
-        new Info(Opcodes.SPUT_WIDE, "sput-wide",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_WIDE =
+      new Info(Opcodes.SPUT_WIDE, "sput-wide", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_OBJECT =
-        new Info(Opcodes.SPUT_OBJECT, "sput-object",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_OBJECT = new Info(Opcodes.SPUT_OBJECT, "sput-object",
+      InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_BOOLEAN =
-        new Info(Opcodes.SPUT_BOOLEAN, "sput-boolean",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_BOOLEAN = new Info(Opcodes.SPUT_BOOLEAN, "sput-boolean",
+      InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_BYTE =
-        new Info(Opcodes.SPUT_BYTE, "sput-byte",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_BYTE =
+      new Info(Opcodes.SPUT_BYTE, "sput-byte", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_CHAR =
-        new Info(Opcodes.SPUT_CHAR, "sput-char",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_CHAR =
+      new Info(Opcodes.SPUT_CHAR, "sput-char", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info SPUT_SHORT =
-        new Info(Opcodes.SPUT_SHORT, "sput-short",
-            InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
+  public static final Info SPUT_SHORT =
+      new Info(Opcodes.SPUT_SHORT, "sput-short", InstructionCodec.FORMAT_21C, IndexType.FIELD_REF);
 
-    public static final Info INVOKE_VIRTUAL =
-        new Info(Opcodes.INVOKE_VIRTUAL, "invoke-virtual",
-            InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
+  public static final Info INVOKE_VIRTUAL = new Info(Opcodes.INVOKE_VIRTUAL, "invoke-virtual",
+      InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_SUPER =
-        new Info(Opcodes.INVOKE_SUPER, "invoke-super",
-            InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
+  public static final Info INVOKE_SUPER = new Info(Opcodes.INVOKE_SUPER, "invoke-super",
+      InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_DIRECT =
-        new Info(Opcodes.INVOKE_DIRECT, "invoke-direct",
-            InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
+  public static final Info INVOKE_DIRECT = new Info(Opcodes.INVOKE_DIRECT, "invoke-direct",
+      InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_STATIC =
-        new Info(Opcodes.INVOKE_STATIC, "invoke-static",
-            InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
+  public static final Info INVOKE_STATIC = new Info(Opcodes.INVOKE_STATIC, "invoke-static",
+      InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_INTERFACE =
-        new Info(Opcodes.INVOKE_INTERFACE, "invoke-interface",
-            InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
+  public static final Info INVOKE_INTERFACE = new Info(Opcodes.INVOKE_INTERFACE, "invoke-interface",
+      InstructionCodec.FORMAT_35C, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_VIRTUAL_RANGE =
-        new Info(Opcodes.INVOKE_VIRTUAL_RANGE, "invoke-virtual/range",
-            InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
+  public static final Info INVOKE_VIRTUAL_RANGE = new Info(Opcodes.INVOKE_VIRTUAL_RANGE,
+      "invoke-virtual/range", InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_SUPER_RANGE =
-        new Info(Opcodes.INVOKE_SUPER_RANGE, "invoke-super/range",
-            InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
+  public static final Info INVOKE_SUPER_RANGE = new Info(Opcodes.INVOKE_SUPER_RANGE,
+      "invoke-super/range", InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_DIRECT_RANGE =
-        new Info(Opcodes.INVOKE_DIRECT_RANGE, "invoke-direct/range",
-            InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
+  public static final Info INVOKE_DIRECT_RANGE = new Info(Opcodes.INVOKE_DIRECT_RANGE,
+      "invoke-direct/range", InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_STATIC_RANGE =
-        new Info(Opcodes.INVOKE_STATIC_RANGE, "invoke-static/range",
-            InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
+  public static final Info INVOKE_STATIC_RANGE = new Info(Opcodes.INVOKE_STATIC_RANGE,
+      "invoke-static/range", InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
 
-    public static final Info INVOKE_INTERFACE_RANGE =
-        new Info(Opcodes.INVOKE_INTERFACE_RANGE, "invoke-interface/range",
-            InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
+  public static final Info INVOKE_INTERFACE_RANGE = new Info(Opcodes.INVOKE_INTERFACE_RANGE,
+      "invoke-interface/range", InstructionCodec.FORMAT_3RC, IndexType.METHOD_REF);
 
-    public static final Info NEG_INT =
-        new Info(Opcodes.NEG_INT, "neg-int",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NEG_INT =
+      new Info(Opcodes.NEG_INT, "neg-int", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NOT_INT =
-        new Info(Opcodes.NOT_INT, "not-int",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NOT_INT =
+      new Info(Opcodes.NOT_INT, "not-int", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NEG_LONG =
-        new Info(Opcodes.NEG_LONG, "neg-long",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NEG_LONG =
+      new Info(Opcodes.NEG_LONG, "neg-long", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NOT_LONG =
-        new Info(Opcodes.NOT_LONG, "not-long",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NOT_LONG =
+      new Info(Opcodes.NOT_LONG, "not-long", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NEG_FLOAT =
-        new Info(Opcodes.NEG_FLOAT, "neg-float",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NEG_FLOAT =
+      new Info(Opcodes.NEG_FLOAT, "neg-float", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info NEG_DOUBLE =
-        new Info(Opcodes.NEG_DOUBLE, "neg-double",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info NEG_DOUBLE =
+      new Info(Opcodes.NEG_DOUBLE, "neg-double", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_LONG =
-        new Info(Opcodes.INT_TO_LONG, "int-to-long",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_LONG =
+      new Info(Opcodes.INT_TO_LONG, "int-to-long", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_FLOAT =
-        new Info(Opcodes.INT_TO_FLOAT, "int-to-float",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_FLOAT =
+      new Info(Opcodes.INT_TO_FLOAT, "int-to-float", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_DOUBLE =
-        new Info(Opcodes.INT_TO_DOUBLE, "int-to-double",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_DOUBLE =
+      new Info(Opcodes.INT_TO_DOUBLE, "int-to-double", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info LONG_TO_INT =
-        new Info(Opcodes.LONG_TO_INT, "long-to-int",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info LONG_TO_INT =
+      new Info(Opcodes.LONG_TO_INT, "long-to-int", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info LONG_TO_FLOAT =
-        new Info(Opcodes.LONG_TO_FLOAT, "long-to-float",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info LONG_TO_FLOAT =
+      new Info(Opcodes.LONG_TO_FLOAT, "long-to-float", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info LONG_TO_DOUBLE =
-        new Info(Opcodes.LONG_TO_DOUBLE, "long-to-double",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info LONG_TO_DOUBLE = new Info(Opcodes.LONG_TO_DOUBLE, "long-to-double",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info FLOAT_TO_INT =
-        new Info(Opcodes.FLOAT_TO_INT, "float-to-int",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info FLOAT_TO_INT =
+      new Info(Opcodes.FLOAT_TO_INT, "float-to-int", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info FLOAT_TO_LONG =
-        new Info(Opcodes.FLOAT_TO_LONG, "float-to-long",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info FLOAT_TO_LONG =
+      new Info(Opcodes.FLOAT_TO_LONG, "float-to-long", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info FLOAT_TO_DOUBLE =
-        new Info(Opcodes.FLOAT_TO_DOUBLE, "float-to-double",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info FLOAT_TO_DOUBLE = new Info(Opcodes.FLOAT_TO_DOUBLE, "float-to-double",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DOUBLE_TO_INT =
-        new Info(Opcodes.DOUBLE_TO_INT, "double-to-int",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DOUBLE_TO_INT =
+      new Info(Opcodes.DOUBLE_TO_INT, "double-to-int", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DOUBLE_TO_LONG =
-        new Info(Opcodes.DOUBLE_TO_LONG, "double-to-long",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DOUBLE_TO_LONG = new Info(Opcodes.DOUBLE_TO_LONG, "double-to-long",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DOUBLE_TO_FLOAT =
-        new Info(Opcodes.DOUBLE_TO_FLOAT, "double-to-float",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DOUBLE_TO_FLOAT = new Info(Opcodes.DOUBLE_TO_FLOAT, "double-to-float",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_BYTE =
-        new Info(Opcodes.INT_TO_BYTE, "int-to-byte",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_BYTE =
+      new Info(Opcodes.INT_TO_BYTE, "int-to-byte", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_CHAR =
-        new Info(Opcodes.INT_TO_CHAR, "int-to-char",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_CHAR =
+      new Info(Opcodes.INT_TO_CHAR, "int-to-char", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info INT_TO_SHORT =
-        new Info(Opcodes.INT_TO_SHORT, "int-to-short",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info INT_TO_SHORT =
+      new Info(Opcodes.INT_TO_SHORT, "int-to-short", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info ADD_INT =
-        new Info(Opcodes.ADD_INT, "add-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info ADD_INT =
+      new Info(Opcodes.ADD_INT, "add-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SUB_INT =
-        new Info(Opcodes.SUB_INT, "sub-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SUB_INT =
+      new Info(Opcodes.SUB_INT, "sub-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info MUL_INT =
-        new Info(Opcodes.MUL_INT, "mul-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info MUL_INT =
+      new Info(Opcodes.MUL_INT, "mul-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info DIV_INT =
-        new Info(Opcodes.DIV_INT, "div-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info DIV_INT =
+      new Info(Opcodes.DIV_INT, "div-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info REM_INT =
-        new Info(Opcodes.REM_INT, "rem-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info REM_INT =
+      new Info(Opcodes.REM_INT, "rem-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AND_INT =
-        new Info(Opcodes.AND_INT, "and-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info AND_INT =
+      new Info(Opcodes.AND_INT, "and-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info OR_INT =
-        new Info(Opcodes.OR_INT, "or-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info OR_INT =
+      new Info(Opcodes.OR_INT, "or-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info XOR_INT =
-        new Info(Opcodes.XOR_INT, "xor-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info XOR_INT =
+      new Info(Opcodes.XOR_INT, "xor-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SHL_INT =
-        new Info(Opcodes.SHL_INT, "shl-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SHL_INT =
+      new Info(Opcodes.SHL_INT, "shl-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SHR_INT =
-        new Info(Opcodes.SHR_INT, "shr-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SHR_INT =
+      new Info(Opcodes.SHR_INT, "shr-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info USHR_INT =
-        new Info(Opcodes.USHR_INT, "ushr-int",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info USHR_INT =
+      new Info(Opcodes.USHR_INT, "ushr-int", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info ADD_LONG =
-        new Info(Opcodes.ADD_LONG, "add-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info ADD_LONG =
+      new Info(Opcodes.ADD_LONG, "add-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SUB_LONG =
-        new Info(Opcodes.SUB_LONG, "sub-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SUB_LONG =
+      new Info(Opcodes.SUB_LONG, "sub-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info MUL_LONG =
-        new Info(Opcodes.MUL_LONG, "mul-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info MUL_LONG =
+      new Info(Opcodes.MUL_LONG, "mul-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info DIV_LONG =
-        new Info(Opcodes.DIV_LONG, "div-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info DIV_LONG =
+      new Info(Opcodes.DIV_LONG, "div-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info REM_LONG =
-        new Info(Opcodes.REM_LONG, "rem-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info REM_LONG =
+      new Info(Opcodes.REM_LONG, "rem-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
+
+  public static final Info AND_LONG =
+      new Info(Opcodes.AND_LONG, "and-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
+
+  public static final Info OR_LONG =
+      new Info(Opcodes.OR_LONG, "or-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
+
+  public static final Info XOR_LONG =
+      new Info(Opcodes.XOR_LONG, "xor-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info AND_LONG =
-        new Info(Opcodes.AND_LONG, "and-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SHL_LONG =
+      new Info(Opcodes.SHL_LONG, "shl-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info OR_LONG =
-        new Info(Opcodes.OR_LONG, "or-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SHR_LONG =
+      new Info(Opcodes.SHR_LONG, "shr-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info XOR_LONG =
-        new Info(Opcodes.XOR_LONG, "xor-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info USHR_LONG =
+      new Info(Opcodes.USHR_LONG, "ushr-long", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SHL_LONG =
-        new Info(Opcodes.SHL_LONG, "shl-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info ADD_FLOAT =
+      new Info(Opcodes.ADD_FLOAT, "add-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SHR_LONG =
-        new Info(Opcodes.SHR_LONG, "shr-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SUB_FLOAT =
+      new Info(Opcodes.SUB_FLOAT, "sub-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info USHR_LONG =
-        new Info(Opcodes.USHR_LONG, "ushr-long",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info MUL_FLOAT =
+      new Info(Opcodes.MUL_FLOAT, "mul-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info ADD_FLOAT =
-        new Info(Opcodes.ADD_FLOAT, "add-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info DIV_FLOAT =
+      new Info(Opcodes.DIV_FLOAT, "div-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SUB_FLOAT =
-        new Info(Opcodes.SUB_FLOAT, "sub-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info REM_FLOAT =
+      new Info(Opcodes.REM_FLOAT, "rem-float", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info MUL_FLOAT =
-        new Info(Opcodes.MUL_FLOAT, "mul-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info ADD_DOUBLE =
+      new Info(Opcodes.ADD_DOUBLE, "add-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info DIV_FLOAT =
-        new Info(Opcodes.DIV_FLOAT, "div-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SUB_DOUBLE =
+      new Info(Opcodes.SUB_DOUBLE, "sub-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info REM_FLOAT =
-        new Info(Opcodes.REM_FLOAT, "rem-float",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info MUL_DOUBLE =
+      new Info(Opcodes.MUL_DOUBLE, "mul-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info ADD_DOUBLE =
-        new Info(Opcodes.ADD_DOUBLE, "add-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info DIV_DOUBLE =
+      new Info(Opcodes.DIV_DOUBLE, "div-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info SUB_DOUBLE =
-        new Info(Opcodes.SUB_DOUBLE, "sub-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info REM_DOUBLE =
+      new Info(Opcodes.REM_DOUBLE, "rem-double", InstructionCodec.FORMAT_23X, IndexType.NONE);
 
-    public static final Info MUL_DOUBLE =
-        new Info(Opcodes.MUL_DOUBLE, "mul-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info ADD_INT_2ADDR =
+      new Info(Opcodes.ADD_INT_2ADDR, "add-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DIV_DOUBLE =
-        new Info(Opcodes.DIV_DOUBLE, "div-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info SUB_INT_2ADDR =
+      new Info(Opcodes.SUB_INT_2ADDR, "sub-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info REM_DOUBLE =
-        new Info(Opcodes.REM_DOUBLE, "rem-double",
-            InstructionCodec.FORMAT_23X, IndexType.NONE);
+  public static final Info MUL_INT_2ADDR =
+      new Info(Opcodes.MUL_INT_2ADDR, "mul-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info ADD_INT_2ADDR =
-        new Info(Opcodes.ADD_INT_2ADDR, "add-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DIV_INT_2ADDR =
+      new Info(Opcodes.DIV_INT_2ADDR, "div-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SUB_INT_2ADDR =
-        new Info(Opcodes.SUB_INT_2ADDR, "sub-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info REM_INT_2ADDR =
+      new Info(Opcodes.REM_INT_2ADDR, "rem-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MUL_INT_2ADDR =
-        new Info(Opcodes.MUL_INT_2ADDR, "mul-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info AND_INT_2ADDR =
+      new Info(Opcodes.AND_INT_2ADDR, "and-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DIV_INT_2ADDR =
-        new Info(Opcodes.DIV_INT_2ADDR, "div-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info OR_INT_2ADDR =
+      new Info(Opcodes.OR_INT_2ADDR, "or-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info REM_INT_2ADDR =
-        new Info(Opcodes.REM_INT_2ADDR, "rem-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info XOR_INT_2ADDR =
+      new Info(Opcodes.XOR_INT_2ADDR, "xor-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info AND_INT_2ADDR =
-        new Info(Opcodes.AND_INT_2ADDR, "and-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SHL_INT_2ADDR =
+      new Info(Opcodes.SHL_INT_2ADDR, "shl-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info OR_INT_2ADDR =
-        new Info(Opcodes.OR_INT_2ADDR, "or-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SHR_INT_2ADDR =
+      new Info(Opcodes.SHR_INT_2ADDR, "shr-int/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info XOR_INT_2ADDR =
-        new Info(Opcodes.XOR_INT_2ADDR, "xor-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info USHR_INT_2ADDR = new Info(Opcodes.USHR_INT_2ADDR, "ushr-int/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SHL_INT_2ADDR =
-        new Info(Opcodes.SHL_INT_2ADDR, "shl-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info ADD_LONG_2ADDR = new Info(Opcodes.ADD_LONG_2ADDR, "add-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SHR_INT_2ADDR =
-        new Info(Opcodes.SHR_INT_2ADDR, "shr-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SUB_LONG_2ADDR = new Info(Opcodes.SUB_LONG_2ADDR, "sub-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info USHR_INT_2ADDR =
-        new Info(Opcodes.USHR_INT_2ADDR, "ushr-int/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MUL_LONG_2ADDR = new Info(Opcodes.MUL_LONG_2ADDR, "mul-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info ADD_LONG_2ADDR =
-        new Info(Opcodes.ADD_LONG_2ADDR, "add-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DIV_LONG_2ADDR = new Info(Opcodes.DIV_LONG_2ADDR, "div-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SUB_LONG_2ADDR =
-        new Info(Opcodes.SUB_LONG_2ADDR, "sub-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info REM_LONG_2ADDR = new Info(Opcodes.REM_LONG_2ADDR, "rem-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MUL_LONG_2ADDR =
-        new Info(Opcodes.MUL_LONG_2ADDR, "mul-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info AND_LONG_2ADDR = new Info(Opcodes.AND_LONG_2ADDR, "and-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DIV_LONG_2ADDR =
-        new Info(Opcodes.DIV_LONG_2ADDR, "div-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info OR_LONG_2ADDR =
+      new Info(Opcodes.OR_LONG_2ADDR, "or-long/2addr", InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info REM_LONG_2ADDR =
-        new Info(Opcodes.REM_LONG_2ADDR, "rem-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info XOR_LONG_2ADDR = new Info(Opcodes.XOR_LONG_2ADDR, "xor-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info AND_LONG_2ADDR =
-        new Info(Opcodes.AND_LONG_2ADDR, "and-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SHL_LONG_2ADDR = new Info(Opcodes.SHL_LONG_2ADDR, "shl-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info OR_LONG_2ADDR =
-        new Info(Opcodes.OR_LONG_2ADDR, "or-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SHR_LONG_2ADDR = new Info(Opcodes.SHR_LONG_2ADDR, "shr-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info XOR_LONG_2ADDR =
-        new Info(Opcodes.XOR_LONG_2ADDR, "xor-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info USHR_LONG_2ADDR = new Info(Opcodes.USHR_LONG_2ADDR, "ushr-long/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SHL_LONG_2ADDR =
-        new Info(Opcodes.SHL_LONG_2ADDR, "shl-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info ADD_FLOAT_2ADDR = new Info(Opcodes.ADD_FLOAT_2ADDR, "add-float/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SHR_LONG_2ADDR =
-        new Info(Opcodes.SHR_LONG_2ADDR, "shr-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SUB_FLOAT_2ADDR = new Info(Opcodes.SUB_FLOAT_2ADDR, "sub-float/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info USHR_LONG_2ADDR =
-        new Info(Opcodes.USHR_LONG_2ADDR, "ushr-long/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MUL_FLOAT_2ADDR = new Info(Opcodes.MUL_FLOAT_2ADDR, "mul-float/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info ADD_FLOAT_2ADDR =
-        new Info(Opcodes.ADD_FLOAT_2ADDR, "add-float/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DIV_FLOAT_2ADDR = new Info(Opcodes.DIV_FLOAT_2ADDR, "div-float/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SUB_FLOAT_2ADDR =
-        new Info(Opcodes.SUB_FLOAT_2ADDR, "sub-float/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info REM_FLOAT_2ADDR = new Info(Opcodes.REM_FLOAT_2ADDR, "rem-float/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MUL_FLOAT_2ADDR =
-        new Info(Opcodes.MUL_FLOAT_2ADDR, "mul-float/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info ADD_DOUBLE_2ADDR = new Info(Opcodes.ADD_DOUBLE_2ADDR, "add-double/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info DIV_FLOAT_2ADDR =
-        new Info(Opcodes.DIV_FLOAT_2ADDR, "div-float/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info SUB_DOUBLE_2ADDR = new Info(Opcodes.SUB_DOUBLE_2ADDR, "sub-double/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info REM_FLOAT_2ADDR =
-        new Info(Opcodes.REM_FLOAT_2ADDR, "rem-float/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MUL_DOUBLE_2ADDR = new Info(Opcodes.MUL_DOUBLE_2ADDR, "mul-double/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info ADD_DOUBLE_2ADDR =
-        new Info(Opcodes.ADD_DOUBLE_2ADDR, "add-double/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info DIV_DOUBLE_2ADDR = new Info(Opcodes.DIV_DOUBLE_2ADDR, "div-double/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info SUB_DOUBLE_2ADDR =
-        new Info(Opcodes.SUB_DOUBLE_2ADDR, "sub-double/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info REM_DOUBLE_2ADDR = new Info(Opcodes.REM_DOUBLE_2ADDR, "rem-double/2addr",
+      InstructionCodec.FORMAT_12X, IndexType.NONE);
 
-    public static final Info MUL_DOUBLE_2ADDR =
-        new Info(Opcodes.MUL_DOUBLE_2ADDR, "mul-double/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info ADD_INT_LIT16 =
+      new Info(Opcodes.ADD_INT_LIT16, "add-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info DIV_DOUBLE_2ADDR =
-        new Info(Opcodes.DIV_DOUBLE_2ADDR, "div-double/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info RSUB_INT =
+      new Info(Opcodes.RSUB_INT, "rsub-int", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info REM_DOUBLE_2ADDR =
-        new Info(Opcodes.REM_DOUBLE_2ADDR, "rem-double/2addr",
-            InstructionCodec.FORMAT_12X, IndexType.NONE);
+  public static final Info MUL_INT_LIT16 =
+      new Info(Opcodes.MUL_INT_LIT16, "mul-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info ADD_INT_LIT16 =
-        new Info(Opcodes.ADD_INT_LIT16, "add-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info DIV_INT_LIT16 =
+      new Info(Opcodes.DIV_INT_LIT16, "div-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info RSUB_INT =
-        new Info(Opcodes.RSUB_INT, "rsub-int",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info REM_INT_LIT16 =
+      new Info(Opcodes.REM_INT_LIT16, "rem-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info MUL_INT_LIT16 =
-        new Info(Opcodes.MUL_INT_LIT16, "mul-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info AND_INT_LIT16 =
+      new Info(Opcodes.AND_INT_LIT16, "and-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info DIV_INT_LIT16 =
-        new Info(Opcodes.DIV_INT_LIT16, "div-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info OR_INT_LIT16 =
+      new Info(Opcodes.OR_INT_LIT16, "or-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info REM_INT_LIT16 =
-        new Info(Opcodes.REM_INT_LIT16, "rem-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info XOR_INT_LIT16 =
+      new Info(Opcodes.XOR_INT_LIT16, "xor-int/lit16", InstructionCodec.FORMAT_22S, IndexType.NONE);
 
-    public static final Info AND_INT_LIT16 =
-        new Info(Opcodes.AND_INT_LIT16, "and-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info ADD_INT_LIT8 =
+      new Info(Opcodes.ADD_INT_LIT8, "add-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info OR_INT_LIT16 =
-        new Info(Opcodes.OR_INT_LIT16, "or-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info RSUB_INT_LIT8 =
+      new Info(Opcodes.RSUB_INT_LIT8, "rsub-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info XOR_INT_LIT16 =
-        new Info(Opcodes.XOR_INT_LIT16, "xor-int/lit16",
-            InstructionCodec.FORMAT_22S, IndexType.NONE);
+  public static final Info MUL_INT_LIT8 =
+      new Info(Opcodes.MUL_INT_LIT8, "mul-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info ADD_INT_LIT8 =
-        new Info(Opcodes.ADD_INT_LIT8, "add-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info DIV_INT_LIT8 =
+      new Info(Opcodes.DIV_INT_LIT8, "div-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info RSUB_INT_LIT8 =
-        new Info(Opcodes.RSUB_INT_LIT8, "rsub-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info REM_INT_LIT8 =
+      new Info(Opcodes.REM_INT_LIT8, "rem-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info MUL_INT_LIT8 =
-        new Info(Opcodes.MUL_INT_LIT8, "mul-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info AND_INT_LIT8 =
+      new Info(Opcodes.AND_INT_LIT8, "and-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info DIV_INT_LIT8 =
-        new Info(Opcodes.DIV_INT_LIT8, "div-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info OR_INT_LIT8 =
+      new Info(Opcodes.OR_INT_LIT8, "or-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info REM_INT_LIT8 =
-        new Info(Opcodes.REM_INT_LIT8, "rem-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info XOR_INT_LIT8 =
+      new Info(Opcodes.XOR_INT_LIT8, "xor-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info AND_INT_LIT8 =
-        new Info(Opcodes.AND_INT_LIT8, "and-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info SHL_INT_LIT8 =
+      new Info(Opcodes.SHL_INT_LIT8, "shl-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info OR_INT_LIT8 =
-        new Info(Opcodes.OR_INT_LIT8, "or-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info SHR_INT_LIT8 =
+      new Info(Opcodes.SHR_INT_LIT8, "shr-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info XOR_INT_LIT8 =
-        new Info(Opcodes.XOR_INT_LIT8, "xor-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  public static final Info USHR_INT_LIT8 =
+      new Info(Opcodes.USHR_INT_LIT8, "ushr-int/lit8", InstructionCodec.FORMAT_22B, IndexType.NONE);
 
-    public static final Info SHL_INT_LIT8 =
-        new Info(Opcodes.SHL_INT_LIT8, "shl-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  // END(opcode-info-defs)
 
-    public static final Info SHR_INT_LIT8 =
-        new Info(Opcodes.SHR_INT_LIT8, "shr-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+  // Static initialization.
+  static {
+    INFO = new Info[Opcodes.MAX_VALUE - Opcodes.MIN_VALUE + 1];
 
-    public static final Info USHR_INT_LIT8 =
-        new Info(Opcodes.USHR_INT_LIT8, "ushr-int/lit8",
-            InstructionCodec.FORMAT_22B, IndexType.NONE);
+    // TODO(dx team): Stop using this constant.
+    set(SPECIAL_FORMAT);
 
-    // END(opcode-info-defs)
+    // TODO(dx team): These payload opcodes should be generated by opcode-gen.
+    set(PACKED_SWITCH_PAYLOAD);
+    set(SPARSE_SWITCH_PAYLOAD);
+    set(FILL_ARRAY_DATA_PAYLOAD);
 
-    // Static initialization.
-    static {
-        INFO = new Info[Opcodes.MAX_VALUE - Opcodes.MIN_VALUE + 1];
+    // BEGIN(opcode-info-init); GENERATED AUTOMATICALLY BY opcode-gen
+    set(NOP);
+    set(MOVE);
+    set(MOVE_FROM16);
+    set(MOVE_16);
+    set(MOVE_WIDE);
+    set(MOVE_WIDE_FROM16);
+    set(MOVE_WIDE_16);
+    set(MOVE_OBJECT);
+    set(MOVE_OBJECT_FROM16);
+    set(MOVE_OBJECT_16);
+    set(MOVE_RESULT);
+    set(MOVE_RESULT_WIDE);
+    set(MOVE_RESULT_OBJECT);
+    set(MOVE_EXCEPTION);
+    set(RETURN_VOID);
+    set(RETURN);
+    set(RETURN_WIDE);
+    set(RETURN_OBJECT);
+    set(CONST_4);
+    set(CONST_16);
+    set(CONST);
+    set(CONST_HIGH16);
+    set(CONST_WIDE_16);
+    set(CONST_WIDE_32);
+    set(CONST_WIDE);
+    set(CONST_WIDE_HIGH16);
+    set(CONST_STRING);
+    set(CONST_STRING_JUMBO);
+    set(CONST_CLASS);
+    set(MONITOR_ENTER);
+    set(MONITOR_EXIT);
+    set(CHECK_CAST);
+    set(INSTANCE_OF);
+    set(ARRAY_LENGTH);
+    set(NEW_INSTANCE);
+    set(NEW_ARRAY);
+    set(FILLED_NEW_ARRAY);
+    set(FILLED_NEW_ARRAY_RANGE);
+    set(FILL_ARRAY_DATA);
+    set(THROW);
+    set(GOTO);
+    set(GOTO_16);
+    set(GOTO_32);
+    set(PACKED_SWITCH);
+    set(SPARSE_SWITCH);
+    set(CMPL_FLOAT);
+    set(CMPG_FLOAT);
+    set(CMPL_DOUBLE);
+    set(CMPG_DOUBLE);
+    set(CMP_LONG);
+    set(IF_EQ);
+    set(IF_NE);
+    set(IF_LT);
+    set(IF_GE);
+    set(IF_GT);
+    set(IF_LE);
+    set(IF_EQZ);
+    set(IF_NEZ);
+    set(IF_LTZ);
+    set(IF_GEZ);
+    set(IF_GTZ);
+    set(IF_LEZ);
+    set(AGET);
+    set(AGET_WIDE);
+    set(AGET_OBJECT);
+    set(AGET_BOOLEAN);
+    set(AGET_BYTE);
+    set(AGET_CHAR);
+    set(AGET_SHORT);
+    set(APUT);
+    set(APUT_WIDE);
+    set(APUT_OBJECT);
+    set(APUT_BOOLEAN);
+    set(APUT_BYTE);
+    set(APUT_CHAR);
+    set(APUT_SHORT);
+    set(IGET);
+    set(IGET_WIDE);
+    set(IGET_OBJECT);
+    set(IGET_BOOLEAN);
+    set(IGET_BYTE);
+    set(IGET_CHAR);
+    set(IGET_SHORT);
+    set(IPUT);
+    set(IPUT_WIDE);
+    set(IPUT_OBJECT);
+    set(IPUT_BOOLEAN);
+    set(IPUT_BYTE);
+    set(IPUT_CHAR);
+    set(IPUT_SHORT);
+    set(SGET);
+    set(SGET_WIDE);
+    set(SGET_OBJECT);
+    set(SGET_BOOLEAN);
+    set(SGET_BYTE);
+    set(SGET_CHAR);
+    set(SGET_SHORT);
+    set(SPUT);
+    set(SPUT_WIDE);
+    set(SPUT_OBJECT);
+    set(SPUT_BOOLEAN);
+    set(SPUT_BYTE);
+    set(SPUT_CHAR);
+    set(SPUT_SHORT);
+    set(INVOKE_VIRTUAL);
+    set(INVOKE_SUPER);
+    set(INVOKE_DIRECT);
+    set(INVOKE_STATIC);
+    set(INVOKE_INTERFACE);
+    set(INVOKE_VIRTUAL_RANGE);
+    set(INVOKE_SUPER_RANGE);
+    set(INVOKE_DIRECT_RANGE);
+    set(INVOKE_STATIC_RANGE);
+    set(INVOKE_INTERFACE_RANGE);
+    set(NEG_INT);
+    set(NOT_INT);
+    set(NEG_LONG);
+    set(NOT_LONG);
+    set(NEG_FLOAT);
+    set(NEG_DOUBLE);
+    set(INT_TO_LONG);
+    set(INT_TO_FLOAT);
+    set(INT_TO_DOUBLE);
+    set(LONG_TO_INT);
+    set(LONG_TO_FLOAT);
+    set(LONG_TO_DOUBLE);
+    set(FLOAT_TO_INT);
+    set(FLOAT_TO_LONG);
+    set(FLOAT_TO_DOUBLE);
+    set(DOUBLE_TO_INT);
+    set(DOUBLE_TO_LONG);
+    set(DOUBLE_TO_FLOAT);
+    set(INT_TO_BYTE);
+    set(INT_TO_CHAR);
+    set(INT_TO_SHORT);
+    set(ADD_INT);
+    set(SUB_INT);
+    set(MUL_INT);
+    set(DIV_INT);
+    set(REM_INT);
+    set(AND_INT);
+    set(OR_INT);
+    set(XOR_INT);
+    set(SHL_INT);
+    set(SHR_INT);
+    set(USHR_INT);
+    set(ADD_LONG);
+    set(SUB_LONG);
+    set(MUL_LONG);
+    set(DIV_LONG);
+    set(REM_LONG);
+    set(AND_LONG);
+    set(OR_LONG);
+    set(XOR_LONG);
+    set(SHL_LONG);
+    set(SHR_LONG);
+    set(USHR_LONG);
+    set(ADD_FLOAT);
+    set(SUB_FLOAT);
+    set(MUL_FLOAT);
+    set(DIV_FLOAT);
+    set(REM_FLOAT);
+    set(ADD_DOUBLE);
+    set(SUB_DOUBLE);
+    set(MUL_DOUBLE);
+    set(DIV_DOUBLE);
+    set(REM_DOUBLE);
+    set(ADD_INT_2ADDR);
+    set(SUB_INT_2ADDR);
+    set(MUL_INT_2ADDR);
+    set(DIV_INT_2ADDR);
+    set(REM_INT_2ADDR);
+    set(AND_INT_2ADDR);
+    set(OR_INT_2ADDR);
+    set(XOR_INT_2ADDR);
+    set(SHL_INT_2ADDR);
+    set(SHR_INT_2ADDR);
+    set(USHR_INT_2ADDR);
+    set(ADD_LONG_2ADDR);
+    set(SUB_LONG_2ADDR);
+    set(MUL_LONG_2ADDR);
+    set(DIV_LONG_2ADDR);
+    set(REM_LONG_2ADDR);
+    set(AND_LONG_2ADDR);
+    set(OR_LONG_2ADDR);
+    set(XOR_LONG_2ADDR);
+    set(SHL_LONG_2ADDR);
+    set(SHR_LONG_2ADDR);
+    set(USHR_LONG_2ADDR);
+    set(ADD_FLOAT_2ADDR);
+    set(SUB_FLOAT_2ADDR);
+    set(MUL_FLOAT_2ADDR);
+    set(DIV_FLOAT_2ADDR);
+    set(REM_FLOAT_2ADDR);
+    set(ADD_DOUBLE_2ADDR);
+    set(SUB_DOUBLE_2ADDR);
+    set(MUL_DOUBLE_2ADDR);
+    set(DIV_DOUBLE_2ADDR);
+    set(REM_DOUBLE_2ADDR);
+    set(ADD_INT_LIT16);
+    set(RSUB_INT);
+    set(MUL_INT_LIT16);
+    set(DIV_INT_LIT16);
+    set(REM_INT_LIT16);
+    set(AND_INT_LIT16);
+    set(OR_INT_LIT16);
+    set(XOR_INT_LIT16);
+    set(ADD_INT_LIT8);
+    set(RSUB_INT_LIT8);
+    set(MUL_INT_LIT8);
+    set(DIV_INT_LIT8);
+    set(REM_INT_LIT8);
+    set(AND_INT_LIT8);
+    set(OR_INT_LIT8);
+    set(XOR_INT_LIT8);
+    set(SHL_INT_LIT8);
+    set(SHR_INT_LIT8);
+    set(USHR_INT_LIT8);
+    // END(opcode-info-init)
+  }
 
-        // TODO: Stop using this constant.
-        set(SPECIAL_FORMAT);
+  /**
+   * This class is uninstantiable.
+   */
+  private OpcodeInfo() {
+    // This space intentionally left blank.
+  }
 
-        // TODO: These payload opcodes should be generated by opcode-gen.
-        set(PACKED_SWITCH_PAYLOAD);
-        set(SPARSE_SWITCH_PAYLOAD);
-        set(FILL_ARRAY_DATA_PAYLOAD);
+  /**
+   * Gets the {@link @Info} for the given opcode value.
+   *
+   * @param opcode {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the
+   * opcode value
+   * @return non-null; the associated opcode information instance
+   */
+  public static Info get(int opcode) {
+    int idx = opcode - Opcodes.MIN_VALUE;
 
-        // BEGIN(opcode-info-init); GENERATED AUTOMATICALLY BY opcode-gen
-        set(NOP);
-        set(MOVE);
-        set(MOVE_FROM16);
-        set(MOVE_16);
-        set(MOVE_WIDE);
-        set(MOVE_WIDE_FROM16);
-        set(MOVE_WIDE_16);
-        set(MOVE_OBJECT);
-        set(MOVE_OBJECT_FROM16);
-        set(MOVE_OBJECT_16);
-        set(MOVE_RESULT);
-        set(MOVE_RESULT_WIDE);
-        set(MOVE_RESULT_OBJECT);
-        set(MOVE_EXCEPTION);
-        set(RETURN_VOID);
-        set(RETURN);
-        set(RETURN_WIDE);
-        set(RETURN_OBJECT);
-        set(CONST_4);
-        set(CONST_16);
-        set(CONST);
-        set(CONST_HIGH16);
-        set(CONST_WIDE_16);
-        set(CONST_WIDE_32);
-        set(CONST_WIDE);
-        set(CONST_WIDE_HIGH16);
-        set(CONST_STRING);
-        set(CONST_STRING_JUMBO);
-        set(CONST_CLASS);
-        set(MONITOR_ENTER);
-        set(MONITOR_EXIT);
-        set(CHECK_CAST);
-        set(INSTANCE_OF);
-        set(ARRAY_LENGTH);
-        set(NEW_INSTANCE);
-        set(NEW_ARRAY);
-        set(FILLED_NEW_ARRAY);
-        set(FILLED_NEW_ARRAY_RANGE);
-        set(FILL_ARRAY_DATA);
-        set(THROW);
-        set(GOTO);
-        set(GOTO_16);
-        set(GOTO_32);
-        set(PACKED_SWITCH);
-        set(SPARSE_SWITCH);
-        set(CMPL_FLOAT);
-        set(CMPG_FLOAT);
-        set(CMPL_DOUBLE);
-        set(CMPG_DOUBLE);
-        set(CMP_LONG);
-        set(IF_EQ);
-        set(IF_NE);
-        set(IF_LT);
-        set(IF_GE);
-        set(IF_GT);
-        set(IF_LE);
-        set(IF_EQZ);
-        set(IF_NEZ);
-        set(IF_LTZ);
-        set(IF_GEZ);
-        set(IF_GTZ);
-        set(IF_LEZ);
-        set(AGET);
-        set(AGET_WIDE);
-        set(AGET_OBJECT);
-        set(AGET_BOOLEAN);
-        set(AGET_BYTE);
-        set(AGET_CHAR);
-        set(AGET_SHORT);
-        set(APUT);
-        set(APUT_WIDE);
-        set(APUT_OBJECT);
-        set(APUT_BOOLEAN);
-        set(APUT_BYTE);
-        set(APUT_CHAR);
-        set(APUT_SHORT);
-        set(IGET);
-        set(IGET_WIDE);
-        set(IGET_OBJECT);
-        set(IGET_BOOLEAN);
-        set(IGET_BYTE);
-        set(IGET_CHAR);
-        set(IGET_SHORT);
-        set(IPUT);
-        set(IPUT_WIDE);
-        set(IPUT_OBJECT);
-        set(IPUT_BOOLEAN);
-        set(IPUT_BYTE);
-        set(IPUT_CHAR);
-        set(IPUT_SHORT);
-        set(SGET);
-        set(SGET_WIDE);
-        set(SGET_OBJECT);
-        set(SGET_BOOLEAN);
-        set(SGET_BYTE);
-        set(SGET_CHAR);
-        set(SGET_SHORT);
-        set(SPUT);
-        set(SPUT_WIDE);
-        set(SPUT_OBJECT);
-        set(SPUT_BOOLEAN);
-        set(SPUT_BYTE);
-        set(SPUT_CHAR);
-        set(SPUT_SHORT);
-        set(INVOKE_VIRTUAL);
-        set(INVOKE_SUPER);
-        set(INVOKE_DIRECT);
-        set(INVOKE_STATIC);
-        set(INVOKE_INTERFACE);
-        set(INVOKE_VIRTUAL_RANGE);
-        set(INVOKE_SUPER_RANGE);
-        set(INVOKE_DIRECT_RANGE);
-        set(INVOKE_STATIC_RANGE);
-        set(INVOKE_INTERFACE_RANGE);
-        set(NEG_INT);
-        set(NOT_INT);
-        set(NEG_LONG);
-        set(NOT_LONG);
-        set(NEG_FLOAT);
-        set(NEG_DOUBLE);
-        set(INT_TO_LONG);
-        set(INT_TO_FLOAT);
-        set(INT_TO_DOUBLE);
-        set(LONG_TO_INT);
-        set(LONG_TO_FLOAT);
-        set(LONG_TO_DOUBLE);
-        set(FLOAT_TO_INT);
-        set(FLOAT_TO_LONG);
-        set(FLOAT_TO_DOUBLE);
-        set(DOUBLE_TO_INT);
-        set(DOUBLE_TO_LONG);
-        set(DOUBLE_TO_FLOAT);
-        set(INT_TO_BYTE);
-        set(INT_TO_CHAR);
-        set(INT_TO_SHORT);
-        set(ADD_INT);
-        set(SUB_INT);
-        set(MUL_INT);
-        set(DIV_INT);
-        set(REM_INT);
-        set(AND_INT);
-        set(OR_INT);
-        set(XOR_INT);
-        set(SHL_INT);
-        set(SHR_INT);
-        set(USHR_INT);
-        set(ADD_LONG);
-        set(SUB_LONG);
-        set(MUL_LONG);
-        set(DIV_LONG);
-        set(REM_LONG);
-        set(AND_LONG);
-        set(OR_LONG);
-        set(XOR_LONG);
-        set(SHL_LONG);
-        set(SHR_LONG);
-        set(USHR_LONG);
-        set(ADD_FLOAT);
-        set(SUB_FLOAT);
-        set(MUL_FLOAT);
-        set(DIV_FLOAT);
-        set(REM_FLOAT);
-        set(ADD_DOUBLE);
-        set(SUB_DOUBLE);
-        set(MUL_DOUBLE);
-        set(DIV_DOUBLE);
-        set(REM_DOUBLE);
-        set(ADD_INT_2ADDR);
-        set(SUB_INT_2ADDR);
-        set(MUL_INT_2ADDR);
-        set(DIV_INT_2ADDR);
-        set(REM_INT_2ADDR);
-        set(AND_INT_2ADDR);
-        set(OR_INT_2ADDR);
-        set(XOR_INT_2ADDR);
-        set(SHL_INT_2ADDR);
-        set(SHR_INT_2ADDR);
-        set(USHR_INT_2ADDR);
-        set(ADD_LONG_2ADDR);
-        set(SUB_LONG_2ADDR);
-        set(MUL_LONG_2ADDR);
-        set(DIV_LONG_2ADDR);
-        set(REM_LONG_2ADDR);
-        set(AND_LONG_2ADDR);
-        set(OR_LONG_2ADDR);
-        set(XOR_LONG_2ADDR);
-        set(SHL_LONG_2ADDR);
-        set(SHR_LONG_2ADDR);
-        set(USHR_LONG_2ADDR);
-        set(ADD_FLOAT_2ADDR);
-        set(SUB_FLOAT_2ADDR);
-        set(MUL_FLOAT_2ADDR);
-        set(DIV_FLOAT_2ADDR);
-        set(REM_FLOAT_2ADDR);
-        set(ADD_DOUBLE_2ADDR);
-        set(SUB_DOUBLE_2ADDR);
-        set(MUL_DOUBLE_2ADDR);
-        set(DIV_DOUBLE_2ADDR);
-        set(REM_DOUBLE_2ADDR);
-        set(ADD_INT_LIT16);
-        set(RSUB_INT);
-        set(MUL_INT_LIT16);
-        set(DIV_INT_LIT16);
-        set(REM_INT_LIT16);
-        set(AND_INT_LIT16);
-        set(OR_INT_LIT16);
-        set(XOR_INT_LIT16);
-        set(ADD_INT_LIT8);
-        set(RSUB_INT_LIT8);
-        set(MUL_INT_LIT8);
-        set(DIV_INT_LIT8);
-        set(REM_INT_LIT8);
-        set(AND_INT_LIT8);
-        set(OR_INT_LIT8);
-        set(XOR_INT_LIT8);
-        set(SHL_INT_LIT8);
-        set(SHR_INT_LIT8);
-        set(USHR_INT_LIT8);
-        // END(opcode-info-init)
+    try {
+      Info result = INFO[idx];
+      if (result != null) {
+        return result;
+      }
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Fall through.
     }
 
-    /**
-     * This class is uninstantiable.
-     */
-    private OpcodeInfo() {
-        // This space intentionally left blank.
+    throw new IllegalArgumentException("bogus opcode: " + Hex.u2or4(opcode));
+  }
+
+  /**
+   * Gets the name of the given opcode.
+   */
+  public static String getName(int opcode) {
+    return get(opcode).getName();
+  }
+
+  /**
+   * Gets the format (an {@link InstructionCodec}) for the given opcode
+   * value.
+   */
+  public static InstructionCodec getFormat(int opcode) {
+    return get(opcode).getFormat();
+  }
+
+  /**
+   * Gets the {@link IndexType} for the given opcode value.
+   */
+  public static IndexType getIndexType(int opcode) {
+    return get(opcode).getIndexType();
+  }
+
+  /**
+   * Puts the given opcode into the table of all ops.
+   *
+   * @param opcode non-null; the opcode
+   */
+  private static void set(Info opcode) {
+    int idx = opcode.getOpcode() - Opcodes.MIN_VALUE;
+    INFO[idx] = opcode;
+  }
+
+  /**
+   * Information about an opcode.
+   */
+  public static class Info {
+    private final int opcode;
+    private final String name;
+    private final InstructionCodec format;
+    private final IndexType indexType;
+
+    public Info(int opcode, String name, InstructionCodec format, IndexType indexType) {
+      this.opcode = opcode;
+      this.name = name;
+      this.format = format;
+      this.indexType = indexType;
     }
 
-    /**
-     * Gets the {@link @Info} for the given opcode value.
-     *
-     * @param opcode {@code Opcodes.MIN_VALUE..Opcodes.MAX_VALUE;} the
-     * opcode value
-     * @return non-null; the associated opcode information instance
-     */
-    public static Info get(int opcode) {
-        int idx = opcode - Opcodes.MIN_VALUE;
-
-        try {
-            Info result = INFO[idx];
-            if (result != null) {
-                return result;
-            }
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Fall through.
-        }
-
-        throw new IllegalArgumentException("bogus opcode: "
-                + Hex.u2or4(opcode));
+    public int getOpcode() {
+      return opcode;
     }
 
-    /**
-     * Gets the name of the given opcode.
-     */
-    public static String getName(int opcode) {
-        return get(opcode).getName();
+    public String getName() {
+      return name;
     }
 
-    /**
-     * Gets the format (an {@link InstructionCodec}) for the given opcode
-     * value.
-     */
-    public static InstructionCodec getFormat(int opcode) {
-        return get(opcode).getFormat();
+    public InstructionCodec getFormat() {
+      return format;
     }
 
-    /**
-     * Gets the {@link IndexType} for the given opcode value.
-     */
-    public static IndexType getIndexType(int opcode) {
-        return get(opcode).getIndexType();
+    public IndexType getIndexType() {
+      return indexType;
     }
-
-    /**
-     * Puts the given opcode into the table of all ops.
-     *
-     * @param opcode non-null; the opcode
-     */
-    private static void set(Info opcode) {
-        int idx = opcode.getOpcode() - Opcodes.MIN_VALUE;
-        INFO[idx] = opcode;
-    }
-
-    /**
-     * Information about an opcode.
-     */
-    public static class Info {
-        private final int opcode;
-        private final String name;
-        private final InstructionCodec format;
-        private final IndexType indexType;
-
-        public Info(int opcode, String name, InstructionCodec format,
-                IndexType indexType) {
-            this.opcode = opcode;
-            this.name = name;
-            this.format = format;
-            this.indexType = indexType;
-        }
-
-        public int getOpcode() {
-            return opcode;
-        }
-
-        public String getName() {
-            return name;
-        }
-
-        public InstructionCodec getFormat() {
-            return format;
-        }
-
-        public IndexType getIndexType() {
-            return indexType;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/Opcodes.java b/dx/src/com/android/jack/dx/io/Opcodes.java
index 77b5d8e..4f79a31 100644
--- a/dx/src/com/android/jack/dx/io/Opcodes.java
+++ b/dx/src/com/android/jack/dx/io/Opcodes.java
@@ -21,326 +21,326 @@
  * document for the meaning and instruction format of each opcode.
  */
 public final class Opcodes {
-    /**
-     * pseudo-opcode used for nonstandard format payload "instructions". TODO:
-     * Retire this concept, and start treating the payload instructions
-     * more like the rest.
-     */
-    public static final int SPECIAL_FORMAT = -1;
+  /**
+   * pseudo-opcode used for nonstandard format payload "instructions". TODO(dx team):
+   * Retire this concept, and start treating the payload instructions
+   * more like the rest.
+   */
+  public static final int SPECIAL_FORMAT = -1;
 
-    /**
-     * pseudo-opcode used to indicate there is no next opcode; used
-     * in opcode chaining lists
-     */
-    public static final int NO_NEXT = -1;
+  /**
+   * pseudo-opcode used to indicate there is no next opcode; used
+   * in opcode chaining lists
+   */
+  public static final int NO_NEXT = -1;
 
-    /** minimum valid opcode value */
-    public static final int MIN_VALUE = -1;
+  /** minimum valid opcode value */
+  public static final int MIN_VALUE = -1;
 
-    /** maximum valid opcode value */
-    public static final int MAX_VALUE = 0xffff;
+  /** maximum valid opcode value */
+  public static final int MAX_VALUE = 0xffff;
 
-    // BEGIN(opcodes); GENERATED AUTOMATICALLY BY opcode-gen
-    public static final int NOP = 0x00;
-    public static final int MOVE = 0x01;
-    public static final int MOVE_FROM16 = 0x02;
-    public static final int MOVE_16 = 0x03;
-    public static final int MOVE_WIDE = 0x04;
-    public static final int MOVE_WIDE_FROM16 = 0x05;
-    public static final int MOVE_WIDE_16 = 0x06;
-    public static final int MOVE_OBJECT = 0x07;
-    public static final int MOVE_OBJECT_FROM16 = 0x08;
-    public static final int MOVE_OBJECT_16 = 0x09;
-    public static final int MOVE_RESULT = 0x0a;
-    public static final int MOVE_RESULT_WIDE = 0x0b;
-    public static final int MOVE_RESULT_OBJECT = 0x0c;
-    public static final int MOVE_EXCEPTION = 0x0d;
-    public static final int RETURN_VOID = 0x0e;
-    public static final int RETURN = 0x0f;
-    public static final int RETURN_WIDE = 0x10;
-    public static final int RETURN_OBJECT = 0x11;
-    public static final int CONST_4 = 0x12;
-    public static final int CONST_16 = 0x13;
-    public static final int CONST = 0x14;
-    public static final int CONST_HIGH16 = 0x15;
-    public static final int CONST_WIDE_16 = 0x16;
-    public static final int CONST_WIDE_32 = 0x17;
-    public static final int CONST_WIDE = 0x18;
-    public static final int CONST_WIDE_HIGH16 = 0x19;
-    public static final int CONST_STRING = 0x1a;
-    public static final int CONST_STRING_JUMBO = 0x1b;
-    public static final int CONST_CLASS = 0x1c;
-    public static final int MONITOR_ENTER = 0x1d;
-    public static final int MONITOR_EXIT = 0x1e;
-    public static final int CHECK_CAST = 0x1f;
-    public static final int INSTANCE_OF = 0x20;
-    public static final int ARRAY_LENGTH = 0x21;
-    public static final int NEW_INSTANCE = 0x22;
-    public static final int NEW_ARRAY = 0x23;
-    public static final int FILLED_NEW_ARRAY = 0x24;
-    public static final int FILLED_NEW_ARRAY_RANGE = 0x25;
-    public static final int FILL_ARRAY_DATA = 0x26;
-    public static final int THROW = 0x27;
-    public static final int GOTO = 0x28;
-    public static final int GOTO_16 = 0x29;
-    public static final int GOTO_32 = 0x2a;
-    public static final int PACKED_SWITCH = 0x2b;
-    public static final int SPARSE_SWITCH = 0x2c;
-    public static final int CMPL_FLOAT = 0x2d;
-    public static final int CMPG_FLOAT = 0x2e;
-    public static final int CMPL_DOUBLE = 0x2f;
-    public static final int CMPG_DOUBLE = 0x30;
-    public static final int CMP_LONG = 0x31;
-    public static final int IF_EQ = 0x32;
-    public static final int IF_NE = 0x33;
-    public static final int IF_LT = 0x34;
-    public static final int IF_GE = 0x35;
-    public static final int IF_GT = 0x36;
-    public static final int IF_LE = 0x37;
-    public static final int IF_EQZ = 0x38;
-    public static final int IF_NEZ = 0x39;
-    public static final int IF_LTZ = 0x3a;
-    public static final int IF_GEZ = 0x3b;
-    public static final int IF_GTZ = 0x3c;
-    public static final int IF_LEZ = 0x3d;
-    public static final int AGET = 0x44;
-    public static final int AGET_WIDE = 0x45;
-    public static final int AGET_OBJECT = 0x46;
-    public static final int AGET_BOOLEAN = 0x47;
-    public static final int AGET_BYTE = 0x48;
-    public static final int AGET_CHAR = 0x49;
-    public static final int AGET_SHORT = 0x4a;
-    public static final int APUT = 0x4b;
-    public static final int APUT_WIDE = 0x4c;
-    public static final int APUT_OBJECT = 0x4d;
-    public static final int APUT_BOOLEAN = 0x4e;
-    public static final int APUT_BYTE = 0x4f;
-    public static final int APUT_CHAR = 0x50;
-    public static final int APUT_SHORT = 0x51;
-    public static final int IGET = 0x52;
-    public static final int IGET_WIDE = 0x53;
-    public static final int IGET_OBJECT = 0x54;
-    public static final int IGET_BOOLEAN = 0x55;
-    public static final int IGET_BYTE = 0x56;
-    public static final int IGET_CHAR = 0x57;
-    public static final int IGET_SHORT = 0x58;
-    public static final int IPUT = 0x59;
-    public static final int IPUT_WIDE = 0x5a;
-    public static final int IPUT_OBJECT = 0x5b;
-    public static final int IPUT_BOOLEAN = 0x5c;
-    public static final int IPUT_BYTE = 0x5d;
-    public static final int IPUT_CHAR = 0x5e;
-    public static final int IPUT_SHORT = 0x5f;
-    public static final int SGET = 0x60;
-    public static final int SGET_WIDE = 0x61;
-    public static final int SGET_OBJECT = 0x62;
-    public static final int SGET_BOOLEAN = 0x63;
-    public static final int SGET_BYTE = 0x64;
-    public static final int SGET_CHAR = 0x65;
-    public static final int SGET_SHORT = 0x66;
-    public static final int SPUT = 0x67;
-    public static final int SPUT_WIDE = 0x68;
-    public static final int SPUT_OBJECT = 0x69;
-    public static final int SPUT_BOOLEAN = 0x6a;
-    public static final int SPUT_BYTE = 0x6b;
-    public static final int SPUT_CHAR = 0x6c;
-    public static final int SPUT_SHORT = 0x6d;
-    public static final int INVOKE_VIRTUAL = 0x6e;
-    public static final int INVOKE_SUPER = 0x6f;
-    public static final int INVOKE_DIRECT = 0x70;
-    public static final int INVOKE_STATIC = 0x71;
-    public static final int INVOKE_INTERFACE = 0x72;
-    public static final int INVOKE_VIRTUAL_RANGE = 0x74;
-    public static final int INVOKE_SUPER_RANGE = 0x75;
-    public static final int INVOKE_DIRECT_RANGE = 0x76;
-    public static final int INVOKE_STATIC_RANGE = 0x77;
-    public static final int INVOKE_INTERFACE_RANGE = 0x78;
-    public static final int NEG_INT = 0x7b;
-    public static final int NOT_INT = 0x7c;
-    public static final int NEG_LONG = 0x7d;
-    public static final int NOT_LONG = 0x7e;
-    public static final int NEG_FLOAT = 0x7f;
-    public static final int NEG_DOUBLE = 0x80;
-    public static final int INT_TO_LONG = 0x81;
-    public static final int INT_TO_FLOAT = 0x82;
-    public static final int INT_TO_DOUBLE = 0x83;
-    public static final int LONG_TO_INT = 0x84;
-    public static final int LONG_TO_FLOAT = 0x85;
-    public static final int LONG_TO_DOUBLE = 0x86;
-    public static final int FLOAT_TO_INT = 0x87;
-    public static final int FLOAT_TO_LONG = 0x88;
-    public static final int FLOAT_TO_DOUBLE = 0x89;
-    public static final int DOUBLE_TO_INT = 0x8a;
-    public static final int DOUBLE_TO_LONG = 0x8b;
-    public static final int DOUBLE_TO_FLOAT = 0x8c;
-    public static final int INT_TO_BYTE = 0x8d;
-    public static final int INT_TO_CHAR = 0x8e;
-    public static final int INT_TO_SHORT = 0x8f;
-    public static final int ADD_INT = 0x90;
-    public static final int SUB_INT = 0x91;
-    public static final int MUL_INT = 0x92;
-    public static final int DIV_INT = 0x93;
-    public static final int REM_INT = 0x94;
-    public static final int AND_INT = 0x95;
-    public static final int OR_INT = 0x96;
-    public static final int XOR_INT = 0x97;
-    public static final int SHL_INT = 0x98;
-    public static final int SHR_INT = 0x99;
-    public static final int USHR_INT = 0x9a;
-    public static final int ADD_LONG = 0x9b;
-    public static final int SUB_LONG = 0x9c;
-    public static final int MUL_LONG = 0x9d;
-    public static final int DIV_LONG = 0x9e;
-    public static final int REM_LONG = 0x9f;
-    public static final int AND_LONG = 0xa0;
-    public static final int OR_LONG = 0xa1;
-    public static final int XOR_LONG = 0xa2;
-    public static final int SHL_LONG = 0xa3;
-    public static final int SHR_LONG = 0xa4;
-    public static final int USHR_LONG = 0xa5;
-    public static final int ADD_FLOAT = 0xa6;
-    public static final int SUB_FLOAT = 0xa7;
-    public static final int MUL_FLOAT = 0xa8;
-    public static final int DIV_FLOAT = 0xa9;
-    public static final int REM_FLOAT = 0xaa;
-    public static final int ADD_DOUBLE = 0xab;
-    public static final int SUB_DOUBLE = 0xac;
-    public static final int MUL_DOUBLE = 0xad;
-    public static final int DIV_DOUBLE = 0xae;
-    public static final int REM_DOUBLE = 0xaf;
-    public static final int ADD_INT_2ADDR = 0xb0;
-    public static final int SUB_INT_2ADDR = 0xb1;
-    public static final int MUL_INT_2ADDR = 0xb2;
-    public static final int DIV_INT_2ADDR = 0xb3;
-    public static final int REM_INT_2ADDR = 0xb4;
-    public static final int AND_INT_2ADDR = 0xb5;
-    public static final int OR_INT_2ADDR = 0xb6;
-    public static final int XOR_INT_2ADDR = 0xb7;
-    public static final int SHL_INT_2ADDR = 0xb8;
-    public static final int SHR_INT_2ADDR = 0xb9;
-    public static final int USHR_INT_2ADDR = 0xba;
-    public static final int ADD_LONG_2ADDR = 0xbb;
-    public static final int SUB_LONG_2ADDR = 0xbc;
-    public static final int MUL_LONG_2ADDR = 0xbd;
-    public static final int DIV_LONG_2ADDR = 0xbe;
-    public static final int REM_LONG_2ADDR = 0xbf;
-    public static final int AND_LONG_2ADDR = 0xc0;
-    public static final int OR_LONG_2ADDR = 0xc1;
-    public static final int XOR_LONG_2ADDR = 0xc2;
-    public static final int SHL_LONG_2ADDR = 0xc3;
-    public static final int SHR_LONG_2ADDR = 0xc4;
-    public static final int USHR_LONG_2ADDR = 0xc5;
-    public static final int ADD_FLOAT_2ADDR = 0xc6;
-    public static final int SUB_FLOAT_2ADDR = 0xc7;
-    public static final int MUL_FLOAT_2ADDR = 0xc8;
-    public static final int DIV_FLOAT_2ADDR = 0xc9;
-    public static final int REM_FLOAT_2ADDR = 0xca;
-    public static final int ADD_DOUBLE_2ADDR = 0xcb;
-    public static final int SUB_DOUBLE_2ADDR = 0xcc;
-    public static final int MUL_DOUBLE_2ADDR = 0xcd;
-    public static final int DIV_DOUBLE_2ADDR = 0xce;
-    public static final int REM_DOUBLE_2ADDR = 0xcf;
-    public static final int ADD_INT_LIT16 = 0xd0;
-    public static final int RSUB_INT = 0xd1;
-    public static final int MUL_INT_LIT16 = 0xd2;
-    public static final int DIV_INT_LIT16 = 0xd3;
-    public static final int REM_INT_LIT16 = 0xd4;
-    public static final int AND_INT_LIT16 = 0xd5;
-    public static final int OR_INT_LIT16 = 0xd6;
-    public static final int XOR_INT_LIT16 = 0xd7;
-    public static final int ADD_INT_LIT8 = 0xd8;
-    public static final int RSUB_INT_LIT8 = 0xd9;
-    public static final int MUL_INT_LIT8 = 0xda;
-    public static final int DIV_INT_LIT8 = 0xdb;
-    public static final int REM_INT_LIT8 = 0xdc;
-    public static final int AND_INT_LIT8 = 0xdd;
-    public static final int OR_INT_LIT8 = 0xde;
-    public static final int XOR_INT_LIT8 = 0xdf;
-    public static final int SHL_INT_LIT8 = 0xe0;
-    public static final int SHR_INT_LIT8 = 0xe1;
-    public static final int USHR_INT_LIT8 = 0xe2;
-    // END(opcodes)
+  // BEGIN(opcodes); GENERATED AUTOMATICALLY BY opcode-gen
+  public static final int NOP = 0x00;
+  public static final int MOVE = 0x01;
+  public static final int MOVE_FROM16 = 0x02;
+  public static final int MOVE_16 = 0x03;
+  public static final int MOVE_WIDE = 0x04;
+  public static final int MOVE_WIDE_FROM16 = 0x05;
+  public static final int MOVE_WIDE_16 = 0x06;
+  public static final int MOVE_OBJECT = 0x07;
+  public static final int MOVE_OBJECT_FROM16 = 0x08;
+  public static final int MOVE_OBJECT_16 = 0x09;
+  public static final int MOVE_RESULT = 0x0a;
+  public static final int MOVE_RESULT_WIDE = 0x0b;
+  public static final int MOVE_RESULT_OBJECT = 0x0c;
+  public static final int MOVE_EXCEPTION = 0x0d;
+  public static final int RETURN_VOID = 0x0e;
+  public static final int RETURN = 0x0f;
+  public static final int RETURN_WIDE = 0x10;
+  public static final int RETURN_OBJECT = 0x11;
+  public static final int CONST_4 = 0x12;
+  public static final int CONST_16 = 0x13;
+  public static final int CONST = 0x14;
+  public static final int CONST_HIGH16 = 0x15;
+  public static final int CONST_WIDE_16 = 0x16;
+  public static final int CONST_WIDE_32 = 0x17;
+  public static final int CONST_WIDE = 0x18;
+  public static final int CONST_WIDE_HIGH16 = 0x19;
+  public static final int CONST_STRING = 0x1a;
+  public static final int CONST_STRING_JUMBO = 0x1b;
+  public static final int CONST_CLASS = 0x1c;
+  public static final int MONITOR_ENTER = 0x1d;
+  public static final int MONITOR_EXIT = 0x1e;
+  public static final int CHECK_CAST = 0x1f;
+  public static final int INSTANCE_OF = 0x20;
+  public static final int ARRAY_LENGTH = 0x21;
+  public static final int NEW_INSTANCE = 0x22;
+  public static final int NEW_ARRAY = 0x23;
+  public static final int FILLED_NEW_ARRAY = 0x24;
+  public static final int FILLED_NEW_ARRAY_RANGE = 0x25;
+  public static final int FILL_ARRAY_DATA = 0x26;
+  public static final int THROW = 0x27;
+  public static final int GOTO = 0x28;
+  public static final int GOTO_16 = 0x29;
+  public static final int GOTO_32 = 0x2a;
+  public static final int PACKED_SWITCH = 0x2b;
+  public static final int SPARSE_SWITCH = 0x2c;
+  public static final int CMPL_FLOAT = 0x2d;
+  public static final int CMPG_FLOAT = 0x2e;
+  public static final int CMPL_DOUBLE = 0x2f;
+  public static final int CMPG_DOUBLE = 0x30;
+  public static final int CMP_LONG = 0x31;
+  public static final int IF_EQ = 0x32;
+  public static final int IF_NE = 0x33;
+  public static final int IF_LT = 0x34;
+  public static final int IF_GE = 0x35;
+  public static final int IF_GT = 0x36;
+  public static final int IF_LE = 0x37;
+  public static final int IF_EQZ = 0x38;
+  public static final int IF_NEZ = 0x39;
+  public static final int IF_LTZ = 0x3a;
+  public static final int IF_GEZ = 0x3b;
+  public static final int IF_GTZ = 0x3c;
+  public static final int IF_LEZ = 0x3d;
+  public static final int AGET = 0x44;
+  public static final int AGET_WIDE = 0x45;
+  public static final int AGET_OBJECT = 0x46;
+  public static final int AGET_BOOLEAN = 0x47;
+  public static final int AGET_BYTE = 0x48;
+  public static final int AGET_CHAR = 0x49;
+  public static final int AGET_SHORT = 0x4a;
+  public static final int APUT = 0x4b;
+  public static final int APUT_WIDE = 0x4c;
+  public static final int APUT_OBJECT = 0x4d;
+  public static final int APUT_BOOLEAN = 0x4e;
+  public static final int APUT_BYTE = 0x4f;
+  public static final int APUT_CHAR = 0x50;
+  public static final int APUT_SHORT = 0x51;
+  public static final int IGET = 0x52;
+  public static final int IGET_WIDE = 0x53;
+  public static final int IGET_OBJECT = 0x54;
+  public static final int IGET_BOOLEAN = 0x55;
+  public static final int IGET_BYTE = 0x56;
+  public static final int IGET_CHAR = 0x57;
+  public static final int IGET_SHORT = 0x58;
+  public static final int IPUT = 0x59;
+  public static final int IPUT_WIDE = 0x5a;
+  public static final int IPUT_OBJECT = 0x5b;
+  public static final int IPUT_BOOLEAN = 0x5c;
+  public static final int IPUT_BYTE = 0x5d;
+  public static final int IPUT_CHAR = 0x5e;
+  public static final int IPUT_SHORT = 0x5f;
+  public static final int SGET = 0x60;
+  public static final int SGET_WIDE = 0x61;
+  public static final int SGET_OBJECT = 0x62;
+  public static final int SGET_BOOLEAN = 0x63;
+  public static final int SGET_BYTE = 0x64;
+  public static final int SGET_CHAR = 0x65;
+  public static final int SGET_SHORT = 0x66;
+  public static final int SPUT = 0x67;
+  public static final int SPUT_WIDE = 0x68;
+  public static final int SPUT_OBJECT = 0x69;
+  public static final int SPUT_BOOLEAN = 0x6a;
+  public static final int SPUT_BYTE = 0x6b;
+  public static final int SPUT_CHAR = 0x6c;
+  public static final int SPUT_SHORT = 0x6d;
+  public static final int INVOKE_VIRTUAL = 0x6e;
+  public static final int INVOKE_SUPER = 0x6f;
+  public static final int INVOKE_DIRECT = 0x70;
+  public static final int INVOKE_STATIC = 0x71;
+  public static final int INVOKE_INTERFACE = 0x72;
+  public static final int INVOKE_VIRTUAL_RANGE = 0x74;
+  public static final int INVOKE_SUPER_RANGE = 0x75;
+  public static final int INVOKE_DIRECT_RANGE = 0x76;
+  public static final int INVOKE_STATIC_RANGE = 0x77;
+  public static final int INVOKE_INTERFACE_RANGE = 0x78;
+  public static final int NEG_INT = 0x7b;
+  public static final int NOT_INT = 0x7c;
+  public static final int NEG_LONG = 0x7d;
+  public static final int NOT_LONG = 0x7e;
+  public static final int NEG_FLOAT = 0x7f;
+  public static final int NEG_DOUBLE = 0x80;
+  public static final int INT_TO_LONG = 0x81;
+  public static final int INT_TO_FLOAT = 0x82;
+  public static final int INT_TO_DOUBLE = 0x83;
+  public static final int LONG_TO_INT = 0x84;
+  public static final int LONG_TO_FLOAT = 0x85;
+  public static final int LONG_TO_DOUBLE = 0x86;
+  public static final int FLOAT_TO_INT = 0x87;
+  public static final int FLOAT_TO_LONG = 0x88;
+  public static final int FLOAT_TO_DOUBLE = 0x89;
+  public static final int DOUBLE_TO_INT = 0x8a;
+  public static final int DOUBLE_TO_LONG = 0x8b;
+  public static final int DOUBLE_TO_FLOAT = 0x8c;
+  public static final int INT_TO_BYTE = 0x8d;
+  public static final int INT_TO_CHAR = 0x8e;
+  public static final int INT_TO_SHORT = 0x8f;
+  public static final int ADD_INT = 0x90;
+  public static final int SUB_INT = 0x91;
+  public static final int MUL_INT = 0x92;
+  public static final int DIV_INT = 0x93;
+  public static final int REM_INT = 0x94;
+  public static final int AND_INT = 0x95;
+  public static final int OR_INT = 0x96;
+  public static final int XOR_INT = 0x97;
+  public static final int SHL_INT = 0x98;
+  public static final int SHR_INT = 0x99;
+  public static final int USHR_INT = 0x9a;
+  public static final int ADD_LONG = 0x9b;
+  public static final int SUB_LONG = 0x9c;
+  public static final int MUL_LONG = 0x9d;
+  public static final int DIV_LONG = 0x9e;
+  public static final int REM_LONG = 0x9f;
+  public static final int AND_LONG = 0xa0;
+  public static final int OR_LONG = 0xa1;
+  public static final int XOR_LONG = 0xa2;
+  public static final int SHL_LONG = 0xa3;
+  public static final int SHR_LONG = 0xa4;
+  public static final int USHR_LONG = 0xa5;
+  public static final int ADD_FLOAT = 0xa6;
+  public static final int SUB_FLOAT = 0xa7;
+  public static final int MUL_FLOAT = 0xa8;
+  public static final int DIV_FLOAT = 0xa9;
+  public static final int REM_FLOAT = 0xaa;
+  public static final int ADD_DOUBLE = 0xab;
+  public static final int SUB_DOUBLE = 0xac;
+  public static final int MUL_DOUBLE = 0xad;
+  public static final int DIV_DOUBLE = 0xae;
+  public static final int REM_DOUBLE = 0xaf;
+  public static final int ADD_INT_2ADDR = 0xb0;
+  public static final int SUB_INT_2ADDR = 0xb1;
+  public static final int MUL_INT_2ADDR = 0xb2;
+  public static final int DIV_INT_2ADDR = 0xb3;
+  public static final int REM_INT_2ADDR = 0xb4;
+  public static final int AND_INT_2ADDR = 0xb5;
+  public static final int OR_INT_2ADDR = 0xb6;
+  public static final int XOR_INT_2ADDR = 0xb7;
+  public static final int SHL_INT_2ADDR = 0xb8;
+  public static final int SHR_INT_2ADDR = 0xb9;
+  public static final int USHR_INT_2ADDR = 0xba;
+  public static final int ADD_LONG_2ADDR = 0xbb;
+  public static final int SUB_LONG_2ADDR = 0xbc;
+  public static final int MUL_LONG_2ADDR = 0xbd;
+  public static final int DIV_LONG_2ADDR = 0xbe;
+  public static final int REM_LONG_2ADDR = 0xbf;
+  public static final int AND_LONG_2ADDR = 0xc0;
+  public static final int OR_LONG_2ADDR = 0xc1;
+  public static final int XOR_LONG_2ADDR = 0xc2;
+  public static final int SHL_LONG_2ADDR = 0xc3;
+  public static final int SHR_LONG_2ADDR = 0xc4;
+  public static final int USHR_LONG_2ADDR = 0xc5;
+  public static final int ADD_FLOAT_2ADDR = 0xc6;
+  public static final int SUB_FLOAT_2ADDR = 0xc7;
+  public static final int MUL_FLOAT_2ADDR = 0xc8;
+  public static final int DIV_FLOAT_2ADDR = 0xc9;
+  public static final int REM_FLOAT_2ADDR = 0xca;
+  public static final int ADD_DOUBLE_2ADDR = 0xcb;
+  public static final int SUB_DOUBLE_2ADDR = 0xcc;
+  public static final int MUL_DOUBLE_2ADDR = 0xcd;
+  public static final int DIV_DOUBLE_2ADDR = 0xce;
+  public static final int REM_DOUBLE_2ADDR = 0xcf;
+  public static final int ADD_INT_LIT16 = 0xd0;
+  public static final int RSUB_INT = 0xd1;
+  public static final int MUL_INT_LIT16 = 0xd2;
+  public static final int DIV_INT_LIT16 = 0xd3;
+  public static final int REM_INT_LIT16 = 0xd4;
+  public static final int AND_INT_LIT16 = 0xd5;
+  public static final int OR_INT_LIT16 = 0xd6;
+  public static final int XOR_INT_LIT16 = 0xd7;
+  public static final int ADD_INT_LIT8 = 0xd8;
+  public static final int RSUB_INT_LIT8 = 0xd9;
+  public static final int MUL_INT_LIT8 = 0xda;
+  public static final int DIV_INT_LIT8 = 0xdb;
+  public static final int REM_INT_LIT8 = 0xdc;
+  public static final int AND_INT_LIT8 = 0xdd;
+  public static final int OR_INT_LIT8 = 0xde;
+  public static final int XOR_INT_LIT8 = 0xdf;
+  public static final int SHL_INT_LIT8 = 0xe0;
+  public static final int SHR_INT_LIT8 = 0xe1;
+  public static final int USHR_INT_LIT8 = 0xe2;
+  // END(opcodes)
 
-    // TODO: Generate these payload opcodes with opcode-gen.
+  // TODO(dx team): Generate these payload opcodes with opcode-gen.
 
-    /**
-     * special pseudo-opcode value for packed-switch data payload
-     * instructions
-     */
-    public static final int PACKED_SWITCH_PAYLOAD = 0x100;
+  /**
+   * special pseudo-opcode value for packed-switch data payload
+   * instructions
+   */
+  public static final int PACKED_SWITCH_PAYLOAD = 0x100;
 
-    /** special pseudo-opcode value for packed-switch data payload
-     * instructions
-     */
-    public static final int SPARSE_SWITCH_PAYLOAD = 0x200;
+  /** special pseudo-opcode value for packed-switch data payload
+   * instructions
+   */
+  public static final int SPARSE_SWITCH_PAYLOAD = 0x200;
 
-    /** special pseudo-opcode value for fill-array-data data payload
-     * instructions
-     */
-    public static final int FILL_ARRAY_DATA_PAYLOAD = 0x300;
+  /** special pseudo-opcode value for fill-array-data data payload
+   * instructions
+   */
+  public static final int FILL_ARRAY_DATA_PAYLOAD = 0x300;
 
-    /**
-     * This class is uninstantiable.
-     */
-    private Opcodes() {
-        // This space intentionally left blank.
-    }
+  /**
+   * This class is uninstantiable.
+   */
+  private Opcodes() {
+    // This space intentionally left blank.
+  }
 
-    /**
-     * Determines if the given opcode has the right "shape" to be
-     * valid. This includes the range {@code 0x01..0xfe}, the range
-     * {@code 0x00ff..0xffff} where the low-order byte is either
-     * {@code 0} or {@code 0xff}, and the special opcode values {@code
-     * SPECIAL_FORMAT} and {@code NO_NEXT}. Note that not all of the
-     * opcode values that pass this test are in fact used. This method
-     * is meant to perform a quick check to reject blatantly wrong
-     * values (e.g. when validating arguments).
+  /**
+   * Determines if the given opcode has the right "shape" to be
+   * valid. This includes the range {@code 0x01..0xfe}, the range
+   * {@code 0x00ff..0xffff} where the low-order byte is either
+   * {@code 0} or {@code 0xff}, and the special opcode values {@code
+   * SPECIAL_FORMAT} and {@code NO_NEXT}. Note that not all of the
+   * opcode values that pass this test are in fact used. This method
+   * is meant to perform a quick check to reject blatantly wrong
+   * values (e.g. when validating arguments).
+   *
+   * @param opcode the opcode value
+   * @return {@code true} iff the value has the right "shape" to be
+   * possibly valid
+   */
+  public static boolean isValidShape(int opcode) {
+    /*
+     * Note: This method bakes in knowledge that all opcodes are
+     * one of the forms:
      *
-     * @param opcode the opcode value
-     * @return {@code true} iff the value has the right "shape" to be
-     * possibly valid
+     *   * single byte in range 0x01..0xfe -- normal opcodes
+     *   * (byteValue << 8) -- nop and data payload opcodes
+     *   * ((byteValue << 8) | 0xff) -- 16-bit extended opcodes
+     *   * SPECIAL_FORMAT or NO_NEXT -- pseudo-opcodes
      */
-    public static boolean isValidShape(int opcode) {
-        /*
-         * Note: This method bakes in knowledge that all opcodes are
-         * one of the forms:
-         *
-         *   * single byte in range 0x01..0xfe -- normal opcodes
-         *   * (byteValue << 8) -- nop and data payload opcodes
-         *   * ((byteValue << 8) | 0xff) -- 16-bit extended opcodes
-         *   * SPECIAL_FORMAT or NO_NEXT -- pseudo-opcodes
-         */
 
-        // Note: SPECIAL_FORMAT == NO_NEXT.
-        if (opcode < SPECIAL_FORMAT) {
-            return false;
-        } else if (opcode == SPECIAL_FORMAT) {
-            return true;
-        }
-
-        int lowByte = opcode & 0xff;
-        if ((lowByte == 0) || (lowByte == 0xff)) {
-            return true;
-        }
-
-        return (opcode & 0xff00) == 0;
+// Note: SPECIAL_FORMAT == NO_NEXT.
+    if (opcode < SPECIAL_FORMAT) {
+      return false;
+    } else if (opcode == SPECIAL_FORMAT) {
+      return true;
     }
 
-    /**
-     * Gets the opcode out of an opcode unit, the latter of which may also
-     * include one or more argument values.
-     *
-     * @param opcodeUnit the opcode-containing code unit
-     * @return the extracted opcode
-     */
-    public static int extractOpcodeFromUnit(int opcodeUnit) {
-        /*
-         * Note: This method bakes in knowledge that all opcodes are
-         * either single-byte or of the forms (byteValue << 8) or
-         * ((byteValue << 8) | 0xff).
-         */
-
-        int lowByte = opcodeUnit & 0xff;
-        return ((lowByte == 0) || (lowByte == 0xff)) ? opcodeUnit : lowByte;
+    int lowByte = opcode & 0xff;
+    if ((lowByte == 0) || (lowByte == 0xff)) {
+      return true;
     }
+
+    return (opcode & 0xff00) == 0;
+  }
+
+  /**
+   * Gets the opcode out of an opcode unit, the latter of which may also
+   * include one or more argument values.
+   *
+   * @param opcodeUnit the opcode-containing code unit
+   * @return the extracted opcode
+   */
+  public static int extractOpcodeFromUnit(int opcodeUnit) {
+    /*
+     * Note: This method bakes in knowledge that all opcodes are
+     * either single-byte or of the forms (byteValue << 8) or
+     * ((byteValue << 8) | 0xff).
+     */
+
+int lowByte = opcodeUnit & 0xff;
+    return ((lowByte == 0) || (lowByte == 0xff)) ? opcodeUnit : lowByte;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/ProtoId.java b/dx/src/com/android/jack/dx/io/ProtoId.java
index c1bb61a..d715720 100644
--- a/dx/src/com/android/jack/dx/io/ProtoId.java
+++ b/dx/src/com/android/jack/dx/io/ProtoId.java
@@ -18,51 +18,55 @@
 
 import com.android.jack.dx.util.Unsigned;
 
+/**
+ * TODO(jack team)
+ */
 public final class ProtoId implements Comparable<ProtoId> {
-    private final DexBuffer buffer;
-    private final int shortyIndex;
-    private final int returnTypeIndex;
-    private final int parametersOffset;
+  private final DexBuffer buffer;
+  private final int shortyIndex;
+  private final int returnTypeIndex;
+  private final int parametersOffset;
 
-    public ProtoId(DexBuffer buffer, int shortyIndex, int returnTypeIndex, int parametersOffset) {
-        this.buffer = buffer;
-        this.shortyIndex = shortyIndex;
-        this.returnTypeIndex = returnTypeIndex;
-        this.parametersOffset = parametersOffset;
+  public ProtoId(DexBuffer buffer, int shortyIndex, int returnTypeIndex, int parametersOffset) {
+    this.buffer = buffer;
+    this.shortyIndex = shortyIndex;
+    this.returnTypeIndex = returnTypeIndex;
+    this.parametersOffset = parametersOffset;
+  }
+
+  @Override
+  public int compareTo(ProtoId other) {
+    if (returnTypeIndex != other.returnTypeIndex) {
+      return Unsigned.compare(returnTypeIndex, other.returnTypeIndex);
+    }
+    return Unsigned.compare(parametersOffset, other.parametersOffset);
+  }
+
+  public int getShortyIndex() {
+    return shortyIndex;
+  }
+
+  public int getReturnTypeIndex() {
+    return returnTypeIndex;
+  }
+
+  public int getParametersOffset() {
+    return parametersOffset;
+  }
+
+  public void writeTo(DexBuffer.Section out) {
+    out.writeInt(shortyIndex);
+    out.writeInt(returnTypeIndex);
+    out.writeInt(parametersOffset);
+  }
+
+  @Override
+  public String toString() {
+    if (buffer == null) {
+      return shortyIndex + " " + returnTypeIndex + " " + parametersOffset;
     }
 
-    public int compareTo(ProtoId other) {
-        if (returnTypeIndex != other.returnTypeIndex) {
-            return Unsigned.compare(returnTypeIndex, other.returnTypeIndex);
-        }
-        return Unsigned.compare(parametersOffset, other.parametersOffset);
-    }
-
-    public int getShortyIndex() {
-        return shortyIndex;
-    }
-
-    public int getReturnTypeIndex() {
-        return returnTypeIndex;
-    }
-
-    public int getParametersOffset() {
-        return parametersOffset;
-    }
-
-    public void writeTo(DexBuffer.Section out) {
-        out.writeInt(shortyIndex);
-        out.writeInt(returnTypeIndex);
-        out.writeInt(parametersOffset);
-    }
-
-    @Override public String toString() {
-        if (buffer == null) {
-            return shortyIndex + " " + returnTypeIndex + " " + parametersOffset;
-        }
-
-        return buffer.strings().get(shortyIndex)
-                + ": " + buffer.typeNames().get(returnTypeIndex)
-                + " " + buffer.readTypeList(parametersOffset);
-    }
+    return buffer.strings().get(shortyIndex) + ": " + buffer.typeNames().get(returnTypeIndex) + " "
+        + buffer.readTypeList(parametersOffset);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/AddressMap.java b/dx/src/com/android/jack/dx/io/instructions/AddressMap.java
index 624870b..f546add 100644
--- a/dx/src/com/android/jack/dx/io/instructions/AddressMap.java
+++ b/dx/src/com/android/jack/dx/io/instructions/AddressMap.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.dx.io.instructions;
 
-import java.io.EOFException;
 import java.util.HashMap;
 
 /**
@@ -24,29 +23,29 @@
  * {@code int}s.
  */
 public final class AddressMap {
-    /** underlying map. TODO: This might be too inefficient. */
-    private final HashMap<Integer,Integer> map;
+  /** underlying map. TODO(dx team): This might be too inefficient. */
+  private final HashMap<Integer, Integer> map;
 
-    /**
-     * Constructs an instance.
-     */
-    public AddressMap() {
-        map = new HashMap<Integer,Integer>();
-    }
+  /**
+   * Constructs an instance.
+   */
+  public AddressMap() {
+    map = new HashMap<Integer, Integer>();
+  }
 
-    /**
-     * Gets the value address corresponding to the given key address. Returns
-     * {@code -1} if there is no mapping.
-     */
-    public int get(int keyAddress) {
-        Integer value = map.get(keyAddress);
-        return (value == null) ? -1 : value;
-    }
+  /**
+   * Gets the value address corresponding to the given key address. Returns
+   * {@code -1} if there is no mapping.
+   */
+  public int get(int keyAddress) {
+    Integer value = map.get(keyAddress);
+    return (value == null) ? -1 : value;
+  }
 
-    /**
-     * Sets the value address associated with the given key address.
-     */
-    public void put(int keyAddress, int valueAddress) {
-        map.put(keyAddress, valueAddress);
-    }
+  /**
+   * Sets the value address associated with the given key address.
+   */
+  public void put(int keyAddress, int valueAddress) {
+    map.put(keyAddress, valueAddress);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/BaseCodeCursor.java b/dx/src/com/android/jack/dx/io/instructions/BaseCodeCursor.java
index 8d82cae..f62c9aa 100644
--- a/dx/src/com/android/jack/dx/io/instructions/BaseCodeCursor.java
+++ b/dx/src/com/android/jack/dx/io/instructions/BaseCodeCursor.java
@@ -16,46 +16,48 @@
 
 package com.android.jack.dx.io.instructions;
 
-import java.io.EOFException;
 
 /**
  * Base implementation of {@link CodeCursor}.
  */
 public abstract class BaseCodeCursor implements CodeCursor {
-    /** base address map */
-    private final AddressMap baseAddressMap;
+  /** base address map */
+  private final AddressMap baseAddressMap;
 
-    /** next index within {@link #array} to read from or write to */
-    private int cursor;
+  /** next index within {@link #array} to read from or write to */
+  private int cursor;
 
-    /**
-     * Constructs an instance.
-     */
-    public BaseCodeCursor() {
-        this.baseAddressMap = new AddressMap();
-        this.cursor = 0;
-    }
+  /**
+   * Constructs an instance.
+   */
+  public BaseCodeCursor() {
+    this.baseAddressMap = new AddressMap();
+    this.cursor = 0;
+  }
 
-    /** @inheritDoc */
-    public final int cursor() {
-        return cursor;
-    }
+  /** @inheritDoc */
+  @Override
+  public final int cursor() {
+    return cursor;
+  }
 
-    /** @inheritDoc */
-    public final int baseAddressForCursor() {
-        int mapped = baseAddressMap.get(cursor);
-        return (mapped >= 0) ? mapped : cursor;
-    }
+  /** @inheritDoc */
+  @Override
+  public final int baseAddressForCursor() {
+    int mapped = baseAddressMap.get(cursor);
+    return (mapped >= 0) ? mapped : cursor;
+  }
 
-    /** @inheritDoc */
-    public final void setBaseAddress(int targetAddress, int baseAddress) {
-        baseAddressMap.put(targetAddress, baseAddress);
-    }
+  /** @inheritDoc */
+  @Override
+  public final void setBaseAddress(int targetAddress, int baseAddress) {
+    baseAddressMap.put(targetAddress, baseAddress);
+  }
 
-    /**
-     * Advance the cursor by the indicated amount.
-     */
-    protected final void advance(int amount) {
-        cursor += amount;
-    }
+  /**
+   * Advance the cursor by the indicated amount.
+   */
+  protected final void advance(int amount) {
+    cursor += amount;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/CodeCursor.java b/dx/src/com/android/jack/dx/io/instructions/CodeCursor.java
index b9dbbbe..98e8eae 100644
--- a/dx/src/com/android/jack/dx/io/instructions/CodeCursor.java
+++ b/dx/src/com/android/jack/dx/io/instructions/CodeCursor.java
@@ -20,28 +20,28 @@
  * Cursor over code units, for reading or writing out Dalvik bytecode.
  */
 public interface CodeCursor {
-    /**
-     * Gets the cursor. The cursor is the offset in code units from
-     * the start of the input of the next code unit to be read or
-     * written, where the input generally consists of the code for a
-     * single method.
-     */
-    public int cursor();
+  /**
+   * Gets the cursor. The cursor is the offset in code units from
+   * the start of the input of the next code unit to be read or
+   * written, where the input generally consists of the code for a
+   * single method.
+   */
+  public int cursor();
 
-    /**
-     * Gets the base address associated with the current cursor. This
-     * differs from the cursor value when explicitly set (by {@link
-     * #setBaseAddress). This is used, in particular, to convey base
-     * addresses to switch data payload instructions, whose relative
-     * addresses are relative to the address of a dependant switch
-     * instruction.
-     */
-    public int baseAddressForCursor();
+  /**
+   * Gets the base address associated with the current cursor. This
+   * differs from the cursor value when explicitly set (by {@link
+   * #setBaseAddress). This is used, in particular, to convey base
+   * addresses to switch data payload instructions, whose relative
+   * addresses are relative to the address of a dependant switch
+   * instruction.
+   */
+  public int baseAddressForCursor();
 
-    /**
-     * Sets the base address for the given target address to be as indicated.
-     *
-     * @see #baseAddressForCursor
-     */
-    public void setBaseAddress(int targetAddress, int baseAddress);
+  /**
+   * Sets the base address for the given target address to be as indicated.
+   *
+   * @see #baseAddressForCursor
+   */
+  public void setBaseAddress(int targetAddress, int baseAddress);
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/CodeInput.java b/dx/src/com/android/jack/dx/io/instructions/CodeInput.java
index 9327dc4..cec6a48 100644
--- a/dx/src/com/android/jack/dx/io/instructions/CodeInput.java
+++ b/dx/src/com/android/jack/dx/io/instructions/CodeInput.java
@@ -22,24 +22,24 @@
  * Input stream of code units, for reading in Dalvik bytecode.
  */
 public interface CodeInput extends CodeCursor {
-    /**
-     * Returns whether there are any more code units to read. This
-     * is analogous to {@code hasNext()} on an interator.
-     */
-    public boolean hasMore();
+  /**
+   * Returns whether there are any more code units to read. This
+   * is analogous to {@code hasNext()} on an interator.
+   */
+  public boolean hasMore();
 
-    /**
-     * Reads a code unit.
-     */
-    public int read() throws EOFException;
+  /**
+   * Reads a code unit.
+   */
+  public int read() throws EOFException;
 
-    /**
-     * Reads two code units, treating them as a little-endian {@code int}.
-     */
-    public int readInt() throws EOFException;
+  /**
+   * Reads two code units, treating them as a little-endian {@code int}.
+   */
+  public int readInt() throws EOFException;
 
-    /**
-     * Reads four code units, treating them as a little-endian {@code long}.
-     */
-    public long readLong() throws EOFException;
+  /**
+   * Reads four code units, treating them as a little-endian {@code long}.
+   */
+  public long readLong() throws EOFException;
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/CodeOutput.java b/dx/src/com/android/jack/dx/io/instructions/CodeOutput.java
index 76f4d14..3de07ac 100644
--- a/dx/src/com/android/jack/dx/io/instructions/CodeOutput.java
+++ b/dx/src/com/android/jack/dx/io/instructions/CodeOutput.java
@@ -20,58 +20,58 @@
  * Output stream of code units, for writing out Dalvik bytecode.
  */
 public interface CodeOutput extends CodeCursor {
-    /**
-     * Writes a code unit.
-     */
-    public void write(short codeUnit);
+  /**
+   * Writes a code unit.
+   */
+  public void write(short codeUnit);
 
-    /**
-     * Writes two code units.
-     */
-    public void write(short u0, short u1);
+  /**
+   * Writes two code units.
+   */
+  public void write(short u0, short u1);
 
-    /**
-     * Writes three code units.
-     */
-    public void write(short u0, short u1, short u2);
+  /**
+   * Writes three code units.
+   */
+  public void write(short u0, short u1, short u2);
 
-    /**
-     * Writes four code units.
-     */
-    public void write(short u0, short u1, short u2, short u3);
+  /**
+   * Writes four code units.
+   */
+  public void write(short u0, short u1, short u2, short u3);
 
-    /**
-     * Writes five code units.
-     */
-    public void write(short u0, short u1, short u2, short u3, short u4);
+  /**
+   * Writes five code units.
+   */
+  public void write(short u0, short u1, short u2, short u3, short u4);
 
-    /**
-     * Writes an {@code int}, little-endian.
-     */
-    public void writeInt(int value);
+  /**
+   * Writes an {@code int}, little-endian.
+   */
+  public void writeInt(int value);
 
-    /**
-     * Writes a {@code long}, little-endian.
-     */
-    public void writeLong(long value);
+  /**
+   * Writes a {@code long}, little-endian.
+   */
+  public void writeLong(long value);
 
-    /**
-     * Writes the contents of the given array.
-     */
-    public void write(byte[] data);
+  /**
+   * Writes the contents of the given array.
+   */
+  public void write(byte[] data);
 
-    /**
-     * Writes the contents of the given array.
-     */
-    public void write(short[] data);
+  /**
+   * Writes the contents of the given array.
+   */
+  public void write(short[] data);
 
-    /**
-     * Writes the contents of the given array.
-     */
-    public void write(int[] data);
+  /**
+   * Writes the contents of the given array.
+   */
+  public void write(int[] data);
 
-    /**
-     * Writes the contents of the given array.
-     */
-    public void write(long[] data);
+  /**
+   * Writes the contents of the given array.
+   */
+  public void write(long[] data);
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/DecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/DecodedInstruction.java
index efcdec6..0d71a91 100644
--- a/dx/src/com/android/jack/dx/io/instructions/DecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/DecodedInstruction.java
@@ -38,442 +38,443 @@
  * consistently named alphabetically.</p>
  */
 public abstract class DecodedInstruction {
-    /** non-null; instruction format / codec */
-    private final InstructionCodec format;
+  /** non-null; instruction format / codec */
+  private final InstructionCodec format;
 
-    /** opcode number */
-    private final int opcode;
+  /** opcode number */
+  private final int opcode;
 
-    /** constant index argument */
-    private final int index;
+  /** constant index argument */
+  private final int index;
 
-    /** null-ok; index type */
-    private final IndexType indexType;
+  /** null-ok; index type */
+  private final IndexType indexType;
 
-    /**
-     * target address argument. This is an absolute address, not just
-     * a signed offset. <b>Note:</b> The address is unsigned, even
-     * though it is stored in an {@code int}.
-     */
-    private final int target;
+  /**
+   * target address argument. This is an absolute address, not just
+   * a signed offset. <b>Note:</b> The address is unsigned, even
+   * though it is stored in an {@code int}.
+   */
+  private final int target;
 
-    /**
-     * literal value argument; also used for special verification error
-     * constants (format 20bc) as well as should-be-zero values
-     * (formats 10x, 20t, 30t, and 32x)
-     */
-    private final long literal;
+  /**
+   * literal value argument; also used for special verification error
+   * constants (format 20bc) as well as should-be-zero values
+   * (formats 10x, 20t, 30t, and 32x)
+   */
+  private final long literal;
 
-    /**
-     * Decodes an instruction from the given input source.
-     */
-    public static DecodedInstruction decode(CodeInput in) throws EOFException {
-        int opcodeUnit = in.read();
-        int opcode = Opcodes.extractOpcodeFromUnit(opcodeUnit);
-        InstructionCodec format = OpcodeInfo.getFormat(opcode);
+  /**
+   * Decodes an instruction from the given input source.
+   */
+  public static DecodedInstruction decode(CodeInput in) throws EOFException {
+    int opcodeUnit = in.read();
+    int opcode = Opcodes.extractOpcodeFromUnit(opcodeUnit);
+    InstructionCodec format = OpcodeInfo.getFormat(opcode);
 
-        return format.decode(opcodeUnit, in);
+    return format.decode(opcodeUnit, in);
+  }
+
+  /**
+   * Decodes an array of instructions. The result has non-null
+   * elements at each offset that represents the start of an
+   * instruction.
+   */
+  public static DecodedInstruction[] decodeAll(short[] encodedInstructions) {
+    int size = encodedInstructions.length;
+    DecodedInstruction[] decoded = new DecodedInstruction[size];
+    ShortArrayCodeInput in = new ShortArrayCodeInput(encodedInstructions);
+
+    try {
+      while (in.hasMore()) {
+        decoded[in.cursor()] = DecodedInstruction.decode(in);
+      }
+    } catch (EOFException ex) {
+      throw new DexException(ex);
     }
 
-    /**
-     * Decodes an array of instructions. The result has non-null
-     * elements at each offset that represents the start of an
-     * instruction.
-     */
-    public static DecodedInstruction[] decodeAll(short[] encodedInstructions) {
-        int size = encodedInstructions.length;
-        DecodedInstruction[] decoded = new DecodedInstruction[size];
-        ShortArrayCodeInput in = new ShortArrayCodeInput(encodedInstructions);
+    return decoded;
+  }
 
-        try {
-            while (in.hasMore()) {
-                decoded[in.cursor()] = DecodedInstruction.decode(in);
-            }
-        } catch (EOFException ex) {
-            throw new DexException(ex);
-        }
-
-        return decoded;
+  /**
+   * Constructs an instance.
+   */
+  public DecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal) {
+    if (format == null) {
+      throw new NullPointerException("format == null");
     }
 
-    /**
-     * Constructs an instance.
-     */
-    public DecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal) {
-        if (format == null) {
-            throw new NullPointerException("format == null");
-        }
-
-        if (!Opcodes.isValidShape(opcode)) {
-            throw new IllegalArgumentException("invalid opcode");
-        }
-
-        this.format = format;
-        this.opcode = opcode;
-        this.index = index;
-        this.indexType = indexType;
-        this.target = target;
-        this.literal = literal;
+    if (!Opcodes.isValidShape(opcode)) {
+      throw new IllegalArgumentException("invalid opcode");
     }
 
-    public final InstructionCodec getFormat() {
-        return format;
+    this.format = format;
+    this.opcode = opcode;
+    this.index = index;
+    this.indexType = indexType;
+    this.target = target;
+    this.literal = literal;
+  }
+
+  public final InstructionCodec getFormat() {
+    return format;
+  }
+
+  public final int getOpcode() {
+    return opcode;
+  }
+
+  /**
+   * Gets the opcode, as a code unit.
+   */
+  public final short getOpcodeUnit() {
+    return (short) opcode;
+  }
+
+  public final int getIndex() {
+    return index;
+  }
+
+  /**
+   * Gets the index, as a code unit.
+   */
+  public final short getIndexUnit() {
+    return (short) index;
+  }
+
+  public final IndexType getIndexType() {
+    return indexType;
+  }
+
+  /**
+   * Gets the raw target.
+   */
+  public final int getTarget() {
+    return target;
+  }
+
+  /**
+   * Gets the target as a relative offset from the given address.
+   */
+  public final int getTarget(int baseAddress) {
+    return target - baseAddress;
+  }
+
+  /**
+   * Gets the target as a relative offset from the given base
+   * address, as a code unit. This will throw if the value is out of
+   * the range of a signed code unit.
+   */
+  public final short getTargetUnit(int baseAddress) {
+    int relativeTarget = getTarget(baseAddress);
+
+    if (relativeTarget != (short) relativeTarget) {
+      throw new DexException("Target out of range: " + Hex.s4(relativeTarget));
     }
 
-    public final int getOpcode() {
-        return opcode;
+    return (short) relativeTarget;
+  }
+
+  /**
+   * Gets the target as a relative offset from the given base
+   * address, masked to be a byte in size. This will throw if the
+   * value is out of the range of a signed byte.
+   */
+  public final int getTargetByte(int baseAddress) {
+    int relativeTarget = getTarget(baseAddress);
+
+    if (relativeTarget != (byte) relativeTarget) {
+      throw new DexException("Target out of range: " + Hex.s4(relativeTarget));
     }
 
-    /**
-     * Gets the opcode, as a code unit.
-     */
-    public final short getOpcodeUnit() {
-        return (short) opcode;
+    return relativeTarget & 0xff;
+  }
+
+  public final long getLiteral() {
+    return literal;
+  }
+
+  /**
+   * Gets the literal value, masked to be an int in size. This will
+   * throw if the value is out of the range of a signed int.
+   */
+  public final int getLiteralInt() {
+    if (literal != (int) literal) {
+      throw new DexException("Literal out of range: " + Hex.u8(literal));
     }
 
-    public final int getIndex() {
-        return index;
+    return (int) literal;
+  }
+
+  /**
+   * Gets the literal value, as a code unit. This will throw if the
+   * value is out of the range of a signed code unit.
+   */
+  public final short getLiteralUnit() {
+    if (literal != (short) literal) {
+      throw new DexException("Literal out of range: " + Hex.u8(literal));
     }
 
-    /**
-     * Gets the index, as a code unit.
-     */
-    public final short getIndexUnit() {
-        return (short) index;
+    return (short) literal;
+  }
+
+  /**
+   * Gets the literal value, masked to be a byte in size. This will
+   * throw if the value is out of the range of a signed byte.
+   */
+  public final int getLiteralByte() {
+    if (literal != (byte) literal) {
+      throw new DexException("Literal out of range: " + Hex.u8(literal));
     }
 
-    public final IndexType getIndexType() {
-        return indexType;
+    return (int) literal & 0xff;
+  }
+
+  /**
+   * Gets the literal value, masked to be a nibble in size. This
+   * will throw if the value is out of the range of a signed nibble.
+   */
+  public final int getLiteralNibble() {
+    if ((literal < -8) || (literal > 7)) {
+      throw new DexException("Literal out of range: " + Hex.u8(literal));
     }
 
-    /**
-     * Gets the raw target.
-     */
-    public final int getTarget() {
-        return target;
+    return (int) literal & 0xf;
+  }
+
+  public abstract int getRegisterCount();
+
+  public int getA() {
+    return 0;
+  }
+
+  public int getB() {
+    return 0;
+  }
+
+  public int getC() {
+    return 0;
+  }
+
+  public int getD() {
+    return 0;
+  }
+
+  public int getE() {
+    return 0;
+  }
+
+  /**
+   * Gets the register count, as a code unit. This will throw if the
+   * value is out of the range of an unsigned code unit.
+   */
+  public final short getRegisterCountUnit() {
+    int registerCount = getRegisterCount();
+
+    if ((registerCount & ~0xffff) != 0) {
+      throw new DexException("Register count out of range: " + Hex.u8(registerCount));
     }
 
-    /**
-     * Gets the target as a relative offset from the given address.
-     */
-    public final int getTarget(int baseAddress) {
-        return target - baseAddress;
+    return (short) registerCount;
+  }
+
+  /**
+   * Gets the A register number, as a code unit. This will throw if the
+   * value is out of the range of an unsigned code unit.
+   */
+  public final short getAUnit() {
+    int a = getA();
+
+    if ((a & ~0xffff) != 0) {
+      throw new DexException("Register A out of range: " + Hex.u8(a));
     }
 
-    /**
-     * Gets the target as a relative offset from the given base
-     * address, as a code unit. This will throw if the value is out of
-     * the range of a signed code unit.
-     */
-    public final short getTargetUnit(int baseAddress) {
-        int relativeTarget = getTarget(baseAddress);
+    return (short) a;
+  }
 
-        if (relativeTarget != (short) relativeTarget) {
-            throw new DexException("Target out of range: "
-                    + Hex.s4(relativeTarget));
-        }
+  /**
+   * Gets the A register number, as a byte. This will throw if the
+   * value is out of the range of an unsigned byte.
+   */
+  public final short getAByte() {
+    int a = getA();
 
-        return (short) relativeTarget;
+    if ((a & ~0xff) != 0) {
+      throw new DexException("Register A out of range: " + Hex.u8(a));
     }
 
-    /**
-     * Gets the target as a relative offset from the given base
-     * address, masked to be a byte in size. This will throw if the
-     * value is out of the range of a signed byte.
-     */
-    public final int getTargetByte(int baseAddress) {
-        int relativeTarget = getTarget(baseAddress);
+    return (short) a;
+  }
 
-        if (relativeTarget != (byte) relativeTarget) {
-            throw new DexException("Target out of range: "
-                    + Hex.s4(relativeTarget));
-        }
+  /**
+   * Gets the A register number, as a nibble. This will throw if the
+   * value is out of the range of an unsigned nibble.
+   */
+  public final short getANibble() {
+    int a = getA();
 
-        return relativeTarget & 0xff;
+    if ((a & ~0xf) != 0) {
+      throw new DexException("Register A out of range: " + Hex.u8(a));
     }
 
-    public final long getLiteral() {
-        return literal;
+    return (short) a;
+  }
+
+  /**
+   * Gets the B register number, as a code unit. This will throw if the
+   * value is out of the range of an unsigned code unit.
+   */
+  public final short getBUnit() {
+    int b = getB();
+
+    if ((b & ~0xffff) != 0) {
+      throw new DexException("Register B out of range: " + Hex.u8(b));
     }
 
-    /**
-     * Gets the literal value, masked to be an int in size. This will
-     * throw if the value is out of the range of a signed int.
-     */
-    public final int getLiteralInt() {
-        if (literal != (int) literal) {
-            throw new DexException("Literal out of range: " + Hex.u8(literal));
-        }
+    return (short) b;
+  }
 
-        return (int) literal;
+  /**
+   * Gets the B register number, as a byte. This will throw if the
+   * value is out of the range of an unsigned byte.
+   */
+  public final short getBByte() {
+    int b = getB();
+
+    if ((b & ~0xff) != 0) {
+      throw new DexException("Register B out of range: " + Hex.u8(b));
     }
 
-    /**
-     * Gets the literal value, as a code unit. This will throw if the
-     * value is out of the range of a signed code unit.
-     */
-    public final short getLiteralUnit() {
-        if (literal != (short) literal) {
-            throw new DexException("Literal out of range: " + Hex.u8(literal));
-        }
+    return (short) b;
+  }
 
-        return (short) literal;
+  /**
+   * Gets the B register number, as a nibble. This will throw if the
+   * value is out of the range of an unsigned nibble.
+   */
+  public final short getBNibble() {
+    int b = getB();
+
+    if ((b & ~0xf) != 0) {
+      throw new DexException("Register B out of range: " + Hex.u8(b));
     }
 
-    /**
-     * Gets the literal value, masked to be a byte in size. This will
-     * throw if the value is out of the range of a signed byte.
-     */
-    public final int getLiteralByte() {
-        if (literal != (byte) literal) {
-            throw new DexException("Literal out of range: " + Hex.u8(literal));
-        }
+    return (short) b;
+  }
 
-        return (int) literal & 0xff;
+  /**
+   * Gets the C register number, as a code unit. This will throw if the
+   * value is out of the range of an unsigned code unit.
+   */
+  public final short getCUnit() {
+    int c = getC();
+
+    if ((c & ~0xffff) != 0) {
+      throw new DexException("Register C out of range: " + Hex.u8(c));
     }
 
-    /**
-     * Gets the literal value, masked to be a nibble in size. This
-     * will throw if the value is out of the range of a signed nibble.
-     */
-    public final int getLiteralNibble() {
-        if ((literal < -8) || (literal > 7)) {
-            throw new DexException("Literal out of range: " + Hex.u8(literal));
-        }
+    return (short) c;
+  }
 
-        return (int) literal & 0xf;
+  /**
+   * Gets the C register number, as a byte. This will throw if the
+   * value is out of the range of an unsigned byte.
+   */
+  public final short getCByte() {
+    int c = getC();
+
+    if ((c & ~0xff) != 0) {
+      throw new DexException("Register C out of range: " + Hex.u8(c));
     }
 
-    public abstract int getRegisterCount();
+    return (short) c;
+  }
 
-    public int getA() {
-        return 0;
+  /**
+   * Gets the C register number, as a nibble. This will throw if the
+   * value is out of the range of an unsigned nibble.
+   */
+  public final short getCNibble() {
+    int c = getC();
+
+    if ((c & ~0xf) != 0) {
+      throw new DexException("Register C out of range: " + Hex.u8(c));
     }
 
-    public int getB() {
-        return 0;
+    return (short) c;
+  }
+
+  /**
+   * Gets the D register number, as a code unit. This will throw if the
+   * value is out of the range of an unsigned code unit.
+   */
+  public final short getDUnit() {
+    int d = getD();
+
+    if ((d & ~0xffff) != 0) {
+      throw new DexException("Register D out of range: " + Hex.u8(d));
     }
 
-    public int getC() {
-        return 0;
+    return (short) d;
+  }
+
+  /**
+   * Gets the D register number, as a byte. This will throw if the
+   * value is out of the range of an unsigned byte.
+   */
+  public final short getDByte() {
+    int d = getD();
+
+    if ((d & ~0xff) != 0) {
+      throw new DexException("Register D out of range: " + Hex.u8(d));
     }
 
-    public int getD() {
-        return 0;
+    return (short) d;
+  }
+
+  /**
+   * Gets the D register number, as a nibble. This will throw if the
+   * value is out of the range of an unsigned nibble.
+   */
+  public final short getDNibble() {
+    int d = getD();
+
+    if ((d & ~0xf) != 0) {
+      throw new DexException("Register D out of range: " + Hex.u8(d));
     }
 
-    public int getE() {
-        return 0;
+    return (short) d;
+  }
+
+  /**
+   * Gets the E register number, as a nibble. This will throw if the
+   * value is out of the range of an unsigned nibble.
+   */
+  public final short getENibble() {
+    int e = getE();
+
+    if ((e & ~0xf) != 0) {
+      throw new DexException("Register E out of range: " + Hex.u8(e));
     }
 
-    /**
-     * Gets the register count, as a code unit. This will throw if the
-     * value is out of the range of an unsigned code unit.
-     */
-    public final short getRegisterCountUnit() {
-        int registerCount = getRegisterCount();
+    return (short) e;
+  }
 
-        if ((registerCount & ~0xffff) != 0) {
-            throw new DexException("Register count out of range: "
-                    + Hex.u8(registerCount));
-        }
+  /**
+   * Encodes this instance to the given output.
+   */
+  public final void encode(CodeOutput out) {
+    format.encode(this, out);
+  }
 
-        return (short) registerCount;
-    }
-
-    /**
-     * Gets the A register number, as a code unit. This will throw if the
-     * value is out of the range of an unsigned code unit.
-     */
-    public final short getAUnit() {
-        int a = getA();
-
-        if ((a & ~0xffff) != 0) {
-            throw new DexException("Register A out of range: " + Hex.u8(a));
-        }
-
-        return (short) a;
-    }
-
-    /**
-     * Gets the A register number, as a byte. This will throw if the
-     * value is out of the range of an unsigned byte.
-     */
-    public final short getAByte() {
-        int a = getA();
-
-        if ((a & ~0xff) != 0) {
-            throw new DexException("Register A out of range: " + Hex.u8(a));
-        }
-
-        return (short) a;
-    }
-
-    /**
-     * Gets the A register number, as a nibble. This will throw if the
-     * value is out of the range of an unsigned nibble.
-     */
-    public final short getANibble() {
-        int a = getA();
-
-        if ((a & ~0xf) != 0) {
-            throw new DexException("Register A out of range: " + Hex.u8(a));
-        }
-
-        return (short) a;
-    }
-
-    /**
-     * Gets the B register number, as a code unit. This will throw if the
-     * value is out of the range of an unsigned code unit.
-     */
-    public final short getBUnit() {
-        int b = getB();
-
-        if ((b & ~0xffff) != 0) {
-            throw new DexException("Register B out of range: " + Hex.u8(b));
-        }
-
-        return (short) b;
-    }
-
-    /**
-     * Gets the B register number, as a byte. This will throw if the
-     * value is out of the range of an unsigned byte.
-     */
-    public final short getBByte() {
-        int b = getB();
-
-        if ((b & ~0xff) != 0) {
-            throw new DexException("Register B out of range: " + Hex.u8(b));
-        }
-
-        return (short) b;
-    }
-
-    /**
-     * Gets the B register number, as a nibble. This will throw if the
-     * value is out of the range of an unsigned nibble.
-     */
-    public final short getBNibble() {
-        int b = getB();
-
-        if ((b & ~0xf) != 0) {
-            throw new DexException("Register B out of range: " + Hex.u8(b));
-        }
-
-        return (short) b;
-    }
-
-    /**
-     * Gets the C register number, as a code unit. This will throw if the
-     * value is out of the range of an unsigned code unit.
-     */
-    public final short getCUnit() {
-        int c = getC();
-
-        if ((c & ~0xffff) != 0) {
-            throw new DexException("Register C out of range: " + Hex.u8(c));
-        }
-
-        return (short) c;
-    }
-
-    /**
-     * Gets the C register number, as a byte. This will throw if the
-     * value is out of the range of an unsigned byte.
-     */
-    public final short getCByte() {
-        int c = getC();
-
-        if ((c & ~0xff) != 0) {
-            throw new DexException("Register C out of range: " + Hex.u8(c));
-        }
-
-        return (short) c;
-    }
-
-    /**
-     * Gets the C register number, as a nibble. This will throw if the
-     * value is out of the range of an unsigned nibble.
-     */
-    public final short getCNibble() {
-        int c = getC();
-
-        if ((c & ~0xf) != 0) {
-            throw new DexException("Register C out of range: " + Hex.u8(c));
-        }
-
-        return (short) c;
-    }
-
-    /**
-     * Gets the D register number, as a code unit. This will throw if the
-     * value is out of the range of an unsigned code unit.
-     */
-    public final short getDUnit() {
-        int d = getD();
-
-        if ((d & ~0xffff) != 0) {
-            throw new DexException("Register D out of range: " + Hex.u8(d));
-        }
-
-        return (short) d;
-    }
-
-    /**
-     * Gets the D register number, as a byte. This will throw if the
-     * value is out of the range of an unsigned byte.
-     */
-    public final short getDByte() {
-        int d = getD();
-
-        if ((d & ~0xff) != 0) {
-            throw new DexException("Register D out of range: " + Hex.u8(d));
-        }
-
-        return (short) d;
-    }
-
-    /**
-     * Gets the D register number, as a nibble. This will throw if the
-     * value is out of the range of an unsigned nibble.
-     */
-    public final short getDNibble() {
-        int d = getD();
-
-        if ((d & ~0xf) != 0) {
-            throw new DexException("Register D out of range: " + Hex.u8(d));
-        }
-
-        return (short) d;
-    }
-
-    /**
-     * Gets the E register number, as a nibble. This will throw if the
-     * value is out of the range of an unsigned nibble.
-     */
-    public final short getENibble() {
-        int e = getE();
-
-        if ((e & ~0xf) != 0) {
-            throw new DexException("Register E out of range: " + Hex.u8(e));
-        }
-
-        return (short) e;
-    }
-
-    /**
-     * Encodes this instance to the given output.
-     */
-    public final void encode(CodeOutput out) {
-        format.encode(this, out);
-    }
-
-    /**
-     * Returns an instance just like this one, except with the index replaced
-     * with the given one.
-     */
-    public abstract DecodedInstruction withIndex(int newIndex);
+  /**
+   * Returns an instance just like this one, except with the index replaced
+   * with the given one.
+   */
+  public abstract DecodedInstruction withIndex(int newIndex);
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/FillArrayDataPayloadDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/FillArrayDataPayloadDecodedInstruction.java
index 4e59342..35ada3e 100644
--- a/dx/src/com/android/jack/dx/io/instructions/FillArrayDataPayloadDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/FillArrayDataPayloadDecodedInstruction.java
@@ -20,81 +20,78 @@
  * A decoded Dalvik instruction which contains the payload for
  * a {@code packed-switch} instruction.
  */
-public final class FillArrayDataPayloadDecodedInstruction
-        extends DecodedInstruction {
-    /** data array */
-    private final Object data;
+public final class FillArrayDataPayloadDecodedInstruction extends DecodedInstruction {
+  /** data array */
+  private final Object data;
 
-    /** number of elements */
-    private final int size;
+  /** number of elements */
+  private final int size;
 
-    /** element width */
-    private final int elementWidth;
+  /** element width */
+  private final int elementWidth;
 
-    /**
-     * Constructs an instance. This private instance doesn't check the
-     * type of the data array.
-     */
-    private FillArrayDataPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, Object data, int size, int elementWidth) {
-        super(format, opcode, 0, null, 0, 0L);
+  /**
+   * Constructs an instance. This private instance doesn't check the
+   * type of the data array.
+   */
+  private FillArrayDataPayloadDecodedInstruction(InstructionCodec format, int opcode, Object data,
+      int size, int elementWidth) {
+    super(format, opcode, 0, null, 0, 0L);
 
-        this.data = data;
-        this.size = size;
-        this.elementWidth = elementWidth;
-    }
+    this.data = data;
+    this.size = size;
+    this.elementWidth = elementWidth;
+  }
 
-    /**
-     * Constructs an instance.
-     */
-    public FillArrayDataPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, byte[] data) {
-        this(format, opcode, data, data.length, 1);
-    }
+  /**
+   * Constructs an instance.
+   */
+  public FillArrayDataPayloadDecodedInstruction(InstructionCodec format, int opcode, byte[] data) {
+    this(format, opcode, data, data.length, 1);
+  }
 
-    /**
-     * Constructs an instance.
-     */
-    public FillArrayDataPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, short[] data) {
-        this(format, opcode, data, data.length, 2);
-    }
+  /**
+   * Constructs an instance.
+   */
+  public FillArrayDataPayloadDecodedInstruction(InstructionCodec format, int opcode, short[] data) {
+    this(format, opcode, data, data.length, 2);
+  }
 
-    /**
-     * Constructs an instance.
-     */
-    public FillArrayDataPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, int[] data) {
-        this(format, opcode, data, data.length, 4);
-    }
+  /**
+   * Constructs an instance.
+   */
+  public FillArrayDataPayloadDecodedInstruction(InstructionCodec format, int opcode, int[] data) {
+    this(format, opcode, data, data.length, 4);
+  }
 
-    /**
-     * Constructs an instance.
-     */
-    public FillArrayDataPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, long[] data) {
-        this(format, opcode, data, data.length, 8);
-    }
+  /**
+   * Constructs an instance.
+   */
+  public FillArrayDataPayloadDecodedInstruction(InstructionCodec format, int opcode, long[] data) {
+    this(format, opcode, data, data.length, 8);
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 0;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 0;
+  }
 
-    public short getElementWidthUnit() {
-        return (short) elementWidth;
-    }
+  public short getElementWidthUnit() {
+    return (short) elementWidth;
+  }
 
-    public int getSize() {
-        return size;
-    }
+  public int getSize() {
+    return size;
+  }
 
-    public Object getData() {
-        return data;
-    }
+  public Object getData() {
+    return data;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        throw new UnsupportedOperationException("no index in instruction");
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    throw new UnsupportedOperationException("no index in instruction");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/FiveRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/FiveRegisterDecodedInstruction.java
index 0ed17b3..a7a1aea 100644
--- a/dx/src/com/android/jack/dx/io/instructions/FiveRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/FiveRegisterDecodedInstruction.java
@@ -22,70 +22,93 @@
  * A decoded Dalvik instruction which has five register arguments.
  */
 public final class FiveRegisterDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /** register argument "B" */
-    private final int b;
+  /** register argument "B" */
+  private final int b;
 
-    /** register argument "C" */
-    private final int c;
+  /** register argument "C" */
+  private final int c;
 
-    /** register argument "D" */
-    private final int d;
+  /** register argument "D" */
+  private final int d;
 
-    /** register argument "E" */
-    private final int e;
+  /** register argument "E" */
+  private final int e;
 
-    /**
-     * Constructs an instance.
-     */
-    public FiveRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a, int b, int c, int d, int e) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public FiveRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a,
+      int b,
+      int c,
+      int d,
+      int e) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-        this.b = b;
-        this.c = c;
-        this.d = d;
-        this.e = e;
-    }
+    this.a = a;
+    this.b = b;
+    this.c = c;
+    this.d = d;
+    this.e = e;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 5;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 5;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public int getB() {
-        return b;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getB() {
+    return b;
+  }
 
-    /** @inheritDoc */
-    public int getC() {
-        return c;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getC() {
+    return c;
+  }
 
-    /** @inheritDoc */
-    public int getD() {
-        return d;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getD() {
+    return d;
+  }
 
-    /** @inheritDoc */
-    public int getE() {
-        return e;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getE() {
+    return e;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new FiveRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a, b, c, d, e);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new FiveRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a,
+        b,
+        c,
+        d,
+        e);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/FourRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/FourRegisterDecodedInstruction.java
index 9d3e7e3..912a8eb 100644
--- a/dx/src/com/android/jack/dx/io/instructions/FourRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/FourRegisterDecodedInstruction.java
@@ -22,61 +22,81 @@
  * A decoded Dalvik instruction which has five register arguments.
  */
 public final class FourRegisterDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /** register argument "B" */
-    private final int b;
+  /** register argument "B" */
+  private final int b;
 
-    /** register argument "C" */
-    private final int c;
+  /** register argument "C" */
+  private final int c;
 
-    /** register argument "D" */
-    private final int d;
+  /** register argument "D" */
+  private final int d;
 
-    /**
-     * Constructs an instance.
-     */
-    public FourRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a, int b, int c, int d) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public FourRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a,
+      int b,
+      int c,
+      int d) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-        this.b = b;
-        this.c = c;
-        this.d = d;
-    }
+    this.a = a;
+    this.b = b;
+    this.c = c;
+    this.d = d;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 4;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 4;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public int getB() {
-        return b;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getB() {
+    return b;
+  }
 
-    /** @inheritDoc */
-    public int getC() {
-        return c;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getC() {
+    return c;
+  }
 
-    /** @inheritDoc */
-    public int getD() {
-        return d;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getD() {
+    return d;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new FourRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a, b, c, d);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new FourRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a,
+        b,
+        c,
+        d);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/InstructionCodec.java b/dx/src/com/android/jack/dx/io/instructions/InstructionCodec.java
index d24d930..c913fcb 100644
--- a/dx/src/com/android/jack/dx/io/instructions/InstructionCodec.java
+++ b/dx/src/com/android/jack/dx/io/instructions/InstructionCodec.java
@@ -29,934 +29,864 @@
  * and encode from instances of {@link DecodedInstruction}.
  */
 public enum InstructionCodec {
-    FORMAT_00X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcodeUnit, 0, null,
-                    0, 0L);
-        }
+  FORMAT_00X() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      return new ZeroRegisterDecodedInstruction(this, opcodeUnit, 0, null, 0, 0L);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(insn.getOpcodeUnit());
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      out.write(insn.getOpcodeUnit());
+    }
+  },
 
-    FORMAT_10X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int literal = byte1(opcodeUnit); // should be zero
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal);
-        }
+  FORMAT_10X() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int opcode = byte0(opcodeUnit);
+      int literal = byte1(opcodeUnit); // should be zero
+      return new ZeroRegisterDecodedInstruction(this, opcode, 0, null, 0, literal);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(insn.getOpcodeUnit());
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      out.write(insn.getOpcodeUnit());
+    }
+  },
 
-    FORMAT_12X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int b = nibble3(opcodeUnit);
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, 0L,
-                    a, b);
-        }
+  FORMAT_12X() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int opcode = byte0(opcodeUnit);
+      int a = nibble2(opcodeUnit);
+      int b = nibble3(opcodeUnit);
+      return new TwoRegisterDecodedInstruction(this, opcode, 0, null, 0, 0L, a, b);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcodeUnit(),
-                             makeByte(insn.getA(), insn.getB())));
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      out.write(codeUnit(insn.getOpcodeUnit(), makeByte(insn.getA(), insn.getB())));
+    }
+  },
 
-    FORMAT_11N() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int literal = (nibble3(opcodeUnit) << 28) >> 28; // sign-extend
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a);
-        }
+  FORMAT_11N() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int opcode = byte0(opcodeUnit);
+      int a = nibble2(opcodeUnit);
+      int literal = (nibble3(opcodeUnit) << 28) >> 28; // sign-extend
+      return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcodeUnit(),
-                             makeByte(insn.getA(), insn.getLiteralNibble())));
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      out.write(codeUnit(insn.getOpcodeUnit(), makeByte(insn.getA(), insn.getLiteralNibble())));
+    }
+  },
 
-    FORMAT_11X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, 0L,
-                    a);
-        }
+  FORMAT_11X() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int opcode = byte0(opcodeUnit);
+      int a = byte1(opcodeUnit);
+      return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, 0L, a);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(codeUnit(insn.getOpcode(), insn.getA()));
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      out.write(codeUnit(insn.getOpcode(), insn.getA()));
+    }
+  },
 
-    FORMAT_10T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int target = (byte) byte1(opcodeUnit); // sign-extend
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    baseAddress + target, 0L);
-        }
+  FORMAT_10T() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int baseAddress = in.cursor() - 1;
+      int opcode = byte0(opcodeUnit);
+      int target = (byte) byte1(opcodeUnit); // sign-extend
+      return new ZeroRegisterDecodedInstruction(this, opcode, 0, null, baseAddress + target, 0L);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            int relativeTarget = insn.getTargetByte(out.cursor());
-            out.write(codeUnit(insn.getOpcode(), relativeTarget));
-        }
-    },
+  @Override
+    public void encode(DecodedInstruction insn, CodeOutput out) {
+      int relativeTarget = insn.getTargetByte(out.cursor());
+      out.write(codeUnit(insn.getOpcode(), relativeTarget));
+    }
+  },
 
-    FORMAT_20T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int literal = byte1(opcodeUnit); // should be zero
-            int target = (short) in.read(); // sign-extend
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    baseAddress + target, literal);
-        }
+  FORMAT_20T() {
+  @Override
+    public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+      int baseAddress = in.cursor() - 1;
+      int opcode = byte0(opcodeUnit);
+      int literal = byte1(opcodeUnit); // should be zero
+      int target = (short) in.read(); // sign-extend
+      return new ZeroRegisterDecodedInstruction(this,
+          opcode,
+          0,
+          null,
+          baseAddress + target,
+          literal);
+    }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            short relativeTarget = insn.getTargetUnit(out.cursor());
-            out.write(insn.getOpcodeUnit(), relativeTarget);
-        }
-    },
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    short relativeTarget = insn.getTargetUnit(out.cursor());
+    out.write(insn.getOpcodeUnit(), relativeTarget);
+  }
+},
 
-    FORMAT_20BC() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            // Note: We use the literal field to hold the decoded AA value.
-            int opcode = byte0(opcodeUnit);
-            int literal = byte1(opcodeUnit);
-            int index = in.read();
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcode, index, IndexType.VARIES,
-                    0, literal);
-        }
+  FORMAT_20BC() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    // Note: We use the literal field to hold the decoded AA value.
+    int opcode = byte0(opcodeUnit);
+    int literal = byte1(opcodeUnit);
+    int index = in.read();
+    return new ZeroRegisterDecodedInstruction(this, opcode, index, IndexType.VARIES, 0, literal);
+  }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getLiteralByte()),
-                    insn.getIndexUnit());
-        }
-    },
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getLiteralByte()), insn.getIndexUnit());
+  }
+},
 
-    FORMAT_22X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int b = in.read();
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, 0L,
-                    a, b);
-        }
+  FORMAT_22X() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int b = in.read();
+    return new TwoRegisterDecodedInstruction(this, opcode, 0, null, 0, 0L, a, b);
+  }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    insn.getBUnit());
-        }
-    },
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), insn.getBUnit());
+  }
+},
 
-    FORMAT_21T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int target = (short) in.read(); // sign-extend
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    baseAddress + target, 0L,
-                    a);
-        }
+  FORMAT_21T() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int baseAddress = in.cursor() - 1;
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int target = (short) in.read(); // sign-extend
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, baseAddress + target, 0L, a);
+  }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            short relativeTarget = insn.getTargetUnit(out.cursor());
-            out.write(codeUnit(insn.getOpcode(), insn.getA()), relativeTarget);
-        }
-    },
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    short relativeTarget = insn.getTargetUnit(out.cursor());
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), relativeTarget);
+  }
+},
 
-    FORMAT_21S() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int literal = (short) in.read(); // sign-extend
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a);
-        }
+  FORMAT_21S() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int literal = (short) in.read(); // sign-extend
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a);
+  }
 
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    insn.getLiteralUnit());
-        }
-    },
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), insn.getLiteralUnit());
+  }
+},
 
-    FORMAT_21H() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            long literal = (short) in.read(); // sign-extend
+  FORMAT_21H() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    long literal = (short) in.read(); // sign-extend
 
-            /*
-             * Format 21h decodes differently depending on the opcode,
-             * because the "signed hat" might represent either a 32-
-             * or 64- bit value.
-             */
-            literal <<= (opcode == Opcodes.CONST_HIGH16) ? 16 : 48;
-
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            // See above.
-            int opcode = insn.getOpcode();
-            int shift = (opcode == Opcodes.CONST_HIGH16) ? 16 : 48;
-            short literal = (short) (insn.getLiteral() >> shift);
-
-            out.write(codeUnit(opcode, insn.getA()), literal);
-        }
-    },
-
-    FORMAT_21C() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int index = in.read();
-            IndexType indexType = OpcodeInfo.getIndexType(opcode);
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, index, indexType,
-                    0, 0L,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    insn.getIndexUnit());
-        }
-    },
-
-    FORMAT_23X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int bc = in.read();
-            int b = byte0(bc);
-            int c = byte1(bc);
-            return new ThreeRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, 0L,
-                    a, b, c);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    codeUnit(insn.getB(), insn.getC()));
-        }
-    },
-
-    FORMAT_22B() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int bc = in.read();
-            int b = byte0(bc);
-            int literal = (byte) byte1(bc); // sign-extend
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    codeUnit(insn.getB(),
-                             insn.getLiteralByte()));
-        }
-    },
-
-    FORMAT_22T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int b = nibble3(opcodeUnit);
-            int target = (short) in.read(); // sign-extend
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    baseAddress + target, 0L,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            short relativeTarget = insn.getTargetUnit(out.cursor());
-            out.write(
-                    codeUnit(insn.getOpcode(),
-                             makeByte(insn.getA(), insn.getB())),
-                    relativeTarget);
-        }
-    },
-
-    FORMAT_22S() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int b = nibble3(opcodeUnit);
-            int literal = (short) in.read(); // sign-extend
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(),
-                             makeByte(insn.getA(), insn.getB())),
-                    insn.getLiteralUnit());
-        }
-    },
-
-    FORMAT_22C() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int b = nibble3(opcodeUnit);
-            int index = in.read();
-            IndexType indexType = OpcodeInfo.getIndexType(opcode);
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, index, indexType,
-                    0, 0L,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(),
-                             makeByte(insn.getA(), insn.getB())),
-                    insn.getIndexUnit());
-        }
-    },
-
-    FORMAT_22CS() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = nibble2(opcodeUnit);
-            int b = nibble3(opcodeUnit);
-            int index = in.read();
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, index, IndexType.FIELD_OFFSET,
-                    0, 0L,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(
-                    codeUnit(insn.getOpcode(),
-                             makeByte(insn.getA(), insn.getB())),
-                    insn.getIndexUnit());
-        }
-    },
-
-    FORMAT_30T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int literal = byte1(opcodeUnit); // should be zero
-            int target = in.readInt();
-            return new ZeroRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    baseAddress + target, literal);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            int relativeTarget = insn.getTarget(out.cursor());
-            out.write(insn.getOpcodeUnit(),
-                    unit0(relativeTarget), unit1(relativeTarget));
-        }
-    },
-
-    FORMAT_32X() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int literal = byte1(opcodeUnit); // should be zero
-            int a = in.read();
-            int b = in.read();
-            return new TwoRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a, b);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            out.write(insn.getOpcodeUnit(), insn.getAUnit(), insn.getBUnit());
-        }
-    },
-
-    FORMAT_31I() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int literal = in.readInt();
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            int literal = insn.getLiteralInt();
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    unit0(literal),
-                    unit1(literal));
-        }
-    },
-
-    FORMAT_31T() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int baseAddress = in.cursor() - 1;
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int target = baseAddress + in.readInt();
-
-            /*
-             * Switch instructions need to "forward" their addresses to their
-             * payload target instructions.
-             */
-            switch (opcode) {
-                case Opcodes.PACKED_SWITCH:
-                case Opcodes.SPARSE_SWITCH: {
-                    in.setBaseAddress(target, baseAddress);
-                    break;
-                }
-            }
-
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    target, 0L,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            int relativeTarget = insn.getTarget(out.cursor());
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    unit0(relativeTarget), unit1(relativeTarget));
-        }
-    },
-
-    FORMAT_31C() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            int index = in.readInt();
-            IndexType indexType = OpcodeInfo.getIndexType(opcode);
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, index, indexType,
-                    0, 0L,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            int index = insn.getIndex();
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    unit0(index),
-                    unit1(index));
-        }
-    },
-
-    FORMAT_35C() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterList(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterList(insn, out);
-        }
-    },
-
-    FORMAT_35MS() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterList(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterList(insn, out);
-        }
-    },
-
-    FORMAT_35MI() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterList(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterList(insn, out);
-        }
-    },
-
-    FORMAT_3RC() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterRange(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterRange(insn, out);
-        }
-    },
-
-    FORMAT_3RMS() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterRange(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterRange(insn, out);
-        }
-    },
-
-    FORMAT_3RMI() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            return decodeRegisterRange(this, opcodeUnit, in);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            encodeRegisterRange(insn, out);
-        }
-    },
-
-    FORMAT_51L() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int opcode = byte0(opcodeUnit);
-            int a = byte1(opcodeUnit);
-            long literal = in.readLong();
-            return new OneRegisterDecodedInstruction(
-                    this, opcode, 0, null,
-                    0, literal,
-                    a);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            long literal = insn.getLiteral();
-            out.write(
-                    codeUnit(insn.getOpcode(), insn.getA()),
-                    unit0(literal),
-                    unit1(literal),
-                    unit2(literal),
-                    unit3(literal));
-        }
-    },
-
-    FORMAT_PACKED_SWITCH_PAYLOAD() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int size = in.read();
-            int firstKey = in.readInt();
-            int[] targets = new int[size];
-
-            for (int i = 0; i < size; i++) {
-                targets[i] = in.readInt();
-            }
-
-            return new PackedSwitchPayloadDecodedInstruction(
-                    this, opcodeUnit, firstKey, targets);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            PackedSwitchPayloadDecodedInstruction payload =
-                (PackedSwitchPayloadDecodedInstruction) insn;
-            int[] targets = payload.getTargets();
-
-            out.write(payload.getOpcodeUnit());
-            out.write(asUnsignedUnit(targets.length));
-            out.writeInt(payload.getFirstKey());
-
-            for (int target : targets) {
-                out.writeInt(target);
-            }
-        }
-    },
-
-    FORMAT_SPARSE_SWITCH_PAYLOAD() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int size = in.read();
-            int[] keys = new int[size];
-            int[] targets = new int[size];
-
-            for (int i = 0; i < size; i++) {
-                keys[i] = in.readInt();
-            }
-
-            for (int i = 0; i < size; i++) {
-                targets[i] = in.readInt();
-            }
-
-            return new SparseSwitchPayloadDecodedInstruction(
-                    this, opcodeUnit, keys, targets);
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            SparseSwitchPayloadDecodedInstruction payload =
-                (SparseSwitchPayloadDecodedInstruction) insn;
-            int[] keys = payload.getKeys();
-            int[] targets = payload.getTargets();
-
-            out.write(payload.getOpcodeUnit());
-            out.write(asUnsignedUnit(targets.length));
-
-            for (int key : keys) {
-                out.writeInt(key);
-            }
-
-            for (int target : targets) {
-                out.writeInt(target);
-            }
-        }
-    },
-
-    FORMAT_FILL_ARRAY_DATA_PAYLOAD() {
-        @Override public DecodedInstruction decode(int opcodeUnit,
-                CodeInput in) throws EOFException {
-            int elementWidth = in.read();
-            int size = in.readInt();
-
-            switch (elementWidth) {
-                case 1: {
-                    byte[] array = new byte[size];
-                    boolean even = true;
-                    for (int i = 0, value = 0; i < size; i++, even = !even) {
-                        if (even) {
-                            value = in.read();
-                        }
-                        array[i] = (byte) (value & 0xff);
-                        value >>= 8;
-                    }
-                    return new FillArrayDataPayloadDecodedInstruction(
-                            this, opcodeUnit, array);
-                }
-                case 2: {
-                    short[] array = new short[size];
-                    for (int i = 0; i < size; i++) {
-                        array[i] = (short) in.read();
-                    }
-                    return new FillArrayDataPayloadDecodedInstruction(
-                            this, opcodeUnit, array);
-                }
-                case 4: {
-                    int[] array = new int[size];
-                    for (int i = 0; i < size; i++) {
-                        array[i] = in.readInt();
-                    }
-                    return new FillArrayDataPayloadDecodedInstruction(
-                            this, opcodeUnit, array);
-                }
-                case 8: {
-                    long[] array = new long[size];
-                    for (int i = 0; i < size; i++) {
-                        array[i] = in.readLong();
-                    }
-                    return new FillArrayDataPayloadDecodedInstruction(
-                            this, opcodeUnit, array);
-                }
-            }
-
-            throw new DexException("bogus element_width: "
-                    + Hex.u2(elementWidth));
-        }
-
-        @Override public void encode(DecodedInstruction insn, CodeOutput out) {
-            FillArrayDataPayloadDecodedInstruction payload =
-                (FillArrayDataPayloadDecodedInstruction) insn;
-            short elementWidth = payload.getElementWidthUnit();
-            Object data = payload.getData();
-
-            out.write(payload.getOpcodeUnit());
-            out.write(elementWidth);
-            out.writeInt(payload.getSize());
-
-            switch (elementWidth) {
-                case 1: out.write((byte[]) data);  break;
-                case 2: out.write((short[]) data); break;
-                case 4: out.write((int[]) data);   break;
-                case 8: out.write((long[]) data);  break;
-                default: {
-                    throw new DexException("bogus element_width: "
-                            + Hex.u2(elementWidth));
-                }
-            }
-        }
-    };
-
-    /**
-     * Decodes an instruction specified by the given opcode unit, reading
-     * any required additional code units from the given input source.
+    /*
+     * Format 21h decodes differently depending on the opcode,
+     * because the "signed hat" might represent either a 32-
+     * or 64- bit value.
      */
-    public abstract DecodedInstruction decode(int opcodeUnit, CodeInput in)
-        throws EOFException;
+    literal <<= (opcode == Opcodes.CONST_HIGH16) ? 16 : 48;
 
-    /**
-     * Encodes the given instruction.
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    // See above.
+    int opcode = insn.getOpcode();
+    int shift = (opcode == Opcodes.CONST_HIGH16) ? 16 : 48;
+    short literal = (short) (insn.getLiteral() >> shift);
+
+    out.write(codeUnit(opcode, insn.getA()), literal);
+  }
+},
+
+  FORMAT_21C() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int index = in.read();
+    IndexType indexType = OpcodeInfo.getIndexType(opcode);
+    return new OneRegisterDecodedInstruction(this, opcode, index, indexType, 0, 0L, a);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), insn.getIndexUnit());
+  }
+},
+
+  FORMAT_23X() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int bc = in.read();
+    int b = byte0(bc);
+    int c = byte1(bc);
+    return new ThreeRegisterDecodedInstruction(this, opcode, 0, null, 0, 0L, a, b, c);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), codeUnit(insn.getB(), insn.getC()));
+  }
+},
+
+  FORMAT_22B() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int bc = in.read();
+    int b = byte0(bc);
+    int literal = (byte) byte1(bc); // sign-extend
+    return new TwoRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a, b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getA()),
+        codeUnit(insn.getB(), insn.getLiteralByte()));
+  }
+},
+
+  FORMAT_22T() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int baseAddress = in.cursor() - 1;
+    int opcode = byte0(opcodeUnit);
+    int a = nibble2(opcodeUnit);
+    int b = nibble3(opcodeUnit);
+    int target = (short) in.read(); // sign-extend
+    return new TwoRegisterDecodedInstruction(this, opcode, 0, null, baseAddress + target, 0L, a, b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    short relativeTarget = insn.getTargetUnit(out.cursor());
+    out.write(codeUnit(insn.getOpcode(), makeByte(insn.getA(), insn.getB())), relativeTarget);
+  }
+},
+
+  FORMAT_22S() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = nibble2(opcodeUnit);
+    int b = nibble3(opcodeUnit);
+    int literal = (short) in.read(); // sign-extend
+    return new TwoRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a, b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), makeByte(insn.getA(), insn.getB())),
+        insn.getLiteralUnit());
+  }
+},
+
+  FORMAT_22C() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = nibble2(opcodeUnit);
+    int b = nibble3(opcodeUnit);
+    int index = in.read();
+    IndexType indexType = OpcodeInfo.getIndexType(opcode);
+    return new TwoRegisterDecodedInstruction(this, opcode, index, indexType, 0, 0L, a, b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), makeByte(insn.getA(), insn.getB())), insn.getIndexUnit());
+  }
+},
+
+  FORMAT_22CS() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = nibble2(opcodeUnit);
+    int b = nibble3(opcodeUnit);
+    int index = in.read();
+    return new TwoRegisterDecodedInstruction(this,
+        opcode,
+        index,
+        IndexType.FIELD_OFFSET,
+        0,
+        0L,
+        a,
+        b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), makeByte(insn.getA(), insn.getB())), insn.getIndexUnit());
+  }
+},
+
+  FORMAT_30T() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int baseAddress = in.cursor() - 1;
+    int opcode = byte0(opcodeUnit);
+    int literal = byte1(opcodeUnit); // should be zero
+    int target = in.readInt();
+    return new ZeroRegisterDecodedInstruction(this, opcode, 0, null, baseAddress + target, literal);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    int relativeTarget = insn.getTarget(out.cursor());
+    out.write(insn.getOpcodeUnit(), unit0(relativeTarget), unit1(relativeTarget));
+  }
+},
+
+  FORMAT_32X() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int literal = byte1(opcodeUnit); // should be zero
+    int a = in.read();
+    int b = in.read();
+    return new TwoRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a, b);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    out.write(insn.getOpcodeUnit(), insn.getAUnit(), insn.getBUnit());
+  }
+},
+
+  FORMAT_31I() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int literal = in.readInt();
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    int literal = insn.getLiteralInt();
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), unit0(literal), unit1(literal));
+  }
+},
+
+  FORMAT_31T() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int baseAddress = in.cursor() - 1;
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int target = baseAddress + in.readInt();
+
+    /*
+     * Switch instructions need to "forward" their addresses to their
+     * payload target instructions.
      */
-    public abstract void encode(DecodedInstruction insn, CodeOutput out);
+    switch (opcode) {
+      case Opcodes.PACKED_SWITCH:
+      case Opcodes.SPARSE_SWITCH: {
+        in.setBaseAddress(target, baseAddress);
+        break;
+      }
+    }
 
-    /**
-     * Helper method that decodes any of the register-list formats.
-     */
-    private static DecodedInstruction decodeRegisterList(
-            InstructionCodec format, int opcodeUnit, CodeInput in)
-            throws EOFException {
-        int opcode = byte0(opcodeUnit);
-        int e = nibble2(opcodeUnit);
-        int registerCount = nibble3(opcodeUnit);
-        int index = in.read();
-        int abcd = in.read();
-        int a = nibble0(abcd);
-        int b = nibble1(abcd);
-        int c = nibble2(abcd);
-        int d = nibble3(abcd);
-        IndexType indexType = OpcodeInfo.getIndexType(opcode);
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, target, 0L, a);
+  }
 
-        // TODO: Having to switch like this is less than ideal.
-        switch (registerCount) {
-            case 0:
-                return new ZeroRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L);
-            case 1:
-                return new OneRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L,
-                        a);
-            case 2:
-                return new TwoRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L,
-                        a, b);
-            case 3:
-                return new ThreeRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L,
-                        a, b, c);
-            case 4:
-                return new FourRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L,
-                        a, b, c, d);
-            case 5:
-                return new FiveRegisterDecodedInstruction(
-                        format, opcode, index, indexType,
-                        0, 0L,
-                        a, b, c, d, e);
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    int relativeTarget = insn.getTarget(out.cursor());
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), unit0(relativeTarget),
+        unit1(relativeTarget));
+  }
+},
+
+  FORMAT_31C() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    int index = in.readInt();
+    IndexType indexType = OpcodeInfo.getIndexType(opcode);
+    return new OneRegisterDecodedInstruction(this, opcode, index, indexType, 0, 0L, a);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    int index = insn.getIndex();
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), unit0(index), unit1(index));
+  }
+},
+
+  FORMAT_35C() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterList(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterList(insn, out);
+  }
+},
+
+  FORMAT_35MS() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterList(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterList(insn, out);
+  }
+},
+
+  FORMAT_35MI() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterList(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterList(insn, out);
+  }
+},
+
+  FORMAT_3RC() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterRange(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterRange(insn, out);
+  }
+},
+
+  FORMAT_3RMS() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterRange(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterRange(insn, out);
+  }
+},
+
+  FORMAT_3RMI() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    return decodeRegisterRange(this, opcodeUnit, in);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    encodeRegisterRange(insn, out);
+  }
+},
+
+  FORMAT_51L() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int a = byte1(opcodeUnit);
+    long literal = in.readLong();
+    return new OneRegisterDecodedInstruction(this, opcode, 0, null, 0, literal, a);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    long literal = insn.getLiteral();
+    out.write(codeUnit(insn.getOpcode(), insn.getA()), unit0(literal), unit1(literal),
+        unit2(literal), unit3(literal));
+  }
+},
+
+  FORMAT_PACKED_SWITCH_PAYLOAD() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int size = in.read();
+    int firstKey = in.readInt();
+    int[] targets = new int[size];
+
+    for (int i = 0; i < size; i++) {
+      targets[i] = in.readInt();
+    }
+
+    return new PackedSwitchPayloadDecodedInstruction(this, opcodeUnit, firstKey, targets);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    PackedSwitchPayloadDecodedInstruction payload = (PackedSwitchPayloadDecodedInstruction) insn;
+    int[] targets = payload.getTargets();
+
+    out.write(payload.getOpcodeUnit());
+    out.write(asUnsignedUnit(targets.length));
+    out.writeInt(payload.getFirstKey());
+
+    for (int target : targets) {
+      out.writeInt(target);
+    }
+  }
+},
+
+  FORMAT_SPARSE_SWITCH_PAYLOAD() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int size = in.read();
+    int[] keys = new int[size];
+    int[] targets = new int[size];
+
+    for (int i = 0; i < size; i++) {
+      keys[i] = in.readInt();
+    }
+
+    for (int i = 0; i < size; i++) {
+      targets[i] = in.readInt();
+    }
+
+    return new SparseSwitchPayloadDecodedInstruction(this, opcodeUnit, keys, targets);
+  }
+
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    SparseSwitchPayloadDecodedInstruction payload = (SparseSwitchPayloadDecodedInstruction) insn;
+    int[] keys = payload.getKeys();
+    int[] targets = payload.getTargets();
+
+    out.write(payload.getOpcodeUnit());
+    out.write(asUnsignedUnit(targets.length));
+
+    for (int key : keys) {
+      out.writeInt(key);
+    }
+
+    for (int target : targets) {
+      out.writeInt(target);
+    }
+  }
+},
+
+  FORMAT_FILL_ARRAY_DATA_PAYLOAD() {
+  @Override
+  public DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException {
+    int elementWidth = in.read();
+    int size = in.readInt();
+
+    switch (elementWidth) {
+      case 1: {
+        byte[] array = new byte[size];
+        boolean even = true;
+        for (int i = 0, value = 0; i < size; i++, even = !even) {
+          if (even) {
+            value = in.read();
+          }
+          array[i] = (byte) (value & 0xff);
+          value >>= 8;
         }
-
-        throw new DexException("bogus registerCount: "
-                + Hex.uNibble(registerCount));
-    }
-
-    /**
-     * Helper method that encodes any of the register-list formats.
-     */
-    private static void encodeRegisterList(DecodedInstruction insn,
-            CodeOutput out) {
-        out.write(codeUnit(insn.getOpcode(),
-                        makeByte(insn.getE(), insn.getRegisterCount())),
-                insn.getIndexUnit(),
-                codeUnit(insn.getA(), insn.getB(), insn.getC(), insn.getD()));
-    }
-
-    /**
-     * Helper method that decodes any of the three-unit register-range formats.
-     */
-    private static DecodedInstruction decodeRegisterRange(
-            InstructionCodec format, int opcodeUnit, CodeInput in)
-            throws EOFException {
-        int opcode = byte0(opcodeUnit);
-        int registerCount = byte1(opcodeUnit);
-        int index = in.read();
-        int a = in.read();
-        IndexType indexType = OpcodeInfo.getIndexType(opcode);
-        return new RegisterRangeDecodedInstruction(
-                format, opcode, index, indexType,
-                0, 0L,
-                a, registerCount);
-    }
-
-    /**
-     * Helper method that encodes any of the three-unit register-range formats.
-     */
-    private static void encodeRegisterRange(DecodedInstruction insn,
-            CodeOutput out) {
-        out.write(codeUnit(insn.getOpcode(), insn.getRegisterCount()),
-                insn.getIndexUnit(),
-                insn.getAUnit());
-    }
-
-    private static short codeUnit(int lowByte, int highByte) {
-        if ((lowByte & ~0xff) != 0) {
-            throw new IllegalArgumentException("bogus lowByte");
+        return new FillArrayDataPayloadDecodedInstruction(this, opcodeUnit, array);
+      }
+      case 2: {
+        short[] array = new short[size];
+        for (int i = 0; i < size; i++) {
+          array[i] = (short) in.read();
         }
-
-        if ((highByte & ~0xff) != 0) {
-            throw new IllegalArgumentException("bogus highByte");
+        return new FillArrayDataPayloadDecodedInstruction(this, opcodeUnit, array);
+      }
+      case 4: {
+        int[] array = new int[size];
+        for (int i = 0; i < size; i++) {
+          array[i] = in.readInt();
         }
-
-        return (short) (lowByte | (highByte << 8));
-    }
-
-    private static short codeUnit(int nibble0, int nibble1, int nibble2,
-            int nibble3) {
-        if ((nibble0 & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus nibble0");
+        return new FillArrayDataPayloadDecodedInstruction(this, opcodeUnit, array);
+      }
+      case 8: {
+        long[] array = new long[size];
+        for (int i = 0; i < size; i++) {
+          array[i] = in.readLong();
         }
-
-        if ((nibble1 & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus nibble1");
-        }
-
-        if ((nibble2 & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus nibble2");
-        }
-
-        if ((nibble3 & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus nibble3");
-        }
-
-        return (short) (nibble0 | (nibble1 << 4)
-                | (nibble2 << 8) | (nibble3 << 12));
+        return new FillArrayDataPayloadDecodedInstruction(this, opcodeUnit, array);
+      }
     }
 
-    private static int makeByte(int lowNibble, int highNibble) {
-        if ((lowNibble & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus lowNibble");
-        }
+    throw new DexException("bogus element_width: " + Hex.u2(elementWidth));
+  }
 
-        if ((highNibble & ~0xf) != 0) {
-            throw new IllegalArgumentException("bogus highNibble");
-        }
+  @Override
+  public void encode(DecodedInstruction insn, CodeOutput out) {
+    FillArrayDataPayloadDecodedInstruction payload = (FillArrayDataPayloadDecodedInstruction) insn;
+    short elementWidth = payload.getElementWidthUnit();
+    Object data = payload.getData();
 
-        return lowNibble | (highNibble << 4);
+    out.write(payload.getOpcodeUnit());
+    out.write(elementWidth);
+    out.writeInt(payload.getSize());
+
+    switch (elementWidth) {
+      case 1:
+        out.write((byte[]) data);
+        break;
+      case 2:
+        out.write((short[]) data);
+        break;
+      case 4:
+        out.write((int[]) data);
+        break;
+      case 8:
+        out.write((long[]) data);
+        break;
+      default: {
+        throw new DexException("bogus element_width: " + Hex.u2(elementWidth));
+      }
+    }
+  }
+};
+
+  /**
+   * Decodes an instruction specified by the given opcode unit, reading
+   * any required additional code units from the given input source.
+   */
+  public abstract DecodedInstruction decode(int opcodeUnit, CodeInput in) throws EOFException;
+
+  /**
+   * Encodes the given instruction.
+   */
+  public abstract void encode(DecodedInstruction insn, CodeOutput out);
+
+  /**
+   * Helper method that decodes any of the register-list formats.
+   */
+  private static DecodedInstruction decodeRegisterList(InstructionCodec format, int opcodeUnit,
+      CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int e = nibble2(opcodeUnit);
+    int registerCount = nibble3(opcodeUnit);
+    int index = in.read();
+    int abcd = in.read();
+    int a = nibble0(abcd);
+    int b = nibble1(abcd);
+    int c = nibble2(abcd);
+    int d = nibble3(abcd);
+    IndexType indexType = OpcodeInfo.getIndexType(opcode);
+
+    // TODO(dx team): Having to switch like this is less than ideal.
+    switch (registerCount) {
+      case 0:
+        return new ZeroRegisterDecodedInstruction(format, opcode, index, indexType, 0, 0L);
+      case 1:
+        return new OneRegisterDecodedInstruction(format, opcode, index, indexType, 0, 0L, a);
+      case 2:
+        return new TwoRegisterDecodedInstruction(format, opcode, index, indexType, 0, 0L, a, b);
+      case 3:
+        return new ThreeRegisterDecodedInstruction(format,
+            opcode,
+            index,
+            indexType,
+            0,
+            0L,
+            a,
+            b,
+            c);
+      case 4:
+        return new FourRegisterDecodedInstruction(format,
+            opcode,
+            index,
+            indexType,
+            0,
+            0L,
+            a,
+            b,
+            c,
+            d);
+      case 5:
+        return new FiveRegisterDecodedInstruction(format,
+            opcode,
+            index,
+            indexType,
+            0,
+            0L,
+            a,
+            b,
+            c,
+            d,
+            e);
     }
 
-    private static short asUnsignedUnit(int value) {
-        if ((value & ~0xffff) != 0) {
-            throw new IllegalArgumentException("bogus unsigned code unit");
-        }
+    throw new DexException("bogus registerCount: " + Hex.uNibble(registerCount));
+  }
 
-        return (short) value;
+  /**
+   * Helper method that encodes any of the register-list formats.
+   */
+  private static void encodeRegisterList(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), makeByte(insn.getE(), insn.getRegisterCount())),
+        insn.getIndexUnit(), codeUnit(insn.getA(), insn.getB(), insn.getC(), insn.getD()));
+  }
+
+  /**
+   * Helper method that decodes any of the three-unit register-range formats.
+   */
+  private static DecodedInstruction decodeRegisterRange(InstructionCodec format, int opcodeUnit,
+      CodeInput in) throws EOFException {
+    int opcode = byte0(opcodeUnit);
+    int registerCount = byte1(opcodeUnit);
+    int index = in.read();
+    int a = in.read();
+    IndexType indexType = OpcodeInfo.getIndexType(opcode);
+    return new RegisterRangeDecodedInstruction(format,
+        opcode,
+        index,
+        indexType,
+        0,
+        0L,
+        a,
+        registerCount);
+  }
+
+  /**
+   * Helper method that encodes any of the three-unit register-range formats.
+   */
+  private static void encodeRegisterRange(DecodedInstruction insn, CodeOutput out) {
+    out.write(codeUnit(insn.getOpcode(), insn.getRegisterCount()), insn.getIndexUnit(),
+        insn.getAUnit());
+  }
+
+  private static short codeUnit(int lowByte, int highByte) {
+    if ((lowByte & ~0xff) != 0) {
+      throw new IllegalArgumentException("bogus lowByte");
     }
 
-    private static short unit0(int value) {
-        return (short) value;
+    if ((highByte & ~0xff) != 0) {
+      throw new IllegalArgumentException("bogus highByte");
     }
 
-    private static short unit1(int value) {
-        return (short) (value >> 16);
+    return (short) (lowByte | (highByte << 8));
+  }
+
+  private static short codeUnit(int nibble0, int nibble1, int nibble2, int nibble3) {
+    if ((nibble0 & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus nibble0");
     }
 
-    private static short unit0(long value) {
-        return (short) value;
+    if ((nibble1 & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus nibble1");
     }
 
-    private static short unit1(long value) {
-        return (short) (value >> 16);
+    if ((nibble2 & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus nibble2");
     }
 
-    private static short unit2(long value) {
-        return (short) (value >> 32);
+    if ((nibble3 & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus nibble3");
     }
 
-    private static short unit3(long value) {
-        return (short) (value >> 48);
+    return (short) (nibble0 | (nibble1 << 4) | (nibble2 << 8) | (nibble3 << 12));
+  }
+
+  private static int makeByte(int lowNibble, int highNibble) {
+    if ((lowNibble & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus lowNibble");
     }
 
-    private static int byte0(int value) {
-        return value & 0xff;
+    if ((highNibble & ~0xf) != 0) {
+      throw new IllegalArgumentException("bogus highNibble");
     }
 
-    private static int byte1(int value) {
-        return (value >> 8) & 0xff;
+    return lowNibble | (highNibble << 4);
+  }
+
+  private static short asUnsignedUnit(int value) {
+    if ((value & ~0xffff) != 0) {
+      throw new IllegalArgumentException("bogus unsigned code unit");
     }
 
-    private static int byte2(int value) {
-        return (value >> 16) & 0xff;
-    }
+    return (short) value;
+  }
 
-    private static int byte3(int value) {
-        return value >>> 24;
-    }
+  private static short unit0(int value) {
+    return (short) value;
+  }
 
-    private static int nibble0(int value) {
-        return value & 0xf;
-    }
+  private static short unit1(int value) {
+    return (short) (value >> 16);
+  }
 
-    private static int nibble1(int value) {
-        return (value >> 4) & 0xf;
-    }
+  private static short unit0(long value) {
+    return (short) value;
+  }
 
-    private static int nibble2(int value) {
-        return (value >> 8) & 0xf;
-    }
+  private static short unit1(long value) {
+    return (short) (value >> 16);
+  }
 
-    private static int nibble3(int value) {
-        return (value >> 12) & 0xf;
-    }
+  private static short unit2(long value) {
+    return (short) (value >> 32);
+  }
+
+  private static short unit3(long value) {
+    return (short) (value >> 48);
+  }
+
+  private static int byte0(int value) {
+    return value & 0xff;
+  }
+
+  private static int byte1(int value) {
+    return (value >> 8) & 0xff;
+  }
+
+  private static int nibble0(int value) {
+    return value & 0xf;
+  }
+
+  private static int nibble1(int value) {
+    return (value >> 4) & 0xf;
+  }
+
+  private static int nibble2(int value) {
+    return (value >> 8) & 0xf;
+  }
+
+  private static int nibble3(int value) {
+    return (value >> 12) & 0xf;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/OneRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/OneRegisterDecodedInstruction.java
index acde53a..cac4d96 100644
--- a/dx/src/com/android/jack/dx/io/instructions/OneRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/OneRegisterDecodedInstruction.java
@@ -22,34 +22,45 @@
  * A decoded Dalvik instruction which has one register argument.
  */
 public final class OneRegisterDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /**
-     * Constructs an instance.
-     */
-    public OneRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public OneRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-    }
+    this.a = a;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 1;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 1;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new OneRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new OneRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/PackedSwitchPayloadDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/PackedSwitchPayloadDecodedInstruction.java
index f2b5049..0b2ee32 100644
--- a/dx/src/com/android/jack/dx/io/instructions/PackedSwitchPayloadDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/PackedSwitchPayloadDecodedInstruction.java
@@ -20,43 +20,44 @@
  * A decoded Dalvik instruction which contains the payload for
  * a {@code packed-switch} instruction.
  */
-public final class PackedSwitchPayloadDecodedInstruction
-        extends DecodedInstruction {
-    /** first key value */
-    private final int firstKey;
+public final class PackedSwitchPayloadDecodedInstruction extends DecodedInstruction {
+  /** first key value */
+  private final int firstKey;
 
-    /**
-     * array of target addresses. These are absolute, not relative,
-     * addresses.
-     */
-    private final int[] targets;
+  /**
+   * array of target addresses. These are absolute, not relative,
+   * addresses.
+   */
+  private final int[] targets;
 
-    /**
-     * Constructs an instance.
-     */
-    public PackedSwitchPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, int firstKey, int[] targets) {
-        super(format, opcode, 0, null, 0, 0L);
+  /**
+   * Constructs an instance.
+   */
+  public PackedSwitchPayloadDecodedInstruction(InstructionCodec format, int opcode, int firstKey,
+      int[] targets) {
+    super(format, opcode, 0, null, 0, 0L);
 
-        this.firstKey = firstKey;
-        this.targets = targets;
-    }
+    this.firstKey = firstKey;
+    this.targets = targets;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 0;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 0;
+  }
 
-    public int getFirstKey() {
-        return firstKey;
-    }
+  public int getFirstKey() {
+    return firstKey;
+  }
 
-    public int[] getTargets() {
-        return targets;
-    }
+  public int[] getTargets() {
+    return targets;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        throw new UnsupportedOperationException("no index in instruction");
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    throw new UnsupportedOperationException("no index in instruction");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/RegisterRangeDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/RegisterRangeDecodedInstruction.java
index 30f1242..eb73d9b 100644
--- a/dx/src/com/android/jack/dx/io/instructions/RegisterRangeDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/RegisterRangeDecodedInstruction.java
@@ -23,38 +23,51 @@
  * "A" start register and a register count).
  */
 public final class RegisterRangeDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /** register count */
-    private final int registerCount;
+  /** register count */
+  private final int registerCount;
 
-    /**
-     * Constructs an instance.
-     */
-    public RegisterRangeDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a, int registerCount) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public RegisterRangeDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a,
+      int registerCount) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-        this.registerCount = registerCount;
-    }
+    this.a = a;
+    this.registerCount = registerCount;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return registerCount;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return registerCount;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new RegisterRangeDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a, registerCount);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new RegisterRangeDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a,
+        registerCount);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeInput.java b/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeInput.java
index c225f83..29e73ce 100644
--- a/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeInput.java
+++ b/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeInput.java
@@ -21,53 +21,56 @@
 /**
  * Implementation of {@code CodeInput} that reads from a {@code short[]}.
  */
-public final class ShortArrayCodeInput extends BaseCodeCursor
-        implements CodeInput {
-    /** source array to read from */
-    private final short[] array;
+public final class ShortArrayCodeInput extends BaseCodeCursor implements CodeInput {
+  /** source array to read from */
+  private final short[] array;
 
-    /**
-     * Constructs an instance.
-     */
-    public ShortArrayCodeInput(short[] array) {
-        if (array == null) {
-            throw new NullPointerException("array == null");
-        }
-
-        this.array = array;
+  /**
+   * Constructs an instance.
+   */
+  public ShortArrayCodeInput(short[] array) {
+    if (array == null) {
+      throw new NullPointerException("array == null");
     }
 
-    /** @inheritDoc */
-    public boolean hasMore() {
-        return cursor() < array.length;
+    this.array = array;
+  }
+
+  /** @inheritDoc */
+  @Override
+  public boolean hasMore() {
+    return cursor() < array.length;
+  }
+
+  /** @inheritDoc */
+  @Override
+  public int read() throws EOFException {
+    try {
+      int value = array[cursor()];
+      advance(1);
+      return value & 0xffff;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      throw new EOFException();
     }
+  }
 
-    /** @inheritDoc */
-    public int read() throws EOFException {
-        try {
-            int value = array[cursor()];
-            advance(1);
-            return value & 0xffff;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            throw new EOFException();
-        }
-    }
+  /** @inheritDoc */
+  @Override
+  public int readInt() throws EOFException {
+    int short0 = read();
+    int short1 = read();
 
-    /** @inheritDoc */
-    public int readInt() throws EOFException {
-        int short0 = read();
-        int short1 = read();
+    return short0 | (short1 << 16);
+  }
 
-        return short0 | (short1 << 16);
-    }
+  /** @inheritDoc */
+  @Override
+  public long readLong() throws EOFException {
+    long short0 = read();
+    long short1 = read();
+    long short2 = read();
+    long short3 = read();
 
-    /** @inheritDoc */
-    public long readLong() throws EOFException {
-        long short0 = read();
-        long short1 = read();
-        long short2 = read();
-        long short3 = read();
-
-        return short0 | (short1 << 16) | (short2 << 32) | (short3 << 48);
-    }
+    return short0 | (short1 << 16) | (short2 << 32) | (short3 << 48);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeOutput.java b/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeOutput.java
index 4de2e71..a1a0cd9 100644
--- a/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeOutput.java
+++ b/dx/src/com/android/jack/dx/io/instructions/ShortArrayCodeOutput.java
@@ -19,128 +19,138 @@
 /**
  * Implementation of {@code CodeOutput} that writes to a {@code short[]}.
  */
-public final class ShortArrayCodeOutput extends BaseCodeCursor
-        implements CodeOutput {
-    /** array to write to */
-    private final short[] array;
+public final class ShortArrayCodeOutput extends BaseCodeCursor implements CodeOutput {
+  /** array to write to */
+  private final short[] array;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param maxSize the maximum number of code units that will be written
-     */
-    public ShortArrayCodeOutput(int maxSize) {
-        if (maxSize < 0) {
-            throw new IllegalArgumentException("maxSize < 0");
-        }
-
-        this.array = new short[maxSize];
+  /**
+   * Constructs an instance.
+   *
+   * @param maxSize the maximum number of code units that will be written
+   */
+  public ShortArrayCodeOutput(int maxSize) {
+    if (maxSize < 0) {
+      throw new IllegalArgumentException("maxSize < 0");
     }
 
-    /**
-     * Gets the array. The returned array contains exactly the data
-     * written (e.g. no leftover space at the end).
-     */
-    public short[] getArray() {
-        int cursor = cursor();
+    this.array = new short[maxSize];
+  }
 
-        if (cursor == array.length) {
-            return array;
-        }
+  /**
+   * Gets the array. The returned array contains exactly the data
+   * written (e.g. no leftover space at the end).
+   */
+  public short[] getArray() {
+    int cursor = cursor();
 
-        short[] result = new short[cursor];
-        System.arraycopy(array, 0, result, 0, cursor);
-        return result;
+    if (cursor == array.length) {
+      return array;
     }
 
-    /** @inheritDoc */
-    public void write(short codeUnit) {
-        array[cursor()] = codeUnit;
-        advance(1);
-    }
+    short[] result = new short[cursor];
+    System.arraycopy(array, 0, result, 0, cursor);
+    return result;
+  }
 
-    /** @inheritDoc */
-    public void write(short u0, short u1) {
-        write(u0);
-        write(u1);
-    }
+  /** @inheritDoc */
+  @Override
+  public void write(short codeUnit) {
+    array[cursor()] = codeUnit;
+    advance(1);
+  }
 
-    /** @inheritDoc */
-    public void write(short u0, short u1, short u2) {
-        write(u0);
-        write(u1);
-        write(u2);
-    }
+  /** @inheritDoc */
+  @Override
+  public void write(short u0, short u1) {
+    write(u0);
+    write(u1);
+  }
 
-    /** @inheritDoc */
-    public void write(short u0, short u1, short u2, short u3) {
-        write(u0);
-        write(u1);
-        write(u2);
-        write(u3);
-    }
+  /** @inheritDoc */
+  @Override
+  public void write(short u0, short u1, short u2) {
+    write(u0);
+    write(u1);
+    write(u2);
+  }
 
-    /** @inheritDoc */
-    public void write(short u0, short u1, short u2, short u3, short u4) {
-        write(u0);
-        write(u1);
-        write(u2);
-        write(u3);
-        write(u4);
-    }
+  /** @inheritDoc */
+  @Override
+  public void write(short u0, short u1, short u2, short u3) {
+    write(u0);
+    write(u1);
+    write(u2);
+    write(u3);
+  }
 
-    /** @inheritDoc */
-    public void writeInt(int value) {
+  /** @inheritDoc */
+  @Override
+  public void write(short u0, short u1, short u2, short u3, short u4) {
+    write(u0);
+    write(u1);
+    write(u2);
+    write(u3);
+    write(u4);
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void writeInt(int value) {
+    write((short) value);
+    write((short) (value >> 16));
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void writeLong(long value) {
+    write((short) value);
+    write((short) (value >> 16));
+    write((short) (value >> 32));
+    write((short) (value >> 48));
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void write(byte[] data) {
+    int value = 0;
+    boolean even = true;
+    for (byte b : data) {
+      if (even) {
+        value = b & 0xff;
+        even = false;
+      } else {
+        value |= b << 8;
         write((short) value);
-        write((short) (value >> 16));
+        even = true;
+      }
     }
 
-    /** @inheritDoc */
-    public void writeLong(long value) {
-        write((short) value);
-        write((short) (value >> 16));
-        write((short) (value >> 32));
-        write((short) (value >> 48));
+    if (!even) {
+      write((short) value);
     }
+  }
 
-    /** @inheritDoc */
-    public void write(byte[] data) {
-        int value = 0;
-        boolean even = true;
-        for (byte b : data) {
-            if (even) {
-                value = b & 0xff;
-                even = false;
-            } else {
-                value |= b << 8;
-                write((short) value);
-                even = true;
-            }
-        }
-
-        if (!even) {
-            write((short) value);
-        }
+  /** @inheritDoc */
+  @Override
+  public void write(short[] data) {
+    for (short unit : data) {
+      write(unit);
     }
+  }
 
-    /** @inheritDoc */
-    public void write(short[] data) {
-        for (short unit : data) {
-            write(unit);
-        }
+  /** @inheritDoc */
+  @Override
+  public void write(int[] data) {
+    for (int i : data) {
+      writeInt(i);
     }
+  }
 
-    /** @inheritDoc */
-    public void write(int[] data) {
-        for (int i : data) {
-            writeInt(i);
-        }
+  /** @inheritDoc */
+  @Override
+  public void write(long[] data) {
+    for (long l : data) {
+      writeLong(l);
     }
-
-    /** @inheritDoc */
-    public void write(long[] data) {
-        for (long l : data) {
-            writeLong(l);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/SparseSwitchPayloadDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/SparseSwitchPayloadDecodedInstruction.java
index 5155976..781c12c 100644
--- a/dx/src/com/android/jack/dx/io/instructions/SparseSwitchPayloadDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/SparseSwitchPayloadDecodedInstruction.java
@@ -20,47 +20,48 @@
  * A decoded Dalvik instruction which contains the payload for
  * a {@code packed-switch} instruction.
  */
-public final class SparseSwitchPayloadDecodedInstruction
-        extends DecodedInstruction {
-    /** array of key values */
-    private final int[] keys;
+public final class SparseSwitchPayloadDecodedInstruction extends DecodedInstruction {
+  /** array of key values */
+  private final int[] keys;
 
-    /**
-     * array of target addresses. These are absolute, not relative,
-     * addresses.
-     */
-    private final int[] targets;
+  /**
+   * array of target addresses. These are absolute, not relative,
+   * addresses.
+   */
+  private final int[] targets;
 
-    /**
-     * Constructs an instance.
-     */
-    public SparseSwitchPayloadDecodedInstruction(InstructionCodec format,
-            int opcode, int[] keys, int[] targets) {
-        super(format, opcode, 0, null, 0, 0L);
+  /**
+   * Constructs an instance.
+   */
+  public SparseSwitchPayloadDecodedInstruction(InstructionCodec format, int opcode, int[] keys,
+      int[] targets) {
+    super(format, opcode, 0, null, 0, 0L);
 
-        if (keys.length != targets.length) {
-            throw new IllegalArgumentException("keys/targets length mismatch");
-        }
-
-        this.keys = keys;
-        this.targets = targets;
+    if (keys.length != targets.length) {
+      throw new IllegalArgumentException("keys/targets length mismatch");
     }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 0;
-    }
+    this.keys = keys;
+    this.targets = targets;
+  }
 
-    public int[] getKeys() {
-        return keys;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 0;
+  }
 
-    public int[] getTargets() {
-        return targets;
-    }
+  public int[] getKeys() {
+    return keys;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        throw new UnsupportedOperationException("no index in instruction");
-    }
+  public int[] getTargets() {
+    return targets;
+  }
+
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    throw new UnsupportedOperationException("no index in instruction");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/ThreeRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/ThreeRegisterDecodedInstruction.java
index 3fe93ac..c80d827 100644
--- a/dx/src/com/android/jack/dx/io/instructions/ThreeRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/ThreeRegisterDecodedInstruction.java
@@ -22,52 +22,69 @@
  * A decoded Dalvik instruction which has three register arguments.
  */
 public final class ThreeRegisterDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /** register argument "B" */
-    private final int b;
+  /** register argument "B" */
+  private final int b;
 
-    /** register argument "C" */
-    private final int c;
+  /** register argument "C" */
+  private final int c;
 
-    /**
-     * Constructs an instance.
-     */
-    public ThreeRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a, int b, int c) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public ThreeRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a,
+      int b,
+      int c) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-        this.b = b;
-        this.c = c;
-    }
+    this.a = a;
+    this.b = b;
+    this.c = c;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 3;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 3;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public int getB() {
-        return b;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getB() {
+    return b;
+  }
 
-    /** @inheritDoc */
-    public int getC() {
-        return c;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getC() {
+    return c;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new ThreeRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a, b, c);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new ThreeRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a,
+        b,
+        c);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/TwoRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/TwoRegisterDecodedInstruction.java
index 6ff4e17..2be0f98 100644
--- a/dx/src/com/android/jack/dx/io/instructions/TwoRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/TwoRegisterDecodedInstruction.java
@@ -22,43 +22,57 @@
  * A decoded Dalvik instruction which has two register arguments.
  */
 public final class TwoRegisterDecodedInstruction extends DecodedInstruction {
-    /** register argument "A" */
-    private final int a;
+  /** register argument "A" */
+  private final int a;
 
-    /** register argument "B" */
-    private final int b;
+  /** register argument "B" */
+  private final int b;
 
-    /**
-     * Constructs an instance.
-     */
-    public TwoRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal,
-            int a, int b) {
-        super(format, opcode, index, indexType, target, literal);
+  /**
+   * Constructs an instance.
+   */
+  public TwoRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal,
+      int a,
+      int b) {
+    super(format, opcode, index, indexType, target, literal);
 
-        this.a = a;
-        this.b = b;
-    }
+    this.a = a;
+    this.b = b;
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 2;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 2;
+  }
 
-    /** @inheritDoc */
-    public int getA() {
-        return a;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getA() {
+    return a;
+  }
 
-    /** @inheritDoc */
-    public int getB() {
-        return b;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getB() {
+    return b;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new TwoRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral(), a, b);
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new TwoRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral(),
+        a,
+        b);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/io/instructions/ZeroRegisterDecodedInstruction.java b/dx/src/com/android/jack/dx/io/instructions/ZeroRegisterDecodedInstruction.java
index 0e69a5e..443b854 100644
--- a/dx/src/com/android/jack/dx/io/instructions/ZeroRegisterDecodedInstruction.java
+++ b/dx/src/com/android/jack/dx/io/instructions/ZeroRegisterDecodedInstruction.java
@@ -22,23 +22,32 @@
  * A decoded Dalvik instruction which has no register arguments.
  */
 public final class ZeroRegisterDecodedInstruction extends DecodedInstruction {
-    /**
-     * Constructs an instance.
-     */
-    public ZeroRegisterDecodedInstruction(InstructionCodec format, int opcode,
-            int index, IndexType indexType, int target, long literal) {
-        super(format, opcode, index, indexType, target, literal);
-    }
+  /**
+   * Constructs an instance.
+   */
+  public ZeroRegisterDecodedInstruction(InstructionCodec format,
+      int opcode,
+      int index,
+      IndexType indexType,
+      int target,
+      long literal) {
+    super(format, opcode, index, indexType, target, literal);
+  }
 
-    /** @inheritDoc */
-    public int getRegisterCount() {
-        return 0;
-    }
+  /** @inheritDoc */
+  @Override
+  public int getRegisterCount() {
+    return 0;
+  }
 
-    /** @inheritDoc */
-    public DecodedInstruction withIndex(int newIndex) {
-        return new ZeroRegisterDecodedInstruction(
-                getFormat(), getOpcode(), newIndex, getIndexType(),
-                getTarget(), getLiteral());
-    }
+  /** @inheritDoc */
+  @Override
+  public DecodedInstruction withIndex(int newIndex) {
+    return new ZeroRegisterDecodedInstruction(getFormat(),
+        getOpcode(),
+        newIndex,
+        getIndexType(),
+        getTarget(),
+        getLiteral());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/merge/CollisionPolicy.java b/dx/src/com/android/jack/dx/merge/CollisionPolicy.java
index f30bf0a..1a883ab 100644
--- a/dx/src/com/android/jack/dx/merge/CollisionPolicy.java
+++ b/dx/src/com/android/jack/dx/merge/CollisionPolicy.java
@@ -21,14 +21,14 @@
  */
 public enum CollisionPolicy {
 
-    /**
-     * Keep the class def from the first dex file and discard the def from the
-     * second dex file. This policy is appropriate for incremental builds.
-     */
-    KEEP_FIRST,
+  /**
+   * Keep the class def from the first dex file and discard the def from the
+   * second dex file. This policy is appropriate for incremental builds.
+   */
+  KEEP_FIRST,
 
-    /**
-     * Forbid collisions. This policy is appropriate for merging libraries.
-     */
-    FAIL
+  /**
+   * Forbid collisions. This policy is appropriate for merging libraries.
+   */
+  FAIL
 }
diff --git a/dx/src/com/android/jack/dx/merge/DexMerger.java b/dx/src/com/android/jack/dx/merge/DexMerger.java
index dad2524..b473a5e 100644
--- a/dx/src/com/android/jack/dx/merge/DexMerger.java
+++ b/dx/src/com/android/jack/dx/merge/DexMerger.java
@@ -40,1047 +40,1070 @@
  * Combine two dex files into one.
  */
 public final class DexMerger {
-    private final DexBuffer dexA;
-    private final DexBuffer dexB;
-    private final CollisionPolicy collisionPolicy;
-    private final WriterSizes writerSizes;
+  private final DexBuffer dexA;
+  private final DexBuffer dexB;
+  private final CollisionPolicy collisionPolicy;
+  private final WriterSizes writerSizes;
 
-    private final DexBuffer dexOut = new DexBuffer();
+  private final DexBuffer dexOut = new DexBuffer();
 
-    private final DexBuffer.Section headerOut;
+  private final DexBuffer.Section headerOut;
 
-    /** All IDs and definitions sections */
-    private final DexBuffer.Section idsDefsOut;
+  /** All IDs and definitions sections */
+  private final DexBuffer.Section idsDefsOut;
 
-    private final DexBuffer.Section mapListOut;
+  private final DexBuffer.Section mapListOut;
 
-    private final DexBuffer.Section typeListOut;
+  private final DexBuffer.Section typeListOut;
 
-    private final DexBuffer.Section classDataOut;
+  private final DexBuffer.Section classDataOut;
 
-    private final DexBuffer.Section codeOut;
+  private final DexBuffer.Section codeOut;
 
-    private final DexBuffer.Section stringDataOut;
+  private final DexBuffer.Section stringDataOut;
 
-    private final DexBuffer.Section debugInfoOut;
+  private final DexBuffer.Section debugInfoOut;
 
-    private final DexBuffer.Section encodedArrayOut;
+  private final DexBuffer.Section encodedArrayOut;
 
-    /** annotations directory on a type */
-    private final DexBuffer.Section annotationsDirectoryOut;
+  /** annotations directory on a type */
+  private final DexBuffer.Section annotationsDirectoryOut;
 
-    /** sets of annotations on a member, parameter or type */
-    private final DexBuffer.Section annotationSetOut;
+  /** sets of annotations on a member, parameter or type */
+  private final DexBuffer.Section annotationSetOut;
 
-    /** parameter lists */
-    private final DexBuffer.Section annotationSetRefListOut;
+  /** parameter lists */
+  private final DexBuffer.Section annotationSetRefListOut;
 
-    /** individual annotations, each containing zero or more fields */
-    private final DexBuffer.Section annotationOut;
+  /** individual annotations, each containing zero or more fields */
+  private final DexBuffer.Section annotationOut;
 
-    private final TableOfContents contentsOut;
+  private final TableOfContents contentsOut;
 
-    private final IndexMap aIndexMap;
-    private final IndexMap bIndexMap;
-    private final InstructionTransformer aInstructionTransformer;
-    private final InstructionTransformer bInstructionTransformer;
+  private final IndexMap aIndexMap;
+  private final IndexMap bIndexMap;
+  private final InstructionTransformer aInstructionTransformer;
+  private final InstructionTransformer bInstructionTransformer;
 
-    /** minimum number of wasted bytes before it's worthwhile to compact the result */
-    private int compactWasteThreshold = 1024 * 1024; // 1MiB
+  /** minimum number of wasted bytes before it's worthwhile to compact the result */
+  private int compactWasteThreshold = 1024 * 1024; // 1MiB
 
-    public DexMerger(DexBuffer dexA, DexBuffer dexB, CollisionPolicy collisionPolicy)
-            throws IOException {
-        this(dexA, dexB, collisionPolicy, new WriterSizes(dexA, dexB));
+  public DexMerger(DexBuffer dexA, DexBuffer dexB, CollisionPolicy collisionPolicy)
+      throws IOException {
+    this(dexA, dexB, collisionPolicy, new WriterSizes(dexA, dexB));
+  }
+
+  private DexMerger(DexBuffer dexA, DexBuffer dexB, CollisionPolicy collisionPolicy,
+      WriterSizes writerSizes) throws IOException {
+    this.dexA = dexA;
+    this.dexB = dexB;
+    this.collisionPolicy = collisionPolicy;
+    this.writerSizes = writerSizes;
+
+    TableOfContents aContents = dexA.getTableOfContents();
+    TableOfContents bContents = dexB.getTableOfContents();
+    aIndexMap = new IndexMap(dexOut, aContents);
+    bIndexMap = new IndexMap(dexOut, bContents);
+    aInstructionTransformer = new InstructionTransformer(aIndexMap);
+    bInstructionTransformer = new InstructionTransformer(bIndexMap);
+
+    headerOut = dexOut.appendSection(writerSizes.header, "header");
+    idsDefsOut = dexOut.appendSection(writerSizes.idsDefs, "ids defs");
+
+    contentsOut = dexOut.getTableOfContents();
+    contentsOut.dataOff = dexOut.getLength();
+
+    contentsOut.mapList.off = dexOut.getLength();
+    contentsOut.mapList.size = 1;
+    mapListOut = dexOut.appendSection(writerSizes.mapList, "map list");
+
+    contentsOut.typeLists.off = dexOut.getLength();
+    typeListOut = dexOut.appendSection(writerSizes.typeList, "type list");
+
+    contentsOut.annotationSetRefLists.off = dexOut.getLength();
+    annotationSetRefListOut =
+        dexOut.appendSection(writerSizes.annotationsSetRefList, "annotation set ref list");
+
+    contentsOut.annotationSets.off = dexOut.getLength();
+    annotationSetOut = dexOut.appendSection(writerSizes.annotationsSet, "annotation sets");
+
+    contentsOut.classDatas.off = dexOut.getLength();
+    classDataOut = dexOut.appendSection(writerSizes.classData, "class data");
+
+    contentsOut.codes.off = dexOut.getLength();
+    codeOut = dexOut.appendSection(writerSizes.code, "code");
+
+    contentsOut.stringDatas.off = dexOut.getLength();
+    stringDataOut = dexOut.appendSection(writerSizes.stringData, "string data");
+
+    contentsOut.debugInfos.off = dexOut.getLength();
+    debugInfoOut = dexOut.appendSection(writerSizes.debugInfo, "debug info");
+
+    contentsOut.annotations.off = dexOut.getLength();
+    annotationOut = dexOut.appendSection(writerSizes.annotation, "annotation");
+
+    contentsOut.encodedArrays.off = dexOut.getLength();
+    encodedArrayOut = dexOut.appendSection(writerSizes.encodedArray, "encoded array");
+
+    contentsOut.annotationsDirectories.off = dexOut.getLength();
+    annotationsDirectoryOut =
+        dexOut.appendSection(writerSizes.annotationsDirectory, "annotations directory");
+
+    dexOut.noMoreSections();
+    contentsOut.dataSize = dexOut.getLength() - contentsOut.dataOff;
+  }
+
+  public void setCompactWasteThreshold(int compactWasteThreshold) {
+    this.compactWasteThreshold = compactWasteThreshold;
+  }
+
+  private DexBuffer mergeDexBuffers() throws IOException {
+    mergeStringIds();
+    mergeTypeIds();
+    mergeTypeLists();
+    mergeProtoIds();
+    mergeFieldIds();
+    mergeMethodIds();
+    mergeAnnotations();
+    unionAnnotationSetsAndDirectories();
+    mergeClassDefs();
+
+    // write the header
+    contentsOut.header.off = 0;
+    contentsOut.header.size = 1;
+    contentsOut.fileSize = dexOut.getLength();
+    contentsOut.computeSizesFromOffsets();
+    contentsOut.writeHeader(headerOut);
+    contentsOut.writeMap(mapListOut);
+
+    // generate and write the hashes
+    new DexHasher().writeHashes(dexOut);
+
+    return dexOut;
+  }
+
+  public DexBuffer merge() throws IOException {
+    long start = System.nanoTime();
+    DexBuffer result = mergeDexBuffers();
+
+    /*
+     * We use pessimistic sizes when merging dex files. If those sizes
+     * result in too many bytes wasted, compact the result. To compact,
+     * simply merge the result with itself.
+     */
+    WriterSizes compactedSizes = new WriterSizes(this);
+    int wastedByteCount = writerSizes.size() - compactedSizes.size();
+    if (wastedByteCount > +compactWasteThreshold) {
+      DexMerger compacter =
+          new DexMerger(dexOut, new DexBuffer(), CollisionPolicy.FAIL, compactedSizes);
+      result = compacter.mergeDexBuffers();
+      System.out.printf("Result compacted from %.1fKiB to %.1fKiB to save %.1fKiB%n",
+          dexOut.getLength() / 1024f, result.getLength() / 1024f, wastedByteCount / 1024f);
     }
 
-    private DexMerger(DexBuffer dexA, DexBuffer dexB, CollisionPolicy collisionPolicy,
-            WriterSizes writerSizes) throws IOException {
-        this.dexA = dexA;
-        this.dexB = dexB;
-        this.collisionPolicy = collisionPolicy;
-        this.writerSizes = writerSizes;
+    long elapsed = System.nanoTime() - start;
+    System.out.printf("Merged dex A (%d defs/%.1fKiB) with dex B "
+        + "(%d defs/%.1fKiB). Result is %d defs/%.1fKiB. Took %.1fs%n",
+        dexA.getTableOfContents().classDefs.size,
+        dexA.getLength() / 1024f,
+        dexB.getTableOfContents().classDefs.size,
+        dexB.getLength() / 1024f,
+        result.getTableOfContents().classDefs.size,
+        result.getLength() / 1024f,
+        elapsed / 1000000000f);
 
-        TableOfContents aContents = dexA.getTableOfContents();
-        TableOfContents bContents = dexB.getTableOfContents();
-        aIndexMap = new IndexMap(dexOut, aContents);
-        bIndexMap = new IndexMap(dexOut, bContents);
-        aInstructionTransformer = new InstructionTransformer(aIndexMap);
-        bInstructionTransformer = new InstructionTransformer(bIndexMap);
+    return result;
+  }
 
-        headerOut = dexOut.appendSection(writerSizes.header, "header");
-        idsDefsOut = dexOut.appendSection(writerSizes.idsDefs, "ids defs");
+  /**
+   * Reads an IDs section of two dex files and writes an IDs section of a
+   * merged dex file. Populates maps from old to new indices in the process.
+   */
+  abstract class IdMerger<T extends Comparable<T>> {
+    private final DexBuffer.Section out;
 
-        contentsOut = dexOut.getTableOfContents();
-        contentsOut.dataOff = dexOut.getLength();
-
-        contentsOut.mapList.off = dexOut.getLength();
-        contentsOut.mapList.size = 1;
-        mapListOut = dexOut.appendSection(writerSizes.mapList, "map list");
-
-        contentsOut.typeLists.off = dexOut.getLength();
-        typeListOut = dexOut.appendSection(writerSizes.typeList, "type list");
-
-        contentsOut.annotationSetRefLists.off = dexOut.getLength();
-        annotationSetRefListOut = dexOut.appendSection(
-                writerSizes.annotationsSetRefList, "annotation set ref list");
-
-        contentsOut.annotationSets.off = dexOut.getLength();
-        annotationSetOut = dexOut.appendSection(writerSizes.annotationsSet, "annotation sets");
-
-        contentsOut.classDatas.off = dexOut.getLength();
-        classDataOut = dexOut.appendSection(writerSizes.classData, "class data");
-
-        contentsOut.codes.off = dexOut.getLength();
-        codeOut = dexOut.appendSection(writerSizes.code, "code");
-
-        contentsOut.stringDatas.off = dexOut.getLength();
-        stringDataOut = dexOut.appendSection(writerSizes.stringData, "string data");
-
-        contentsOut.debugInfos.off = dexOut.getLength();
-        debugInfoOut = dexOut.appendSection(writerSizes.debugInfo, "debug info");
-
-        contentsOut.annotations.off = dexOut.getLength();
-        annotationOut = dexOut.appendSection(writerSizes.annotation, "annotation");
-
-        contentsOut.encodedArrays.off = dexOut.getLength();
-        encodedArrayOut = dexOut.appendSection(writerSizes.encodedArray, "encoded array");
-
-        contentsOut.annotationsDirectories.off = dexOut.getLength();
-        annotationsDirectoryOut = dexOut.appendSection(
-                writerSizes.annotationsDirectory, "annotations directory");
-
-        dexOut.noMoreSections();
-        contentsOut.dataSize = dexOut.getLength() - contentsOut.dataOff;
-    }
-
-    public void setCompactWasteThreshold(int compactWasteThreshold) {
-        this.compactWasteThreshold = compactWasteThreshold;
-    }
-
-    private DexBuffer mergeDexBuffers() throws IOException {
-        mergeStringIds();
-        mergeTypeIds();
-        mergeTypeLists();
-        mergeProtoIds();
-        mergeFieldIds();
-        mergeMethodIds();
-        mergeAnnotations();
-        unionAnnotationSetsAndDirectories();
-        mergeClassDefs();
-
-        // write the header
-        contentsOut.header.off = 0;
-        contentsOut.header.size = 1;
-        contentsOut.fileSize = dexOut.getLength();
-        contentsOut.computeSizesFromOffsets();
-        contentsOut.writeHeader(headerOut);
-        contentsOut.writeMap(mapListOut);
-
-        // generate and write the hashes
-        new DexHasher().writeHashes(dexOut);
-
-        return dexOut;
-    }
-
-    public DexBuffer merge() throws IOException {
-        long start = System.nanoTime();
-        DexBuffer result = mergeDexBuffers();
-
-        /*
-         * We use pessimistic sizes when merging dex files. If those sizes
-         * result in too many bytes wasted, compact the result. To compact,
-         * simply merge the result with itself.
-         */
-        WriterSizes compactedSizes = new WriterSizes(this);
-        int wastedByteCount = writerSizes.size() - compactedSizes.size();
-        if (wastedByteCount >  + compactWasteThreshold) {
-            DexMerger compacter = new DexMerger(
-                    dexOut, new DexBuffer(), CollisionPolicy.FAIL, compactedSizes);
-            result = compacter.mergeDexBuffers();
-            System.out.printf("Result compacted from %.1fKiB to %.1fKiB to save %.1fKiB%n",
-                    dexOut.getLength() / 1024f,
-                    result.getLength() / 1024f,
-                    wastedByteCount / 1024f);
-        }
-
-        long elapsed = System.nanoTime() - start;
-        System.out.printf("Merged dex A (%d defs/%.1fKiB) with dex B "
-                + "(%d defs/%.1fKiB). Result is %d defs/%.1fKiB. Took %.1fs%n",
-                dexA.getTableOfContents().classDefs.size,
-                dexA.getLength() / 1024f,
-                dexB.getTableOfContents().classDefs.size,
-                dexB.getLength() / 1024f,
-                result.getTableOfContents().classDefs.size,
-                result.getLength() / 1024f,
-                elapsed / 1000000000f);
-
-        return result;
+    protected IdMerger(DexBuffer.Section out) {
+      this.out = out;
     }
 
     /**
-     * Reads an IDs section of two dex files and writes an IDs section of a
-     * merged dex file. Populates maps from old to new indices in the process.
+     * Merges already-sorted sections, reading only two values into memory
+     * at a time.
      */
-    abstract class IdMerger<T extends Comparable<T>> {
-        private final DexBuffer.Section out;
+    public final void mergeSorted() {
+      TableOfContents.Section aSection = getSection(dexA.getTableOfContents());
+      TableOfContents.Section bSection = getSection(dexB.getTableOfContents());
+      getSection(contentsOut).off = out.getPosition();
 
-        protected IdMerger(DexBuffer.Section out) {
-            this.out = out;
+      DexBuffer.Section inA = aSection.exists() ? dexA.open(aSection.off) : null;
+      DexBuffer.Section inB = bSection.exists() ? dexB.open(bSection.off) : null;
+      int aOffset = -1;
+      int bOffset = -1;
+      int aIndex = 0;
+      int bIndex = 0;
+      int outCount = 0;
+      T a = null;
+      T b = null;
+
+      while (true) {
+        if (a == null && aIndex < aSection.size) {
+          aOffset = inA.getPosition();
+          a = read(inA, aIndexMap, aIndex);
+        }
+        if (b == null && bIndex < bSection.size) {
+          bOffset = inB.getPosition();
+          b = read(inB, bIndexMap, bIndex);
         }
 
-        /**
-         * Merges already-sorted sections, reading only two values into memory
-         * at a time.
-         */
-        public final void mergeSorted() {
-            TableOfContents.Section aSection = getSection(dexA.getTableOfContents());
-            TableOfContents.Section bSection = getSection(dexB.getTableOfContents());
-            getSection(contentsOut).off = out.getPosition();
-
-            DexBuffer.Section inA = aSection.exists() ? dexA.open(aSection.off) : null;
-            DexBuffer.Section inB = bSection.exists() ? dexB.open(bSection.off) : null;
-            int aOffset = -1;
-            int bOffset = -1;
-            int aIndex = 0;
-            int bIndex = 0;
-            int outCount = 0;
-            T a = null;
-            T b = null;
-
-            while (true) {
-                if (a == null && aIndex < aSection.size) {
-                    aOffset = inA.getPosition();
-                    a = read(inA, aIndexMap, aIndex);
-                }
-                if (b == null && bIndex < bSection.size) {
-                    bOffset = inB.getPosition();
-                    b = read(inB, bIndexMap, bIndex);
-                }
-
-                // Write the smaller of a and b. If they're equal, write only once
-                boolean advanceA;
-                boolean advanceB;
-                if (a != null && b != null) {
-                    int compare = a.compareTo(b);
-                    advanceA = compare <= 0;
-                    advanceB = compare >= 0;
-                } else {
-                    advanceA = (a != null);
-                    advanceB = (b != null);
-                }
-
-                T toWrite = null;
-                if (advanceA) {
-                    toWrite = a;
-                    updateIndex(aOffset, aIndexMap, aIndex++, outCount);
-                    a = null;
-                    aOffset = -1;
-                }
-                if (advanceB) {
-                    toWrite = b;
-                    updateIndex(bOffset, bIndexMap, bIndex++, outCount);
-                    b = null;
-                    bOffset = -1;
-                }
-                if (toWrite == null) {
-                    break; // advanceA == false && advanceB == false
-                }
-                write(toWrite);
-                outCount++;
-            }
-
-            getSection(contentsOut).size = outCount;
-        }
-
-        /**
-         * Merges unsorted sections by reading them completely into memory and
-         * sorting in memory.
-         */
-        public final void mergeUnsorted() {
-            getSection(contentsOut).off = out.getPosition();
-
-            List<UnsortedValue> all = new ArrayList<UnsortedValue>();
-            all.addAll(readUnsortedValues(dexA, aIndexMap));
-            all.addAll(readUnsortedValues(dexB, bIndexMap));
-            Collections.sort(all);
-
-            int outCount = 0;
-            for (int i = 0; i < all.size(); ) {
-                UnsortedValue e1 = all.get(i++);
-                updateIndex(e1.offset, getIndexMap(e1.source), e1.index, outCount - 1);
-
-                while (i < all.size() && e1.compareTo(all.get(i)) == 0) {
-                    UnsortedValue e2 = all.get(i++);
-                    updateIndex(e2.offset, getIndexMap(e2.source), e2.index, outCount - 1);
-                }
-
-                write(e1.value);
-                outCount++;
-            }
-
-            getSection(contentsOut).size = outCount;
-        }
-
-        private List<UnsortedValue> readUnsortedValues(DexBuffer source, IndexMap indexMap) {
-            TableOfContents.Section section = getSection(source.getTableOfContents());
-            if (!section.exists()) {
-                return Collections.emptyList();
-            }
-
-            List<UnsortedValue> result = new ArrayList<UnsortedValue>();
-            DexBuffer.Section in = source.open(section.off);
-            for (int i = 0; i < section.size; i++) {
-                int offset = in.getPosition();
-                T value = read(in, indexMap, 0);
-                result.add(new UnsortedValue(source, indexMap, value, i, offset));
-            }
-            return result;
-        }
-
-        abstract TableOfContents.Section getSection(TableOfContents tableOfContents);
-        abstract T read(DexBuffer.Section in, IndexMap indexMap, int index);
-        abstract void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex);
-        abstract void write(T value);
-
-        class UnsortedValue implements Comparable<UnsortedValue> {
-            final DexBuffer source;
-            final IndexMap indexMap;
-            final T value;
-            final int index;
-            final int offset;
-
-            UnsortedValue(DexBuffer source, IndexMap indexMap, T value, int index, int offset) {
-                this.source = source;
-                this.indexMap = indexMap;
-                this.value = value;
-                this.index = index;
-                this.offset = offset;
-            }
-
-            public int compareTo(UnsortedValue unsortedValue) {
-                return value.compareTo(unsortedValue.value);
-            }
-        }
-    }
-
-    private IndexMap getIndexMap(DexBuffer dexBuffer) {
-        if (dexBuffer == dexA) {
-            return aIndexMap;
-        } else if (dexBuffer == dexB) {
-            return bIndexMap;
+        // Write the smaller of a and b. If they're equal, write only once
+        boolean advanceA;
+        boolean advanceB;
+        if (a != null && b != null) {
+          int compare = a.compareTo(b);
+          advanceA = compare <= 0;
+          advanceB = compare >= 0;
         } else {
-            throw new IllegalArgumentException();
+          advanceA = (a != null);
+          advanceB = (b != null);
         }
-    }
 
-    private void mergeStringIds() {
-        new IdMerger<String>(idsDefsOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.stringIds;
-            }
-
-            @Override String read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return in.readString();
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                indexMap.stringIds[oldIndex] = newIndex;
-            }
-
-            @Override void write(String value) {
-                contentsOut.stringDatas.size++;
-                idsDefsOut.writeInt(stringDataOut.getPosition());
-                stringDataOut.writeStringData(value);
-            }
-        }.mergeSorted();
-    }
-
-    private void mergeTypeIds() {
-        new IdMerger<Integer>(idsDefsOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.typeIds;
-            }
-
-            @Override Integer read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                int stringIndex = in.readInt();
-                return indexMap.adjustString(stringIndex);
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                checkIndex16(newIndex);
-                indexMap.typeIds[oldIndex] = (short) newIndex;
-            }
-
-            @Override void write(Integer value) {
-                idsDefsOut.writeInt(value);
-            }
-        }.mergeSorted();
-    }
-
-    private void mergeTypeLists() {
-        new IdMerger<TypeList>(typeListOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.typeLists;
-            }
-
-            @Override TypeList read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return indexMap.adjustTypeList(in.readTypeList());
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                indexMap.putTypeListOffset(offset, typeListOut.getPosition());
-            }
-
-            @Override void write(TypeList value) {
-                typeListOut.writeTypeList(value);
-            }
-        }.mergeUnsorted();
-    }
-
-    private void mergeProtoIds() {
-        new IdMerger<ProtoId>(idsDefsOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.protoIds;
-            }
-
-            @Override ProtoId read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return indexMap.adjust(in.readProtoId());
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                checkIndex16(newIndex);
-                indexMap.protoIds[oldIndex] = (short) newIndex;
-            }
-
-            @Override void write(ProtoId value) {
-                value.writeTo(idsDefsOut);
-            }
-        }.mergeSorted();
-    }
-
-    private void mergeFieldIds() {
-        new IdMerger<FieldId>(idsDefsOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.fieldIds;
-            }
-
-            @Override FieldId read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return indexMap.adjust(in.readFieldId());
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                checkIndex16(newIndex);
-                indexMap.fieldIds[oldIndex] = (short) newIndex;
-            }
-
-            @Override void write(FieldId value) {
-                value.writeTo(idsDefsOut);
-            }
-        }.mergeSorted();
-    }
-
-    private void mergeMethodIds() {
-        new IdMerger<MethodId>(idsDefsOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.methodIds;
-            }
-
-            @Override MethodId read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return indexMap.adjust(in.readMethodId());
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                checkIndex16(newIndex);
-                indexMap.methodIds[oldIndex] = (short) newIndex;
-            }
-
-            @Override void write(MethodId methodId) {
-                methodId.writeTo(idsDefsOut);
-            }
-        }.mergeSorted();
-    }
-
-    private void mergeAnnotations() {
-        new IdMerger<Annotation>(annotationOut) {
-            @Override TableOfContents.Section getSection(TableOfContents tableOfContents) {
-                return tableOfContents.annotations;
-            }
-
-            @Override Annotation read(DexBuffer.Section in, IndexMap indexMap, int index) {
-                return indexMap.adjust(in.readAnnotation());
-            }
-
-            @Override void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
-                indexMap.putAnnotationOffset(offset, annotationOut.getPosition());
-            }
-
-            @Override void write(Annotation value) {
-                value.writeTo(annotationOut);
-            }
-        }.mergeUnsorted();
-    }
-
-    private void mergeClassDefs() {
-        SortableType[] types = getSortedTypes();
-        contentsOut.classDefs.off = idsDefsOut.getPosition();
-        contentsOut.classDefs.size = types.length;
-
-        for (SortableType type : types) {
-            DexBuffer in = type.getBuffer();
-            IndexMap indexMap = (in == dexA) ? aIndexMap : bIndexMap;
-            transformClassDef(in, type.getClassDef(), indexMap);
+        T toWrite = null;
+        if (advanceA) {
+          toWrite = a;
+          updateIndex(aOffset, aIndexMap, aIndex++, outCount);
+          a = null;
+          aOffset = -1;
         }
+        if (advanceB) {
+          toWrite = b;
+          updateIndex(bOffset, bIndexMap, bIndex++, outCount);
+          b = null;
+          bOffset = -1;
+        }
+        if (toWrite == null) {
+          break; // advanceA == false && advanceB == false
+        }
+        write(toWrite);
+        outCount++;
+      }
+
+      getSection(contentsOut).size = outCount;
     }
 
     /**
-     * Returns the union of classes from both files, sorted in order such that
-     * a class is always preceded by its supertype and implemented interfaces.
+     * Merges unsorted sections by reading them completely into memory and
+     * sorting in memory.
      */
-    private SortableType[] getSortedTypes() {
-        // size is pessimistic; doesn't include arrays
-        SortableType[] sortableTypes = new SortableType[contentsOut.typeIds.size];
-        readSortableTypes(sortableTypes, dexA, aIndexMap);
-        readSortableTypes(sortableTypes, dexB, bIndexMap);
+    public final void mergeUnsorted() {
+      getSection(contentsOut).off = out.getPosition();
 
-        /*
-         * Populate the depths of each sortable type. This makes D iterations
-         * through all N types, where 'D' is the depth of the deepest type. For
-         * example, the deepest class in libcore is Xalan's KeyIterator, which
-         * is 11 types deep.
-         */
-        while (true) {
-            boolean allDone = true;
-            for (SortableType sortableType : sortableTypes) {
-                if (sortableType != null && !sortableType.isDepthAssigned()) {
-                    allDone &= sortableType.tryAssignDepth(sortableTypes);
-                }
-            }
-            if (allDone) {
-                break;
-            }
+      List<UnsortedValue> all = new ArrayList<UnsortedValue>();
+      all.addAll(readUnsortedValues(dexA, aIndexMap));
+      all.addAll(readUnsortedValues(dexB, bIndexMap));
+      Collections.sort(all);
+
+      int outCount = 0;
+      for (int i = 0; i < all.size();) {
+        UnsortedValue e1 = all.get(i++);
+        updateIndex(e1.offset, getIndexMap(e1.source), e1.index, outCount - 1);
+
+        while (i < all.size() && e1.compareTo(all.get(i)) == 0) {
+          UnsortedValue e2 = all.get(i++);
+          updateIndex(e2.offset, getIndexMap(e2.source), e2.index, outCount - 1);
         }
 
-        // Now that all types have depth information, the result can be sorted
-        Arrays.sort(sortableTypes, SortableType.NULLS_LAST_ORDER);
+        write(e1.value);
+        outCount++;
+      }
 
-        // Strip nulls from the end
-        int firstNull = Arrays.asList(sortableTypes).indexOf(null);
-        return firstNull != -1
-                ? Arrays.copyOfRange(sortableTypes, 0, firstNull)
-                : sortableTypes;
+      getSection(contentsOut).size = outCount;
     }
 
+    private List<UnsortedValue> readUnsortedValues(DexBuffer source, IndexMap indexMap) {
+      TableOfContents.Section section = getSection(source.getTableOfContents());
+      if (!section.exists()) {
+        return Collections.emptyList();
+      }
+
+      List<UnsortedValue> result = new ArrayList<UnsortedValue>();
+      DexBuffer.Section in = source.open(section.off);
+      for (int i = 0; i < section.size; i++) {
+        int offset = in.getPosition();
+        T value = read(in, indexMap, 0);
+        result.add(new UnsortedValue(source, indexMap, value, i, offset));
+      }
+      return result;
+    }
+
+    abstract TableOfContents.Section getSection(TableOfContents tableOfContents);
+
+    abstract T read(DexBuffer.Section in, IndexMap indexMap, int index);
+
+    abstract void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex);
+
+    abstract void write(T value);
+
+    class UnsortedValue implements Comparable<UnsortedValue> {
+      final DexBuffer source;
+      final IndexMap indexMap;
+      final T value;
+      final int index;
+      final int offset;
+
+      UnsortedValue(DexBuffer source, IndexMap indexMap, T value, int index, int offset) {
+        this.source = source;
+        this.indexMap = indexMap;
+        this.value = value;
+        this.index = index;
+        this.offset = offset;
+      }
+
+      @Override
+      public int compareTo(UnsortedValue unsortedValue) {
+        return value.compareTo(unsortedValue.value);
+      }
+    }
+  }
+
+  private IndexMap getIndexMap(DexBuffer dexBuffer) {
+    if (dexBuffer == dexA) {
+      return aIndexMap;
+    } else if (dexBuffer == dexB) {
+      return bIndexMap;
+    } else {
+      throw new IllegalArgumentException();
+    }
+  }
+
+  private void mergeStringIds() {
+    new IdMerger<String>(idsDefsOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.stringIds;
+      }
+
+      @Override
+      String read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return in.readString();
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        indexMap.stringIds[oldIndex] = newIndex;
+      }
+
+      @Override
+      void write(String value) {
+        contentsOut.stringDatas.size++;
+        idsDefsOut.writeInt(stringDataOut.getPosition());
+        stringDataOut.writeStringData(value);
+      }
+    }.mergeSorted();
+  }
+
+  private void mergeTypeIds() {
+    new IdMerger<Integer>(idsDefsOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.typeIds;
+      }
+
+      @Override
+      Integer read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        int stringIndex = in.readInt();
+        return indexMap.adjustString(stringIndex);
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        checkIndex16(newIndex);
+        indexMap.typeIds[oldIndex] = (short) newIndex;
+      }
+
+      @Override
+      void write(Integer value) {
+        idsDefsOut.writeInt(value);
+      }
+    }.mergeSorted();
+  }
+
+  private void mergeTypeLists() {
+    new IdMerger<TypeList>(typeListOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.typeLists;
+      }
+
+      @Override
+      TypeList read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return indexMap.adjustTypeList(in.readTypeList());
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        indexMap.putTypeListOffset(offset, typeListOut.getPosition());
+      }
+
+      @Override
+      void write(TypeList value) {
+        typeListOut.writeTypeList(value);
+      }
+    }.mergeUnsorted();
+  }
+
+  private void mergeProtoIds() {
+    new IdMerger<ProtoId>(idsDefsOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.protoIds;
+      }
+
+      @Override
+      ProtoId read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return indexMap.adjust(in.readProtoId());
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        checkIndex16(newIndex);
+        indexMap.protoIds[oldIndex] = (short) newIndex;
+      }
+
+      @Override
+      void write(ProtoId value) {
+        value.writeTo(idsDefsOut);
+      }
+    }.mergeSorted();
+  }
+
+  private void mergeFieldIds() {
+    new IdMerger<FieldId>(idsDefsOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.fieldIds;
+      }
+
+      @Override
+      FieldId read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return indexMap.adjust(in.readFieldId());
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        checkIndex16(newIndex);
+        indexMap.fieldIds[oldIndex] = (short) newIndex;
+      }
+
+      @Override
+      void write(FieldId value) {
+        value.writeTo(idsDefsOut);
+      }
+    }.mergeSorted();
+  }
+
+  private void mergeMethodIds() {
+    new IdMerger<MethodId>(idsDefsOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.methodIds;
+      }
+
+      @Override
+      MethodId read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return indexMap.adjust(in.readMethodId());
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        checkIndex16(newIndex);
+        indexMap.methodIds[oldIndex] = (short) newIndex;
+      }
+
+      @Override
+      void write(MethodId methodId) {
+        methodId.writeTo(idsDefsOut);
+      }
+    }.mergeSorted();
+  }
+
+  private void mergeAnnotations() {
+    new IdMerger<Annotation>(annotationOut) {
+      @Override
+      TableOfContents.Section getSection(TableOfContents tableOfContents) {
+        return tableOfContents.annotations;
+      }
+
+      @Override
+      Annotation read(DexBuffer.Section in, IndexMap indexMap, int index) {
+        return indexMap.adjust(in.readAnnotation());
+      }
+
+      @Override
+      void updateIndex(int offset, IndexMap indexMap, int oldIndex, int newIndex) {
+        indexMap.putAnnotationOffset(offset, annotationOut.getPosition());
+      }
+
+      @Override
+      void write(Annotation value) {
+        value.writeTo(annotationOut);
+      }
+    }.mergeUnsorted();
+  }
+
+  private void mergeClassDefs() {
+    SortableType[] types = getSortedTypes();
+    contentsOut.classDefs.off = idsDefsOut.getPosition();
+    contentsOut.classDefs.size = types.length;
+
+    for (SortableType type : types) {
+      DexBuffer in = type.getBuffer();
+      IndexMap indexMap = (in == dexA) ? aIndexMap : bIndexMap;
+      transformClassDef(in, type.getClassDef(), indexMap);
+    }
+  }
+
+  /**
+   * Returns the union of classes from both files, sorted in order such that
+   * a class is always preceded by its supertype and implemented interfaces.
+   */
+  private SortableType[] getSortedTypes() {
+    // size is pessimistic; doesn't include arrays
+    SortableType[] sortableTypes = new SortableType[contentsOut.typeIds.size];
+    readSortableTypes(sortableTypes, dexA, aIndexMap);
+    readSortableTypes(sortableTypes, dexB, bIndexMap);
+
+    /*
+     * Populate the depths of each sortable type. This makes D iterations
+     * through all N types, where 'D' is the depth of the deepest type. For
+     * example, the deepest class in libcore is Xalan's KeyIterator, which
+     * is 11 types deep.
+     */
+    while (true) {
+      boolean allDone = true;
+      for (SortableType sortableType : sortableTypes) {
+        if (sortableType != null && !sortableType.isDepthAssigned()) {
+          allDone &= sortableType.tryAssignDepth(sortableTypes);
+        }
+      }
+      if (allDone) {
+        break;
+      }
+    }
+
+    // Now that all types have depth information, the result can be sorted
+    Arrays.sort(sortableTypes, SortableType.NULLS_LAST_ORDER);
+
+    // Strip nulls from the end
+    int firstNull = Arrays.asList(sortableTypes).indexOf(null);
+    return firstNull != -1 ? Arrays.copyOfRange(sortableTypes, 0, firstNull) : sortableTypes;
+  }
+
+  /**
+   * Reads just enough data on each class so that we can sort it and then find
+   * it later.
+   */
+  private void readSortableTypes(SortableType[] sortableTypes, DexBuffer buffer,
+      IndexMap indexMap) {
+    for (ClassDef classDef : buffer.classDefs()) {
+      SortableType sortableType = indexMap.adjust(new SortableType(buffer, classDef));
+      int t = sortableType.getTypeIndex();
+      if (sortableTypes[t] == null) {
+        sortableTypes[t] = sortableType;
+      } else if (collisionPolicy != CollisionPolicy.KEEP_FIRST) {
+        throw new DexException(
+            "Multiple dex files define " + buffer.typeNames().get(classDef.getTypeIndex()));
+      }
+    }
+  }
+
+  /**
+   * Copy annotation sets from each input to the output.
+   *
+   * TODO(dx team): this may write multiple copies of the same annotation set.
+   * We should shrink the output by merging rather than unioning
+   */
+  private void unionAnnotationSetsAndDirectories() {
+    transformAnnotationSets(dexA, aIndexMap);
+    transformAnnotationSets(dexB, bIndexMap);
+    transformAnnotationDirectories(dexA, aIndexMap);
+    transformAnnotationDirectories(dexB, bIndexMap);
+    transformStaticValues(dexA, aIndexMap);
+    transformStaticValues(dexB, bIndexMap);
+  }
+
+  private void transformAnnotationSets(DexBuffer in, IndexMap indexMap) {
+    TableOfContents.Section section = in.getTableOfContents().annotationSets;
+    if (section.exists()) {
+      DexBuffer.Section setIn = in.open(section.off);
+      for (int i = 0; i < section.size; i++) {
+        transformAnnotationSet(indexMap, setIn);
+      }
+    }
+  }
+
+  private void checkIndex16(int index) {
+    if (index > Character.MAX_VALUE || index < 0) {
+      throw new DexException("Too many IDs in dex");
+    }
+  }
+
+  private void transformAnnotationDirectories(DexBuffer in, IndexMap indexMap) {
+    TableOfContents.Section section = in.getTableOfContents().annotationsDirectories;
+    if (section.exists()) {
+      DexBuffer.Section directoryIn = in.open(section.off);
+      for (int i = 0; i < section.size; i++) {
+        transformAnnotationDirectory(in, directoryIn, indexMap);
+      }
+    }
+  }
+
+  private void transformStaticValues(DexBuffer in, IndexMap indexMap) {
+    TableOfContents.Section section = in.getTableOfContents().encodedArrays;
+    if (section.exists()) {
+      DexBuffer.Section staticValuesIn = in.open(section.off);
+      for (int i = 0; i < section.size; i++) {
+        transformStaticValues(staticValuesIn, indexMap);
+      }
+    }
+  }
+
+  /**
+   * Reads a class_def_item beginning at {@code in} and writes the index and
+   * data.
+   */
+  private void transformClassDef(DexBuffer in, ClassDef classDef, IndexMap indexMap) {
+    idsDefsOut.assertFourByteAligned();
+    idsDefsOut.writeInt(classDef.getTypeIndex());
+    idsDefsOut.writeInt(classDef.getAccessFlags());
+    idsDefsOut.writeInt(classDef.getSupertypeIndex());
+    idsDefsOut.writeInt(classDef.getInterfacesOffset());
+
+    int sourceFileIndex = indexMap.adjustString(classDef.getSourceFileIndex());
+    idsDefsOut.writeInt(sourceFileIndex);
+
+    int annotationsOff = classDef.getAnnotationsOffset();
+    idsDefsOut.writeInt(indexMap.adjustAnnotationDirectory(annotationsOff));
+
+    int classDataOff = classDef.getClassDataOffset();
+    if (classDataOff == 0) {
+      idsDefsOut.writeInt(0);
+    } else {
+      idsDefsOut.writeInt(classDataOut.getPosition());
+      ClassData classData = in.readClassData(classDef);
+      transformClassData(in, classData, indexMap);
+    }
+
+    int staticValuesOff = classDef.getStaticValuesOffset();
+    idsDefsOut.writeInt(indexMap.adjustStaticValues(staticValuesOff));
+  }
+
+  /**
+   * Transform all annotations on a class.
+   */
+  private void transformAnnotationDirectory(DexBuffer in, DexBuffer.Section directoryIn,
+      IndexMap indexMap) {
+    contentsOut.annotationsDirectories.size++;
+    annotationsDirectoryOut.assertFourByteAligned();
+    indexMap.putAnnotationDirectoryOffset(directoryIn.getPosition(),
+        annotationsDirectoryOut.getPosition());
+
+    int classAnnotationsOffset = indexMap.adjustAnnotationSet(directoryIn.readInt());
+    annotationsDirectoryOut.writeInt(classAnnotationsOffset);
+
+    int fieldsSize = directoryIn.readInt();
+    annotationsDirectoryOut.writeInt(fieldsSize);
+
+    int methodsSize = directoryIn.readInt();
+    annotationsDirectoryOut.writeInt(methodsSize);
+
+    int parameterListSize = directoryIn.readInt();
+    annotationsDirectoryOut.writeInt(parameterListSize);
+
+    for (int i = 0; i < fieldsSize; i++) {
+      // field index
+      annotationsDirectoryOut.writeInt(indexMap.adjustField(directoryIn.readInt()));
+
+      // annotations offset
+      annotationsDirectoryOut.writeInt(indexMap.adjustAnnotationSet(directoryIn.readInt()));
+    }
+
+    for (int i = 0; i < methodsSize; i++) {
+      // method index
+      annotationsDirectoryOut.writeInt(indexMap.adjustMethod(directoryIn.readInt()));
+
+      // annotation set offset
+      annotationsDirectoryOut.writeInt(indexMap.adjustAnnotationSet(directoryIn.readInt()));
+    }
+
+    for (int i = 0; i < parameterListSize; i++) {
+      contentsOut.annotationSetRefLists.size++;
+      annotationSetRefListOut.assertFourByteAligned();
+
+      // method index
+      annotationsDirectoryOut.writeInt(indexMap.adjustMethod(directoryIn.readInt()));
+
+      // annotations offset
+      annotationsDirectoryOut.writeInt(annotationSetRefListOut.getPosition());
+      DexBuffer.Section refListIn = in.open(directoryIn.readInt());
+
+      // parameters
+      int parameterCount = refListIn.readInt();
+      annotationSetRefListOut.writeInt(parameterCount);
+      for (int p = 0; p < parameterCount; p++) {
+        annotationSetRefListOut.writeInt(indexMap.adjustAnnotationSet(refListIn.readInt()));
+      }
+    }
+  }
+
+  /**
+   * Transform all annotations on a single type, member or parameter.
+   */
+  private void transformAnnotationSet(IndexMap indexMap, DexBuffer.Section setIn) {
+    contentsOut.annotationSets.size++;
+    annotationSetOut.assertFourByteAligned();
+    indexMap.putAnnotationSetOffset(setIn.getPosition(), annotationSetOut.getPosition());
+
+    int size = setIn.readInt();
+    annotationSetOut.writeInt(size);
+
+    for (int j = 0; j < size; j++) {
+      annotationSetOut.writeInt(indexMap.adjustAnnotation(setIn.readInt()));
+    }
+  }
+
+  private void transformClassData(DexBuffer in, ClassData classData, IndexMap indexMap) {
+    contentsOut.classDatas.size++;
+
+    ClassData.Field[] staticFields = classData.getStaticFields();
+    ClassData.Field[] instanceFields = classData.getInstanceFields();
+    ClassData.Method[] directMethods = classData.getDirectMethods();
+    ClassData.Method[] virtualMethods = classData.getVirtualMethods();
+
+    classDataOut.writeUleb128(staticFields.length);
+    classDataOut.writeUleb128(instanceFields.length);
+    classDataOut.writeUleb128(directMethods.length);
+    classDataOut.writeUleb128(virtualMethods.length);
+
+    transformFields(indexMap, staticFields);
+    transformFields(indexMap, instanceFields);
+    transformMethods(in, indexMap, directMethods);
+    transformMethods(in, indexMap, virtualMethods);
+  }
+
+  private void transformFields(IndexMap indexMap, ClassData.Field[] fields) {
+    int lastOutFieldIndex = 0;
+    for (ClassData.Field field : fields) {
+      int outFieldIndex = indexMap.adjustField(field.getFieldIndex());
+      classDataOut.writeUleb128(outFieldIndex - lastOutFieldIndex);
+      lastOutFieldIndex = outFieldIndex;
+      classDataOut.writeUleb128(field.getAccessFlags());
+    }
+  }
+
+  private void transformMethods(DexBuffer in, IndexMap indexMap, ClassData.Method[] methods) {
+    int lastOutMethodIndex = 0;
+    for (ClassData.Method method : methods) {
+      int outMethodIndex = indexMap.adjustMethod(method.getMethodIndex());
+      classDataOut.writeUleb128(outMethodIndex - lastOutMethodIndex);
+      lastOutMethodIndex = outMethodIndex;
+
+      classDataOut.writeUleb128(method.getAccessFlags());
+
+      if (method.getCodeOffset() == 0) {
+        classDataOut.writeUleb128(0);
+      } else {
+        codeOut.alignToFourBytes();
+        classDataOut.writeUleb128(codeOut.getPosition());
+        transformCode(in, in.readCode(method), indexMap);
+      }
+    }
+  }
+
+  private void transformCode(DexBuffer in, Code code, IndexMap indexMap) {
+    contentsOut.codes.size++;
+    codeOut.assertFourByteAligned();
+
+    codeOut.writeUnsignedShort(code.getRegistersSize());
+    codeOut.writeUnsignedShort(code.getInsSize());
+    codeOut.writeUnsignedShort(code.getOutsSize());
+
+    Code.Try[] tries = code.getTries();
+    Code.CatchHandler[] catchHandlers = code.getCatchHandlers();
+    codeOut.writeUnsignedShort(tries.length);
+
+    int debugInfoOffset = code.getDebugInfoOffset();
+    if (debugInfoOffset != 0) {
+      codeOut.writeInt(debugInfoOut.getPosition());
+      transformDebugInfoItem(in.open(debugInfoOffset), indexMap);
+    } else {
+      codeOut.writeInt(0);
+    }
+
+    short[] instructions = code.getInstructions();
+    InstructionTransformer transformer =
+        (in == dexA) ? aInstructionTransformer : bInstructionTransformer;
+    short[] newInstructions = transformer.transform(instructions);
+    codeOut.writeInt(newInstructions.length);
+    codeOut.write(newInstructions);
+
+    if (tries.length > 0) {
+      if (newInstructions.length % 2 == 1) {
+        codeOut.writeShort((short) 0); // padding
+      }
+
+      /*
+       * We can't write the tries until we've written the catch handlers.
+       * Unfortunately they're in the opposite order in the dex file so we
+       * need to transform them out-of-order.
+       */
+      DexBuffer.Section triesSection = dexOut.open(codeOut.getPosition());
+      codeOut.skip(tries.length * SizeOf.TRY_ITEM);
+      int[] offsets = transformCatchHandlers(indexMap, catchHandlers);
+      transformTries(triesSection, tries, offsets);
+    }
+  }
+
+  /**
+   * Writes the catch handlers to {@code codeOut} and returns their indices.
+   */
+  private int[] transformCatchHandlers(IndexMap indexMap, Code.CatchHandler[] catchHandlers) {
+    int baseOffset = codeOut.getPosition();
+    codeOut.writeUleb128(catchHandlers.length);
+    int[] offsets = new int[catchHandlers.length];
+    for (int i = 0; i < catchHandlers.length; i++) {
+      offsets[i] = codeOut.getPosition() - baseOffset;
+      transformEncodedCatchHandler(catchHandlers[i], indexMap);
+    }
+    return offsets;
+  }
+
+  private void transformTries(DexBuffer.Section out, Code.Try[] tries, int[] catchHandlerOffsets) {
+    for (Code.Try tryItem : tries) {
+      out.writeInt(tryItem.getStartAddress());
+      out.writeUnsignedShort(tryItem.getInstructionCount());
+      out.writeUnsignedShort(catchHandlerOffsets[tryItem.getCatchHandlerIndex()]);
+    }
+  }
+
+  private static final byte DBG_END_SEQUENCE = 0x00;
+  private static final byte DBG_ADVANCE_PC = 0x01;
+  private static final byte DBG_ADVANCE_LINE = 0x02;
+  private static final byte DBG_START_LOCAL = 0x03;
+  private static final byte DBG_START_LOCAL_EXTENDED = 0x04;
+  private static final byte DBG_END_LOCAL = 0x05;
+  private static final byte DBG_RESTART_LOCAL = 0x06;
+  private static final byte DBG_SET_PROLOGUE_END = 0x07;
+  private static final byte DBG_SET_EPILOGUE_BEGIN = 0x08;
+  private static final byte DBG_SET_FILE = 0x09;
+
+  private void transformDebugInfoItem(DexBuffer.Section in, IndexMap indexMap) {
+    contentsOut.debugInfos.size++;
+    int lineStart = in.readUleb128();
+    debugInfoOut.writeUleb128(lineStart);
+
+    int parametersSize = in.readUleb128();
+    debugInfoOut.writeUleb128(parametersSize);
+
+    for (int p = 0; p < parametersSize; p++) {
+      int parameterName = in.readUleb128p1();
+      debugInfoOut.writeUleb128p1(indexMap.adjustString(parameterName));
+    }
+
+    int addrDiff; // uleb128   address delta.
+    int lineDiff; // sleb128   line delta.
+    int registerNum; // uleb128   register number.
+    int nameIndex; // uleb128p1 string index.    Needs indexMap adjustment.
+    int typeIndex; // uleb128p1 type index.      Needs indexMap adjustment.
+    int sigIndex; // uleb128p1 string index.    Needs indexMap adjustment.
+
+    while (true) {
+      int opcode = in.readByte();
+      debugInfoOut.writeByte(opcode);
+
+      switch (opcode) {
+        case DBG_END_SEQUENCE:
+          return;
+
+        case DBG_ADVANCE_PC:
+          addrDiff = in.readUleb128();
+          debugInfoOut.writeUleb128(addrDiff);
+          break;
+
+        case DBG_ADVANCE_LINE:
+          lineDiff = in.readSleb128();
+          debugInfoOut.writeSleb128(lineDiff);
+          break;
+
+        case DBG_START_LOCAL:
+        case DBG_START_LOCAL_EXTENDED:
+          registerNum = in.readUleb128();
+          debugInfoOut.writeUleb128(registerNum);
+          nameIndex = in.readUleb128p1();
+          debugInfoOut.writeUleb128p1(indexMap.adjustString(nameIndex));
+          typeIndex = in.readUleb128p1();
+          debugInfoOut.writeUleb128p1(indexMap.adjustType(typeIndex));
+          if (opcode == DBG_START_LOCAL_EXTENDED) {
+            sigIndex = in.readUleb128p1();
+            debugInfoOut.writeUleb128p1(indexMap.adjustString(sigIndex));
+          }
+          break;
+
+        case DBG_END_LOCAL:
+        case DBG_RESTART_LOCAL:
+          registerNum = in.readUleb128();
+          debugInfoOut.writeUleb128(registerNum);
+          break;
+
+        case DBG_SET_FILE:
+          nameIndex = in.readUleb128p1();
+          debugInfoOut.writeUleb128p1(indexMap.adjustString(nameIndex));
+          break;
+
+        case DBG_SET_PROLOGUE_END:
+        case DBG_SET_EPILOGUE_BEGIN:
+        default:
+          break;
+      }
+    }
+  }
+
+  private void transformEncodedCatchHandler(Code.CatchHandler catchHandler, IndexMap indexMap) {
+    int catchAllAddress = catchHandler.getCatchAllAddress();
+    int[] typeIndexes = catchHandler.getTypeIndexes();
+    int[] addresses = catchHandler.getAddresses();
+
+    if (catchAllAddress != -1) {
+      codeOut.writeSleb128(-typeIndexes.length);
+    } else {
+      codeOut.writeSleb128(typeIndexes.length);
+    }
+
+    for (int i = 0; i < typeIndexes.length; i++) {
+      codeOut.writeUleb128(indexMap.adjustType(typeIndexes[i]));
+      codeOut.writeUleb128(addresses[i]);
+    }
+
+    if (catchAllAddress != -1) {
+      codeOut.writeUleb128(catchAllAddress);
+    }
+  }
+
+  private void transformStaticValues(DexBuffer.Section in, IndexMap indexMap) {
+    contentsOut.encodedArrays.size++;
+    indexMap.putStaticValuesOffset(in.getPosition(), encodedArrayOut.getPosition());
+    indexMap.adjustEncodedArray(in.readEncodedArray()).writeTo(encodedArrayOut);
+  }
+
+  /**
+   * Byte counts for the sections written when creating a dex. Target sizes
+   * are defined in one of two ways:
+   * <ul>
+   * <li>By pessimistically guessing how large the union of dex files will be.
+   *     We're pessimistic because we can't predict the amount of duplication
+   *     between dex files, nor can we predict the length of ULEB-encoded
+   *     offsets or indices.
+   * <li>By exactly measuring an existing dex.
+   * </ul>
+   */
+  private static class WriterSizes {
+    private int header = SizeOf.HEADER_ITEM;
+    private int idsDefs;
+    private int mapList;
+    private int typeList;
+    private int classData;
+    private int code;
+    private int stringData;
+    private int debugInfo;
+    private int encodedArray;
+    private int annotationsDirectory;
+    private int annotationsSet;
+    private int annotationsSetRefList;
+    private int annotation;
+
     /**
-     * Reads just enough data on each class so that we can sort it and then find
-     * it later.
+     * Compute sizes for merging a and b.
      */
-    private void readSortableTypes(SortableType[] sortableTypes, DexBuffer buffer,
-            IndexMap indexMap) {
-        for (ClassDef classDef : buffer.classDefs()) {
-            SortableType sortableType = indexMap.adjust(new SortableType(buffer, classDef));
-            int t = sortableType.getTypeIndex();
-            if (sortableTypes[t] == null) {
-                sortableTypes[t] = sortableType;
-            } else if (collisionPolicy != CollisionPolicy.KEEP_FIRST) {
-                throw new DexException("Multiple dex files define "
-                        + buffer.typeNames().get(classDef.getTypeIndex()));
-            }
-        }
+    public WriterSizes(DexBuffer a, DexBuffer b) {
+      plus(a.getTableOfContents(), false);
+      plus(b.getTableOfContents(), false);
     }
 
-    /**
-     * Copy annotation sets from each input to the output.
-     *
-     * TODO: this may write multiple copies of the same annotation set.
-     * We should shrink the output by merging rather than unioning
-     */
-    private void unionAnnotationSetsAndDirectories() {
-        transformAnnotationSets(dexA, aIndexMap);
-        transformAnnotationSets(dexB, bIndexMap);
-        transformAnnotationDirectories(dexA, aIndexMap);
-        transformAnnotationDirectories(dexB, bIndexMap);
-        transformStaticValues(dexA, aIndexMap);
-        transformStaticValues(dexB, bIndexMap);
+    public WriterSizes(DexMerger dexMerger) {
+      header = dexMerger.headerOut.used();
+      idsDefs = dexMerger.idsDefsOut.used();
+      mapList = dexMerger.mapListOut.used();
+      typeList = dexMerger.typeListOut.used();
+      classData = dexMerger.classDataOut.used();
+      code = dexMerger.codeOut.used();
+      stringData = dexMerger.stringDataOut.used();
+      debugInfo = dexMerger.debugInfoOut.used();
+      encodedArray = dexMerger.encodedArrayOut.used();
+      annotationsDirectory = dexMerger.annotationsDirectoryOut.used();
+      annotationsSet = dexMerger.annotationSetOut.used();
+      annotationsSetRefList = dexMerger.annotationSetRefListOut.used();
+      annotation = dexMerger.annotationOut.used();
     }
 
-    private void transformAnnotationSets(DexBuffer in, IndexMap indexMap) {
-        TableOfContents.Section section = in.getTableOfContents().annotationSets;
-        if (section.exists()) {
-            DexBuffer.Section setIn = in.open(section.off);
-            for (int i = 0; i < section.size; i++) {
-                transformAnnotationSet(indexMap, setIn);
-            }
-        }
+    public void plus(TableOfContents contents, boolean exact) {
+      idsDefs += contents.stringIds.size * SizeOf.STRING_ID_ITEM + contents.typeIds.size
+          * SizeOf.TYPE_ID_ITEM + contents.protoIds.size * SizeOf.PROTO_ID_ITEM
+          + contents.fieldIds.size * SizeOf.MEMBER_ID_ITEM + contents.methodIds.size
+          * SizeOf.MEMBER_ID_ITEM + contents.classDefs.size * SizeOf.CLASS_DEF_ITEM;
+      mapList = SizeOf.UINT + (contents.sections.length * SizeOf.MAP_ITEM);
+      typeList += contents.typeLists.byteCount;
+      stringData += contents.stringDatas.byteCount;
+      annotationsDirectory += contents.annotationsDirectories.byteCount;
+      annotationsSet += contents.annotationSets.byteCount;
+      annotationsSetRefList += contents.annotationSetRefLists.byteCount;
+
+      if (exact) {
+        code += contents.codes.byteCount;
+        classData += contents.classDatas.byteCount;
+        encodedArray += contents.encodedArrays.byteCount;
+        annotation += contents.annotations.byteCount;
+        debugInfo += contents.debugInfos.byteCount;
+      } else {
+        // at most 1/4 of the bytes in a code section are uleb/sleb
+        code += (int) Math.ceil(contents.codes.byteCount * 1.25);
+        // at most 1/3 of the bytes in a class data section are uleb/sleb
+        classData += (int) Math.ceil(contents.classDatas.byteCount * 1.34);
+        // all of the bytes in an encoding arrays section may be uleb/sleb
+        encodedArray += contents.encodedArrays.byteCount * 2;
+        // all of the bytes in an annotations section may be uleb/sleb
+        annotation += (int) Math.ceil(contents.annotations.byteCount * 2);
+        // all of the bytes in a debug info section may be uleb/sleb
+        debugInfo += contents.debugInfos.byteCount * 2;
+      }
+
+      typeList = DexBuffer.fourByteAlign(typeList);
+      code = DexBuffer.fourByteAlign(code);
     }
 
-    private void checkIndex16(int index) {
-        if (index > Character.MAX_VALUE || index < 0) {
-            throw new DexException("Too many IDs in dex");
-        }
+    public int size() {
+      return header + idsDefs + mapList + typeList + classData + code + stringData + debugInfo
+          + encodedArray + annotationsDirectory + annotationsSet + annotationsSetRefList
+          + annotation;
+    }
+  }
+
+  public static void main(String[] args) throws IOException {
+    if (args.length < 2) {
+      printUsage();
+      return;
     }
 
-    private void transformAnnotationDirectories(DexBuffer in, IndexMap indexMap) {
-        TableOfContents.Section section = in.getTableOfContents().annotationsDirectories;
-        if (section.exists()) {
-            DexBuffer.Section directoryIn = in.open(section.off);
-            for (int i = 0; i < section.size; i++) {
-                transformAnnotationDirectory(in, directoryIn, indexMap);
-            }
-        }
+    DexBuffer merged = new DexBuffer(new File(args[1]));
+    for (int i = 2; i < args.length; i++) {
+      DexBuffer toMerge = new DexBuffer(new File(args[i]));
+      merged = new DexMerger(merged, toMerge, CollisionPolicy.KEEP_FIRST).merge();
     }
+    merged.writeTo(new File(args[0]));
+  }
 
-    private void transformStaticValues(DexBuffer in, IndexMap indexMap) {
-        TableOfContents.Section section = in.getTableOfContents().encodedArrays;
-        if (section.exists()) {
-            DexBuffer.Section staticValuesIn = in.open(section.off);
-            for (int i = 0; i < section.size; i++) {
-                transformStaticValues(staticValuesIn, indexMap);
-            }
-        }
-    }
-
-    /**
-     * Reads a class_def_item beginning at {@code in} and writes the index and
-     * data.
-     */
-    private void transformClassDef(DexBuffer in, ClassDef classDef, IndexMap indexMap) {
-        idsDefsOut.assertFourByteAligned();
-        idsDefsOut.writeInt(classDef.getTypeIndex());
-        idsDefsOut.writeInt(classDef.getAccessFlags());
-        idsDefsOut.writeInt(classDef.getSupertypeIndex());
-        idsDefsOut.writeInt(classDef.getInterfacesOffset());
-
-        int sourceFileIndex = indexMap.adjustString(classDef.getSourceFileIndex());
-        idsDefsOut.writeInt(sourceFileIndex);
-
-        int annotationsOff = classDef.getAnnotationsOffset();
-        idsDefsOut.writeInt(indexMap.adjustAnnotationDirectory(annotationsOff));
-
-        int classDataOff = classDef.getClassDataOffset();
-        if (classDataOff == 0) {
-            idsDefsOut.writeInt(0);
-        } else {
-            idsDefsOut.writeInt(classDataOut.getPosition());
-            ClassData classData = in.readClassData(classDef);
-            transformClassData(in, classData, indexMap);
-        }
-
-        int staticValuesOff = classDef.getStaticValuesOffset();
-        idsDefsOut.writeInt(indexMap.adjustStaticValues(staticValuesOff));
-    }
-
-    /**
-     * Transform all annotations on a class.
-     */
-    private void transformAnnotationDirectory(
-            DexBuffer in, DexBuffer.Section directoryIn, IndexMap indexMap) {
-        contentsOut.annotationsDirectories.size++;
-        annotationsDirectoryOut.assertFourByteAligned();
-        indexMap.putAnnotationDirectoryOffset(
-                directoryIn.getPosition(), annotationsDirectoryOut.getPosition());
-
-        int classAnnotationsOffset = indexMap.adjustAnnotationSet(directoryIn.readInt());
-        annotationsDirectoryOut.writeInt(classAnnotationsOffset);
-
-        int fieldsSize = directoryIn.readInt();
-        annotationsDirectoryOut.writeInt(fieldsSize);
-
-        int methodsSize = directoryIn.readInt();
-        annotationsDirectoryOut.writeInt(methodsSize);
-
-        int parameterListSize = directoryIn.readInt();
-        annotationsDirectoryOut.writeInt(parameterListSize);
-
-        for (int i = 0; i < fieldsSize; i++) {
-            // field index
-            annotationsDirectoryOut.writeInt(indexMap.adjustField(directoryIn.readInt()));
-
-            // annotations offset
-            annotationsDirectoryOut.writeInt(indexMap.adjustAnnotationSet(directoryIn.readInt()));
-        }
-
-        for (int i = 0; i < methodsSize; i++) {
-            // method index
-            annotationsDirectoryOut.writeInt(indexMap.adjustMethod(directoryIn.readInt()));
-
-            // annotation set offset
-            annotationsDirectoryOut.writeInt(
-                    indexMap.adjustAnnotationSet(directoryIn.readInt()));
-        }
-
-        for (int i = 0; i < parameterListSize; i++) {
-            contentsOut.annotationSetRefLists.size++;
-            annotationSetRefListOut.assertFourByteAligned();
-
-            // method index
-            annotationsDirectoryOut.writeInt(indexMap.adjustMethod(directoryIn.readInt()));
-
-            // annotations offset
-            annotationsDirectoryOut.writeInt(annotationSetRefListOut.getPosition());
-            DexBuffer.Section refListIn = in.open(directoryIn.readInt());
-
-            // parameters
-            int parameterCount = refListIn.readInt();
-            annotationSetRefListOut.writeInt(parameterCount);
-            for (int p = 0; p < parameterCount; p++) {
-                annotationSetRefListOut.writeInt(indexMap.adjustAnnotationSet(refListIn.readInt()));
-            }
-        }
-    }
-
-    /**
-     * Transform all annotations on a single type, member or parameter.
-     */
-    private void transformAnnotationSet(IndexMap indexMap, DexBuffer.Section setIn) {
-        contentsOut.annotationSets.size++;
-        annotationSetOut.assertFourByteAligned();
-        indexMap.putAnnotationSetOffset(setIn.getPosition(), annotationSetOut.getPosition());
-
-        int size = setIn.readInt();
-        annotationSetOut.writeInt(size);
-
-        for (int j = 0; j < size; j++) {
-            annotationSetOut.writeInt(indexMap.adjustAnnotation(setIn.readInt()));
-        }
-    }
-
-    private void transformClassData(DexBuffer in, ClassData classData, IndexMap indexMap) {
-        contentsOut.classDatas.size++;
-
-        ClassData.Field[] staticFields = classData.getStaticFields();
-        ClassData.Field[] instanceFields = classData.getInstanceFields();
-        ClassData.Method[] directMethods = classData.getDirectMethods();
-        ClassData.Method[] virtualMethods = classData.getVirtualMethods();
-
-        classDataOut.writeUleb128(staticFields.length);
-        classDataOut.writeUleb128(instanceFields.length);
-        classDataOut.writeUleb128(directMethods.length);
-        classDataOut.writeUleb128(virtualMethods.length);
-
-        transformFields(indexMap, staticFields);
-        transformFields(indexMap, instanceFields);
-        transformMethods(in, indexMap, directMethods);
-        transformMethods(in, indexMap, virtualMethods);
-    }
-
-    private void transformFields(IndexMap indexMap, ClassData.Field[] fields) {
-        int lastOutFieldIndex = 0;
-        for (ClassData.Field field : fields) {
-            int outFieldIndex = indexMap.adjustField(field.getFieldIndex());
-            classDataOut.writeUleb128(outFieldIndex - lastOutFieldIndex);
-            lastOutFieldIndex = outFieldIndex;
-            classDataOut.writeUleb128(field.getAccessFlags());
-        }
-    }
-
-    private void transformMethods(DexBuffer in, IndexMap indexMap, ClassData.Method[] methods) {
-        int lastOutMethodIndex = 0;
-        for (ClassData.Method method : methods) {
-            int outMethodIndex = indexMap.adjustMethod(method.getMethodIndex());
-            classDataOut.writeUleb128(outMethodIndex - lastOutMethodIndex);
-            lastOutMethodIndex = outMethodIndex;
-
-            classDataOut.writeUleb128(method.getAccessFlags());
-
-            if (method.getCodeOffset() == 0) {
-                classDataOut.writeUleb128(0);
-            } else {
-                codeOut.alignToFourBytes();
-                classDataOut.writeUleb128(codeOut.getPosition());
-                transformCode(in, in.readCode(method), indexMap);
-            }
-        }
-    }
-
-    private void transformCode(DexBuffer in, Code code, IndexMap indexMap) {
-        contentsOut.codes.size++;
-        codeOut.assertFourByteAligned();
-
-        codeOut.writeUnsignedShort(code.getRegistersSize());
-        codeOut.writeUnsignedShort(code.getInsSize());
-        codeOut.writeUnsignedShort(code.getOutsSize());
-
-        Code.Try[] tries = code.getTries();
-        Code.CatchHandler[] catchHandlers = code.getCatchHandlers();
-        codeOut.writeUnsignedShort(tries.length);
-
-        int debugInfoOffset = code.getDebugInfoOffset();
-        if (debugInfoOffset != 0) {
-            codeOut.writeInt(debugInfoOut.getPosition());
-            transformDebugInfoItem(in.open(debugInfoOffset), indexMap);
-        } else {
-            codeOut.writeInt(0);
-        }
-
-        short[] instructions = code.getInstructions();
-        InstructionTransformer transformer = (in == dexA)
-                ? aInstructionTransformer
-                : bInstructionTransformer;
-        short[] newInstructions = transformer.transform(instructions);
-        codeOut.writeInt(newInstructions.length);
-        codeOut.write(newInstructions);
-
-        if (tries.length > 0) {
-            if (newInstructions.length % 2 == 1) {
-                codeOut.writeShort((short) 0); // padding
-            }
-
-            /*
-             * We can't write the tries until we've written the catch handlers.
-             * Unfortunately they're in the opposite order in the dex file so we
-             * need to transform them out-of-order.
-             */
-            DexBuffer.Section triesSection = dexOut.open(codeOut.getPosition());
-            codeOut.skip(tries.length * SizeOf.TRY_ITEM);
-            int[] offsets = transformCatchHandlers(indexMap, catchHandlers);
-            transformTries(triesSection, tries, offsets);
-        }
-    }
-
-    /**
-     * Writes the catch handlers to {@code codeOut} and returns their indices.
-     */
-    private int[] transformCatchHandlers(IndexMap indexMap, Code.CatchHandler[] catchHandlers) {
-        int baseOffset = codeOut.getPosition();
-        codeOut.writeUleb128(catchHandlers.length);
-        int[] offsets = new int[catchHandlers.length];
-        for (int i = 0; i < catchHandlers.length; i++) {
-            offsets[i] = codeOut.getPosition() - baseOffset;
-            transformEncodedCatchHandler(catchHandlers[i], indexMap);
-        }
-        return offsets;
-    }
-
-    private void transformTries(DexBuffer.Section out, Code.Try[] tries,
-            int[] catchHandlerOffsets) {
-        for (Code.Try tryItem : tries) {
-            out.writeInt(tryItem.getStartAddress());
-            out.writeUnsignedShort(tryItem.getInstructionCount());
-            out.writeUnsignedShort(catchHandlerOffsets[tryItem.getCatchHandlerIndex()]);
-        }
-    }
-
-    private static final byte DBG_END_SEQUENCE = 0x00;
-    private static final byte DBG_ADVANCE_PC = 0x01;
-    private static final byte DBG_ADVANCE_LINE = 0x02;
-    private static final byte DBG_START_LOCAL = 0x03;
-    private static final byte DBG_START_LOCAL_EXTENDED = 0x04;
-    private static final byte DBG_END_LOCAL = 0x05;
-    private static final byte DBG_RESTART_LOCAL = 0x06;
-    private static final byte DBG_SET_PROLOGUE_END = 0x07;
-    private static final byte DBG_SET_EPILOGUE_BEGIN = 0x08;
-    private static final byte DBG_SET_FILE = 0x09;
-
-    private void transformDebugInfoItem(DexBuffer.Section in, IndexMap indexMap) {
-        contentsOut.debugInfos.size++;
-        int lineStart = in.readUleb128();
-        debugInfoOut.writeUleb128(lineStart);
-
-        int parametersSize = in.readUleb128();
-        debugInfoOut.writeUleb128(parametersSize);
-
-        for (int p = 0; p < parametersSize; p++) {
-            int parameterName = in.readUleb128p1();
-            debugInfoOut.writeUleb128p1(indexMap.adjustString(parameterName));
-        }
-
-        int addrDiff;    // uleb128   address delta.
-        int lineDiff;    // sleb128   line delta.
-        int registerNum; // uleb128   register number.
-        int nameIndex;   // uleb128p1 string index.    Needs indexMap adjustment.
-        int typeIndex;   // uleb128p1 type index.      Needs indexMap adjustment.
-        int sigIndex;    // uleb128p1 string index.    Needs indexMap adjustment.
-
-        while (true) {
-            int opcode = in.readByte();
-            debugInfoOut.writeByte(opcode);
-
-            switch (opcode) {
-            case DBG_END_SEQUENCE:
-                return;
-
-            case DBG_ADVANCE_PC:
-                addrDiff = in.readUleb128();
-                debugInfoOut.writeUleb128(addrDiff);
-                break;
-
-            case DBG_ADVANCE_LINE:
-                lineDiff = in.readSleb128();
-                debugInfoOut.writeSleb128(lineDiff);
-                break;
-
-            case DBG_START_LOCAL:
-            case DBG_START_LOCAL_EXTENDED:
-                registerNum = in.readUleb128();
-                debugInfoOut.writeUleb128(registerNum);
-                nameIndex = in.readUleb128p1();
-                debugInfoOut.writeUleb128p1(indexMap.adjustString(nameIndex));
-                typeIndex = in.readUleb128p1();
-                debugInfoOut.writeUleb128p1(indexMap.adjustType(typeIndex));
-                if (opcode == DBG_START_LOCAL_EXTENDED) {
-                    sigIndex = in.readUleb128p1();
-                    debugInfoOut.writeUleb128p1(indexMap.adjustString(sigIndex));
-                }
-                break;
-
-            case DBG_END_LOCAL:
-            case DBG_RESTART_LOCAL:
-                registerNum = in.readUleb128();
-                debugInfoOut.writeUleb128(registerNum);
-                break;
-
-            case DBG_SET_FILE:
-                nameIndex = in.readUleb128p1();
-                debugInfoOut.writeUleb128p1(indexMap.adjustString(nameIndex));
-                break;
-
-            case DBG_SET_PROLOGUE_END:
-            case DBG_SET_EPILOGUE_BEGIN:
-            default:
-                break;
-            }
-        }
-    }
-
-    private void transformEncodedCatchHandler(Code.CatchHandler catchHandler, IndexMap indexMap) {
-        int catchAllAddress = catchHandler.getCatchAllAddress();
-        int[] typeIndexes = catchHandler.getTypeIndexes();
-        int[] addresses = catchHandler.getAddresses();
-
-        if (catchAllAddress != -1) {
-            codeOut.writeSleb128(-typeIndexes.length);
-        } else {
-            codeOut.writeSleb128(typeIndexes.length);
-        }
-
-        for (int i = 0; i < typeIndexes.length; i++) {
-            codeOut.writeUleb128(indexMap.adjustType(typeIndexes[i]));
-            codeOut.writeUleb128(addresses[i]);
-        }
-
-        if (catchAllAddress != -1) {
-            codeOut.writeUleb128(catchAllAddress);
-        }
-    }
-
-    private void transformStaticValues(DexBuffer.Section in, IndexMap indexMap) {
-        contentsOut.encodedArrays.size++;
-        indexMap.putStaticValuesOffset(in.getPosition(), encodedArrayOut.getPosition());
-        indexMap.adjustEncodedArray(in.readEncodedArray()).writeTo(encodedArrayOut);
-    }
-
-    /**
-     * Byte counts for the sections written when creating a dex. Target sizes
-     * are defined in one of two ways:
-     * <ul>
-     * <li>By pessimistically guessing how large the union of dex files will be.
-     *     We're pessimistic because we can't predict the amount of duplication
-     *     between dex files, nor can we predict the length of ULEB-encoded
-     *     offsets or indices.
-     * <li>By exactly measuring an existing dex.
-     * </ul>
-     */
-    private static class WriterSizes {
-        private int header = SizeOf.HEADER_ITEM;
-        private int idsDefs;
-        private int mapList;
-        private int typeList;
-        private int classData;
-        private int code;
-        private int stringData;
-        private int debugInfo;
-        private int encodedArray;
-        private int annotationsDirectory;
-        private int annotationsSet;
-        private int annotationsSetRefList;
-        private int annotation;
-
-        /**
-         * Compute sizes for merging a and b.
-         */
-        public WriterSizes(DexBuffer a, DexBuffer b) {
-            plus(a.getTableOfContents(), false);
-            plus(b.getTableOfContents(), false);
-        }
-
-        public WriterSizes(DexMerger dexMerger) {
-            header = dexMerger.headerOut.used();
-            idsDefs = dexMerger.idsDefsOut.used();
-            mapList = dexMerger.mapListOut.used();
-            typeList = dexMerger.typeListOut.used();
-            classData = dexMerger.classDataOut.used();
-            code = dexMerger.codeOut.used();
-            stringData = dexMerger.stringDataOut.used();
-            debugInfo = dexMerger.debugInfoOut.used();
-            encodedArray = dexMerger.encodedArrayOut.used();
-            annotationsDirectory = dexMerger.annotationsDirectoryOut.used();
-            annotationsSet = dexMerger.annotationSetOut.used();
-            annotationsSetRefList = dexMerger.annotationSetRefListOut.used();
-            annotation = dexMerger.annotationOut.used();
-        }
-
-        public void plus(TableOfContents contents, boolean exact) {
-            idsDefs += contents.stringIds.size * SizeOf.STRING_ID_ITEM
-                    + contents.typeIds.size * SizeOf.TYPE_ID_ITEM
-                    + contents.protoIds.size * SizeOf.PROTO_ID_ITEM
-                    + contents.fieldIds.size * SizeOf.MEMBER_ID_ITEM
-                    + contents.methodIds.size * SizeOf.MEMBER_ID_ITEM
-                    + contents.classDefs.size * SizeOf.CLASS_DEF_ITEM;
-            mapList = SizeOf.UINT + (contents.sections.length * SizeOf.MAP_ITEM);
-            typeList += contents.typeLists.byteCount;
-            stringData += contents.stringDatas.byteCount;
-            annotationsDirectory += contents.annotationsDirectories.byteCount;
-            annotationsSet += contents.annotationSets.byteCount;
-            annotationsSetRefList += contents.annotationSetRefLists.byteCount;
-
-            if (exact) {
-                code += contents.codes.byteCount;
-                classData += contents.classDatas.byteCount;
-                encodedArray += contents.encodedArrays.byteCount;
-                annotation += contents.annotations.byteCount;
-                debugInfo += contents.debugInfos.byteCount;
-            } else {
-                // at most 1/4 of the bytes in a code section are uleb/sleb
-                code += (int) Math.ceil(contents.codes.byteCount * 1.25);
-                // at most 1/3 of the bytes in a class data section are uleb/sleb
-                classData += (int) Math.ceil(contents.classDatas.byteCount * 1.34);
-                // all of the bytes in an encoding arrays section may be uleb/sleb
-                encodedArray += contents.encodedArrays.byteCount * 2;
-                // all of the bytes in an annotations section may be uleb/sleb
-                annotation += (int) Math.ceil(contents.annotations.byteCount * 2);
-                // all of the bytes in a debug info section may be uleb/sleb
-                debugInfo += contents.debugInfos.byteCount * 2;
-            }
-
-            typeList = DexBuffer.fourByteAlign(typeList);
-            code = DexBuffer.fourByteAlign(code);
-        }
-
-        public int size() {
-            return header + idsDefs + mapList + typeList + classData + code + stringData + debugInfo
-                    + encodedArray + annotationsDirectory + annotationsSet + annotationsSetRefList
-                    + annotation;
-        }
-    }
-
-    public static void main(String[] args) throws IOException {
-        if (args.length < 2) {
-            printUsage();
-            return;
-        }
-
-        DexBuffer merged = new DexBuffer(new File(args[1]));
-        for (int i = 2; i < args.length; i++) {
-            DexBuffer toMerge = new DexBuffer(new File(args[i]));
-            merged = new DexMerger(merged, toMerge, CollisionPolicy.KEEP_FIRST).merge();
-        }
-        merged.writeTo(new File(args[0]));
-    }
-
-    private static void printUsage() {
-        System.out.println("Usage: DexMerger <out.dex> <a.dex> <b.dex> ...");
-        System.out.println();
-        System.out.println(
-            "If a class is defined in several dex, the class found in the first dex will be used.");
-    }
+  private static void printUsage() {
+    System.out.println("Usage: DexMerger <out.dex> <a.dex> <b.dex> ...");
+    System.out.println();
+    System.out.println(
+        "If a class is defined in several dex, the class found in the first dex will be used.");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/merge/IndexMap.java b/dx/src/com/android/jack/dx/merge/IndexMap.java
index 37cd30e..59904f3 100644
--- a/dx/src/com/android/jack/dx/merge/IndexMap.java
+++ b/dx/src/com/android/jack/dx/merge/IndexMap.java
@@ -39,269 +39,281 @@
  * {@code strings[5]}.
  */
 public final class IndexMap {
-    private final DexBuffer target;
-    public final int[] stringIds;
-    public final short[] typeIds;
-    public final short[] protoIds;
-    public final short[] fieldIds;
-    public final short[] methodIds;
-    private final HashMap<Integer, Integer> typeListOffsets;
-    private final HashMap<Integer, Integer> annotationOffsets;
-    private final HashMap<Integer, Integer> annotationSetOffsets;
-    private final HashMap<Integer, Integer> annotationDirectoryOffsets;
-    private final HashMap<Integer, Integer> staticValuesOffsets;
+  private final DexBuffer target;
+  public final int[] stringIds;
+  public final short[] typeIds;
+  public final short[] protoIds;
+  public final short[] fieldIds;
+  public final short[] methodIds;
+  private final HashMap<Integer, Integer> typeListOffsets;
+  private final HashMap<Integer, Integer> annotationOffsets;
+  private final HashMap<Integer, Integer> annotationSetOffsets;
+  private final HashMap<Integer, Integer> annotationDirectoryOffsets;
+  private final HashMap<Integer, Integer> staticValuesOffsets;
 
-    public IndexMap(DexBuffer target, TableOfContents tableOfContents) {
-        this.target = target;
-        this.stringIds = new int[tableOfContents.stringIds.size];
-        this.typeIds = new short[tableOfContents.typeIds.size];
-        this.protoIds = new short[tableOfContents.protoIds.size];
-        this.fieldIds = new short[tableOfContents.fieldIds.size];
-        this.methodIds = new short[tableOfContents.methodIds.size];
-        this.typeListOffsets = new HashMap<Integer, Integer>();
-        this.annotationOffsets = new HashMap<Integer, Integer>();
-        this.annotationSetOffsets = new HashMap<Integer, Integer>();
-        this.annotationDirectoryOffsets = new HashMap<Integer, Integer>();
-        this.staticValuesOffsets = new HashMap<Integer, Integer>();
+  public IndexMap(DexBuffer target, TableOfContents tableOfContents) {
+    this.target = target;
+    this.stringIds = new int[tableOfContents.stringIds.size];
+    this.typeIds = new short[tableOfContents.typeIds.size];
+    this.protoIds = new short[tableOfContents.protoIds.size];
+    this.fieldIds = new short[tableOfContents.fieldIds.size];
+    this.methodIds = new short[tableOfContents.methodIds.size];
+    this.typeListOffsets = new HashMap<Integer, Integer>();
+    this.annotationOffsets = new HashMap<Integer, Integer>();
+    this.annotationSetOffsets = new HashMap<Integer, Integer>();
+    this.annotationDirectoryOffsets = new HashMap<Integer, Integer>();
+    this.staticValuesOffsets = new HashMap<Integer, Integer>();
 
-        /*
-         * A type list, annotation set, annotation directory, or static value at
-         * offset 0 is always empty. Always map offset 0 to 0.
-         */
-        this.typeListOffsets.put(0, 0);
-        this.annotationSetOffsets.put(0, 0);
-        this.annotationDirectoryOffsets.put(0, 0);
-        this.staticValuesOffsets.put(0, 0);
-    }
-
-    public void putTypeListOffset(int oldOffset, int newOffset) {
-        if (oldOffset <= 0 || newOffset <= 0) {
-            throw new IllegalArgumentException();
-        }
-        typeListOffsets.put(oldOffset, newOffset);
-    }
-
-    public void putAnnotationOffset(int oldOffset, int newOffset) {
-        if (oldOffset <= 0 || newOffset <= 0) {
-            throw new IllegalArgumentException();
-        }
-        annotationOffsets.put(oldOffset, newOffset);
-    }
-
-    public void putAnnotationSetOffset(int oldOffset, int newOffset) {
-        if (oldOffset <= 0 || newOffset <= 0) {
-            throw new IllegalArgumentException();
-        }
-        annotationSetOffsets.put(oldOffset, newOffset);
-    }
-
-    public void putAnnotationDirectoryOffset(int oldOffset, int newOffset) {
-        if (oldOffset <= 0 || newOffset <= 0) {
-            throw new IllegalArgumentException();
-        }
-        annotationDirectoryOffsets.put(oldOffset, newOffset);
-    }
-
-    public void putStaticValuesOffset(int oldOffset, int newOffset) {
-        if (oldOffset <= 0 || newOffset <= 0) {
-            throw new IllegalArgumentException();
-        }
-        staticValuesOffsets.put(oldOffset, newOffset);
-    }
-
-    public int adjustString(int stringIndex) {
-        return stringIndex == ClassDef.NO_INDEX ? ClassDef.NO_INDEX : stringIds[stringIndex];
-    }
-
-    public int adjustType(int typeIndex) {
-        return (typeIndex == ClassDef.NO_INDEX) ? ClassDef.NO_INDEX : (typeIds[typeIndex] & 0xffff);
-    }
-
-    public TypeList adjustTypeList(TypeList typeList) {
-        if (typeList == TypeList.EMPTY) {
-            return typeList;
-        }
-        short[] types = typeList.getTypes().clone();
-        for (int i = 0; i < types.length; i++) {
-            types[i] = (short) adjustType(types[i]);
-        }
-        return new TypeList(target, types);
-    }
-
-    public int adjustProto(int protoIndex) {
-        return protoIds[protoIndex] & 0xffff;
-    }
-
-    public int adjustField(int fieldIndex) {
-        return fieldIds[fieldIndex] & 0xffff;
-    }
-
-    public int adjustMethod(int methodIndex) {
-        return methodIds[methodIndex] & 0xffff;
-    }
-
-    public int adjustTypeListOffset(int typeListOffset) {
-        return typeListOffsets.get(typeListOffset);
-    }
-
-    public int adjustAnnotation(int annotationOffset) {
-        return annotationOffsets.get(annotationOffset);
-    }
-
-    public int adjustAnnotationSet(int annotationSetOffset) {
-        return annotationSetOffsets.get(annotationSetOffset);
-    }
-
-    public int adjustAnnotationDirectory(int annotationDirectoryOffset) {
-        return annotationDirectoryOffsets.get(annotationDirectoryOffset);
-    }
-
-    public int adjustStaticValues(int staticValuesOffset) {
-        return staticValuesOffsets.get(staticValuesOffset);
-    }
-
-    public MethodId adjust(MethodId methodId) {
-        return new MethodId(target,
-                adjustType(methodId.getDeclaringClassIndex()),
-                adjustProto(methodId.getProtoIndex()),
-                adjustString(methodId.getNameIndex()));
-    }
-
-    public FieldId adjust(FieldId fieldId) {
-        return new FieldId(target,
-                adjustType(fieldId.getDeclaringClassIndex()),
-                adjustType(fieldId.getTypeIndex()),
-                adjustString(fieldId.getNameIndex()));
-
-    }
-
-    public ProtoId adjust(ProtoId protoId) {
-        return new ProtoId(target,
-                adjustString(protoId.getShortyIndex()),
-                adjustType(protoId.getReturnTypeIndex()),
-                adjustTypeListOffset(protoId.getParametersOffset()));
-    }
-
-    public ClassDef adjust(ClassDef classDef) {
-        return new ClassDef(target, classDef.getOffset(), adjustType(classDef.getTypeIndex()),
-                classDef.getAccessFlags(), adjustType(classDef.getSupertypeIndex()),
-                adjustTypeListOffset(classDef.getInterfacesOffset()), classDef.getSourceFileIndex(),
-                classDef.getAnnotationsOffset(), classDef.getClassDataOffset(),
-                classDef.getStaticValuesOffset());
-    }
-
-    public SortableType adjust(SortableType sortableType) {
-        return new SortableType(sortableType.getBuffer(), adjust(sortableType.getClassDef()));
-    }
-
-    public EncodedValue adjustEncodedValue(EncodedValue encodedValue) {
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(32);
-        new EncodedValueTransformer(encodedValue, out).readValue();
-        return new EncodedValue(out.toByteArray());
-    }
-
-    public EncodedValue adjustEncodedArray(EncodedValue encodedArray) {
-        ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(32);
-        new EncodedValueTransformer(encodedArray, out).readArray();
-        return new EncodedValue(out.toByteArray());
-    }
-
-    public Annotation adjust(Annotation annotation) {
-        int[] names = annotation.getNames().clone();
-        EncodedValue[] values = annotation.getValues().clone();
-        for (int i = 0; i < names.length; i++) {
-            names[i] = adjustString(names[i]);
-            values[i] = adjustEncodedValue(values[i]);
-        }
-        return new Annotation(target, annotation.getVisibility(),
-                adjustType(annotation.getTypeIndex()), names, values);
-    }
-
-    /**
-     * Adjust an encoded value or array.
+    /*
+     * A type list, annotation set, annotation directory, or static value at
+     * offset 0 is always empty. Always map offset 0 to 0.
      */
-    private final class EncodedValueTransformer extends EncodedValueReader {
-        private final ByteOutput out;
+    this.typeListOffsets.put(0, 0);
+    this.annotationSetOffsets.put(0, 0);
+    this.annotationDirectoryOffsets.put(0, 0);
+    this.staticValuesOffsets.put(0, 0);
+  }
 
-        public EncodedValueTransformer(EncodedValue encodedValue, ByteOutput out) {
-            super(encodedValue);
-            this.out = out;
-        }
-
-        protected void visitArray(int size) {
-            Leb128Utils.writeUnsignedLeb128(out, size);
-        }
-
-        protected void visitAnnotation(int typeIndex, int size) {
-            Leb128Utils.writeUnsignedLeb128(out, adjustType(typeIndex));
-            Leb128Utils.writeUnsignedLeb128(out, size);
-        }
-
-        protected void visitAnnotationName(int index) {
-            Leb128Utils.writeUnsignedLeb128(out, adjustString(index));
-        }
-
-        protected void visitPrimitive(int argAndType, int type, int arg, int size) {
-            out.writeByte(argAndType);
-            copyBytes(in, out, size);
-        }
-
-        protected void visitString(int type, int index) {
-            writeTypeAndSizeAndIndex(type, adjustString(index));
-        }
-
-        protected void visitType(int type, int index) {
-            writeTypeAndSizeAndIndex(type, adjustType(index));
-        }
-
-        protected void visitField(int type, int index) {
-            writeTypeAndSizeAndIndex(type, adjustField(index));
-        }
-
-        protected void visitMethod(int type, int index) {
-            writeTypeAndSizeAndIndex(type, adjustMethod(index));
-        }
-
-        protected void visitArrayValue(int argAndType) {
-            out.writeByte(argAndType);
-        }
-
-        protected void visitAnnotationValue(int argAndType) {
-            out.writeByte(argAndType);
-        }
-
-        protected void visitEncodedBoolean(int argAndType) {
-            out.writeByte(argAndType);
-        }
-
-        protected void visitEncodedNull(int argAndType) {
-            out.writeByte(argAndType);
-        }
-
-        private void writeTypeAndSizeAndIndex(int type, int index) {
-            int byteCount;
-            if (Unsigned.compare(index, 0xff) <= 0) {
-                byteCount = 1;
-            } else if (Unsigned.compare(index, 0xffff) <= 0) {
-                byteCount = 2;
-            } else if (Unsigned.compare(index, 0xffffff) <= 0) {
-                byteCount = 3;
-            } else {
-                byteCount = 4;
-            }
-            int argAndType = ((byteCount - 1) << 5) | type;
-            out.writeByte(argAndType);
-
-            for (int i = 0; i < byteCount; i++) {
-                out.writeByte(index & 0xff);
-                index >>>= 8;
-            }
-        }
-
-        private void copyBytes(ByteInput in, ByteOutput out, int size) {
-            for (int i = 0; i < size; i++) {
-                out.writeByte(in.readByte());
-            }
-        }
+  public void putTypeListOffset(int oldOffset, int newOffset) {
+    if (oldOffset <= 0 || newOffset <= 0) {
+      throw new IllegalArgumentException();
     }
+    typeListOffsets.put(oldOffset, newOffset);
+  }
+
+  public void putAnnotationOffset(int oldOffset, int newOffset) {
+    if (oldOffset <= 0 || newOffset <= 0) {
+      throw new IllegalArgumentException();
+    }
+    annotationOffsets.put(oldOffset, newOffset);
+  }
+
+  public void putAnnotationSetOffset(int oldOffset, int newOffset) {
+    if (oldOffset <= 0 || newOffset <= 0) {
+      throw new IllegalArgumentException();
+    }
+    annotationSetOffsets.put(oldOffset, newOffset);
+  }
+
+  public void putAnnotationDirectoryOffset(int oldOffset, int newOffset) {
+    if (oldOffset <= 0 || newOffset <= 0) {
+      throw new IllegalArgumentException();
+    }
+    annotationDirectoryOffsets.put(oldOffset, newOffset);
+  }
+
+  public void putStaticValuesOffset(int oldOffset, int newOffset) {
+    if (oldOffset <= 0 || newOffset <= 0) {
+      throw new IllegalArgumentException();
+    }
+    staticValuesOffsets.put(oldOffset, newOffset);
+  }
+
+  public int adjustString(int stringIndex) {
+    return stringIndex == ClassDef.NO_INDEX ? ClassDef.NO_INDEX : stringIds[stringIndex];
+  }
+
+  public int adjustType(int typeIndex) {
+    return (typeIndex == ClassDef.NO_INDEX) ? ClassDef.NO_INDEX : (typeIds[typeIndex] & 0xffff);
+  }
+
+  public TypeList adjustTypeList(TypeList typeList) {
+    if (typeList == TypeList.EMPTY) {
+      return typeList;
+    }
+    short[] types = typeList.getTypes().clone();
+    for (int i = 0; i < types.length; i++) {
+      types[i] = (short) adjustType(types[i]);
+    }
+    return new TypeList(target, types);
+  }
+
+  public int adjustProto(int protoIndex) {
+    return protoIds[protoIndex] & 0xffff;
+  }
+
+  public int adjustField(int fieldIndex) {
+    return fieldIds[fieldIndex] & 0xffff;
+  }
+
+  public int adjustMethod(int methodIndex) {
+    return methodIds[methodIndex] & 0xffff;
+  }
+
+  public int adjustTypeListOffset(int typeListOffset) {
+    return typeListOffsets.get(typeListOffset);
+  }
+
+  public int adjustAnnotation(int annotationOffset) {
+    return annotationOffsets.get(annotationOffset);
+  }
+
+  public int adjustAnnotationSet(int annotationSetOffset) {
+    return annotationSetOffsets.get(annotationSetOffset);
+  }
+
+  public int adjustAnnotationDirectory(int annotationDirectoryOffset) {
+    return annotationDirectoryOffsets.get(annotationDirectoryOffset);
+  }
+
+  public int adjustStaticValues(int staticValuesOffset) {
+    return staticValuesOffsets.get(staticValuesOffset);
+  }
+
+  public MethodId adjust(MethodId methodId) {
+    return new MethodId(target, adjustType(methodId.getDeclaringClassIndex()),
+        adjustProto(methodId.getProtoIndex()), adjustString(methodId.getNameIndex()));
+  }
+
+  public FieldId adjust(FieldId fieldId) {
+    return new FieldId(target, adjustType(fieldId.getDeclaringClassIndex()),
+        adjustType(fieldId.getTypeIndex()), adjustString(fieldId.getNameIndex()));
+
+  }
+
+  public ProtoId adjust(ProtoId protoId) {
+    return new ProtoId(target, adjustString(protoId.getShortyIndex()),
+        adjustType(protoId.getReturnTypeIndex()),
+        adjustTypeListOffset(protoId.getParametersOffset()));
+  }
+
+  public ClassDef adjust(ClassDef classDef) {
+    return new ClassDef(target,
+        classDef.getOffset(),
+        adjustType(classDef.getTypeIndex()),
+        classDef.getAccessFlags(),
+        adjustType(classDef.getSupertypeIndex()),
+        adjustTypeListOffset(classDef.getInterfacesOffset()),
+        classDef.getSourceFileIndex(),
+        classDef.getAnnotationsOffset(),
+        classDef.getClassDataOffset(),
+        classDef.getStaticValuesOffset());
+  }
+
+  public SortableType adjust(SortableType sortableType) {
+    return new SortableType(sortableType.getBuffer(), adjust(sortableType.getClassDef()));
+  }
+
+  public EncodedValue adjustEncodedValue(EncodedValue encodedValue) {
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(32);
+    new EncodedValueTransformer(encodedValue, out).readValue();
+    return new EncodedValue(out.toByteArray());
+  }
+
+  public EncodedValue adjustEncodedArray(EncodedValue encodedArray) {
+    ByteArrayAnnotatedOutput out = new ByteArrayAnnotatedOutput(32);
+    new EncodedValueTransformer(encodedArray, out).readArray();
+    return new EncodedValue(out.toByteArray());
+  }
+
+  public Annotation adjust(Annotation annotation) {
+    int[] names = annotation.getNames().clone();
+    EncodedValue[] values = annotation.getValues().clone();
+    for (int i = 0; i < names.length; i++) {
+      names[i] = adjustString(names[i]);
+      values[i] = adjustEncodedValue(values[i]);
+    }
+    return new Annotation(target, annotation.getVisibility(), adjustType(annotation.getTypeIndex()),
+        names, values);
+  }
+
+  /**
+   * Adjust an encoded value or array.
+   */
+  private final class EncodedValueTransformer extends EncodedValueReader {
+    private final ByteOutput out;
+
+    public EncodedValueTransformer(EncodedValue encodedValue, ByteOutput out) {
+      super(encodedValue);
+      this.out = out;
+    }
+
+    @Override
+    protected void visitArray(int size) {
+      Leb128Utils.writeUnsignedLeb128(out, size);
+    }
+
+    @Override
+    protected void visitAnnotation(int typeIndex, int size) {
+      Leb128Utils.writeUnsignedLeb128(out, adjustType(typeIndex));
+      Leb128Utils.writeUnsignedLeb128(out, size);
+    }
+
+    @Override
+    protected void visitAnnotationName(int index) {
+      Leb128Utils.writeUnsignedLeb128(out, adjustString(index));
+    }
+
+    @Override
+    protected void visitPrimitive(int argAndType, int type, int arg, int size) {
+      out.writeByte(argAndType);
+      copyBytes(in, out, size);
+    }
+
+    @Override
+    protected void visitString(int type, int index) {
+      writeTypeAndSizeAndIndex(type, adjustString(index));
+    }
+
+    @Override
+    protected void visitType(int type, int index) {
+      writeTypeAndSizeAndIndex(type, adjustType(index));
+    }
+
+    @Override
+    protected void visitField(int type, int index) {
+      writeTypeAndSizeAndIndex(type, adjustField(index));
+    }
+
+    @Override
+    protected void visitMethod(int type, int index) {
+      writeTypeAndSizeAndIndex(type, adjustMethod(index));
+    }
+
+    @Override
+    protected void visitArrayValue(int argAndType) {
+      out.writeByte(argAndType);
+    }
+
+    @Override
+    protected void visitAnnotationValue(int argAndType) {
+      out.writeByte(argAndType);
+    }
+
+    @Override
+    protected void visitEncodedBoolean(int argAndType) {
+      out.writeByte(argAndType);
+    }
+
+    @Override
+    protected void visitEncodedNull(int argAndType) {
+      out.writeByte(argAndType);
+    }
+
+    private void writeTypeAndSizeAndIndex(int type, int index) {
+      int byteCount;
+      if (Unsigned.compare(index, 0xff) <= 0) {
+        byteCount = 1;
+      } else if (Unsigned.compare(index, 0xffff) <= 0) {
+        byteCount = 2;
+      } else if (Unsigned.compare(index, 0xffffff) <= 0) {
+        byteCount = 3;
+      } else {
+        byteCount = 4;
+      }
+      int argAndType = ((byteCount - 1) << 5) | type;
+      out.writeByte(argAndType);
+
+      for (int i = 0; i < byteCount; i++) {
+        out.writeByte(index & 0xff);
+        index >>>= 8;
+      }
+    }
+
+    private void copyBytes(ByteInput in, ByteOutput out, int size) {
+      for (int i = 0; i < size; i++) {
+        out.writeByte(in.readByte());
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/merge/InstructionTransformer.java b/dx/src/com/android/jack/dx/merge/InstructionTransformer.java
index 0aa5364..65d3a3b 100644
--- a/dx/src/com/android/jack/dx/merge/InstructionTransformer.java
+++ b/dx/src/com/android/jack/dx/merge/InstructionTransformer.java
@@ -23,90 +23,94 @@
 import com.android.jack.dx.util.DexException;
 
 final class InstructionTransformer {
-    private final IndexMap indexMap;
-    private final CodeReader reader;
-    private DecodedInstruction[] mappedInstructions;
-    private int mappedAt;
+  private final IndexMap indexMap;
+  private final CodeReader reader;
+  private DecodedInstruction[] mappedInstructions;
+  private int mappedAt;
 
-    public InstructionTransformer(IndexMap indexMap) {
-        this.indexMap = indexMap;
-        this.reader = new CodeReader();
-        this.reader.setAllVisitors(new GenericVisitor());
-        this.reader.setStringVisitor(new StringVisitor());
-        this.reader.setTypeVisitor(new TypeVisitor());
-        this.reader.setFieldVisitor(new FieldVisitor());
-        this.reader.setMethodVisitor(new MethodVisitor());
+  public InstructionTransformer(IndexMap indexMap) {
+    this.indexMap = indexMap;
+    this.reader = new CodeReader();
+    this.reader.setAllVisitors(new GenericVisitor());
+    this.reader.setStringVisitor(new StringVisitor());
+    this.reader.setTypeVisitor(new TypeVisitor());
+    this.reader.setFieldVisitor(new FieldVisitor());
+    this.reader.setMethodVisitor(new MethodVisitor());
+  }
+
+  public short[] transform(short[] encodedInstructions) throws DexException {
+    DecodedInstruction[] decodedInstructions = DecodedInstruction.decodeAll(encodedInstructions);
+    int size = decodedInstructions.length;
+
+    mappedInstructions = new DecodedInstruction[size];
+    mappedAt = 0;
+    reader.visitAll(decodedInstructions);
+
+    ShortArrayCodeOutput out = new ShortArrayCodeOutput(size);
+    for (DecodedInstruction instruction : mappedInstructions) {
+      if (instruction != null) {
+        instruction.encode(out);
+      }
     }
 
-    public short[] transform(short[] encodedInstructions) throws DexException {
-        DecodedInstruction[] decodedInstructions =
-            DecodedInstruction.decodeAll(encodedInstructions);
-        int size = decodedInstructions.length;
+    return out.getArray();
+  }
 
-        mappedInstructions = new DecodedInstruction[size];
-        mappedAt = 0;
-        reader.visitAll(decodedInstructions);
-
-        ShortArrayCodeOutput out = new ShortArrayCodeOutput(size);
-        for (DecodedInstruction instruction : mappedInstructions) {
-            if (instruction != null) {
-                instruction.encode(out);
-            }
-        }
-
-        return out.getArray();
+  private class GenericVisitor implements CodeReader.Visitor {
+    @Override
+    public void visit(DecodedInstruction[] all, DecodedInstruction one) {
+      mappedInstructions[mappedAt++] = one;
     }
+  }
 
-    private class GenericVisitor implements CodeReader.Visitor {
-        public void visit(DecodedInstruction[] all, DecodedInstruction one) {
-            mappedInstructions[mappedAt++] = one;
-        }
+  private class StringVisitor implements CodeReader.Visitor {
+    @Override
+    public void visit(DecodedInstruction[] all, DecodedInstruction one) {
+      int stringId = one.getIndex();
+      int mappedId = indexMap.adjustString(stringId);
+      boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
+      jumboCheck(isJumbo, mappedId);
+      mappedInstructions[mappedAt++] = one.withIndex(mappedId);
     }
+  }
 
-    private class StringVisitor implements CodeReader.Visitor {
-        public void visit(DecodedInstruction[] all, DecodedInstruction one) {
-            int stringId = one.getIndex();
-            int mappedId = indexMap.adjustString(stringId);
-            boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
-            jumboCheck(isJumbo, mappedId);
-            mappedInstructions[mappedAt++] = one.withIndex(mappedId);
-        }
+  private class FieldVisitor implements CodeReader.Visitor {
+    @Override
+    public void visit(DecodedInstruction[] all, DecodedInstruction one) {
+      int fieldId = one.getIndex();
+      int mappedId = indexMap.adjustField(fieldId);
+      boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
+      jumboCheck(isJumbo, mappedId);
+      mappedInstructions[mappedAt++] = one.withIndex(mappedId);
     }
+  }
 
-    private class FieldVisitor implements CodeReader.Visitor {
-        public void visit(DecodedInstruction[] all, DecodedInstruction one) {
-            int fieldId = one.getIndex();
-            int mappedId = indexMap.adjustField(fieldId);
-            boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
-            jumboCheck(isJumbo, mappedId);
-            mappedInstructions[mappedAt++] = one.withIndex(mappedId);
-        }
+  private class TypeVisitor implements CodeReader.Visitor {
+    @Override
+    public void visit(DecodedInstruction[] all, DecodedInstruction one) {
+      int typeId = one.getIndex();
+      int mappedId = indexMap.adjustType(typeId);
+      boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
+      jumboCheck(isJumbo, mappedId);
+      mappedInstructions[mappedAt++] = one.withIndex(mappedId);
     }
+  }
 
-    private class TypeVisitor implements CodeReader.Visitor {
-        public void visit(DecodedInstruction[] all, DecodedInstruction one) {
-            int typeId = one.getIndex();
-            int mappedId = indexMap.adjustType(typeId);
-            boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
-            jumboCheck(isJumbo, mappedId);
-            mappedInstructions[mappedAt++] = one.withIndex(mappedId);
-        }
+  private class MethodVisitor implements CodeReader.Visitor {
+    @Override
+    public void visit(DecodedInstruction[] all, DecodedInstruction one) {
+      int methodId = one.getIndex();
+      int mappedId = indexMap.adjustMethod(methodId);
+      boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
+      jumboCheck(isJumbo, mappedId);
+      mappedInstructions[mappedAt++] = one.withIndex(mappedId);
     }
+  }
 
-    private class MethodVisitor implements CodeReader.Visitor {
-        public void visit(DecodedInstruction[] all, DecodedInstruction one) {
-            int methodId = one.getIndex();
-            int mappedId = indexMap.adjustMethod(methodId);
-            boolean isJumbo = (one.getOpcode() == Opcodes.CONST_STRING_JUMBO);
-            jumboCheck(isJumbo, mappedId);
-            mappedInstructions[mappedAt++] = one.withIndex(mappedId);
-        }
+  private static void jumboCheck(boolean isJumbo, int newIndex) {
+    if (!isJumbo && (newIndex > 0xffff)) {
+      throw new DexException(
+          "Cannot merge new index " + newIndex + " into a non-jumbo instruction!");
     }
-
-    private static void jumboCheck(boolean isJumbo, int newIndex) {
-        if (!isJumbo && (newIndex > 0xffff)) {
-            throw new DexException("Cannot merge new index " + newIndex +
-                                   " into a non-jumbo instruction!");
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/merge/SortableType.java b/dx/src/com/android/jack/dx/merge/SortableType.java
index 9435619..a479a89 100644
--- a/dx/src/com/android/jack/dx/merge/SortableType.java
+++ b/dx/src/com/android/jack/dx/merge/SortableType.java
@@ -26,81 +26,82 @@
  * preceded by its supertype and implemented interfaces.
  */
 final class SortableType {
-    public static final Comparator<SortableType> NULLS_LAST_ORDER = new Comparator<SortableType>() {
-        public int compare(SortableType a, SortableType b) {
-            if (a == b) {
-                return 0;
-            }
-            if (b == null) {
-                return -1;
-            }
-            if (a == null) {
-                return 1;
-            }
-            if (a.depth != b.depth) {
-                return a.depth - b.depth;
-            }
-            return a.getTypeIndex() - b.getTypeIndex();
-        }
-    };
+  public static final Comparator<SortableType> NULLS_LAST_ORDER = new Comparator<SortableType>() {
+    @Override
+    public int compare(SortableType a, SortableType b) {
+      if (a == b) {
+        return 0;
+      }
+      if (b == null) {
+        return -1;
+      }
+      if (a == null) {
+        return 1;
+      }
+      if (a.depth != b.depth) {
+        return a.depth - b.depth;
+      }
+      return a.getTypeIndex() - b.getTypeIndex();
+    }
+  };
 
-    private final DexBuffer buffer;
-    private ClassDef classDef;
-    private int depth = -1;
+  private final DexBuffer buffer;
+  private ClassDef classDef;
+  private int depth = -1;
 
-    public SortableType(DexBuffer buffer, ClassDef classDef) {
-        this.buffer = buffer;
-        this.classDef = classDef;
+  public SortableType(DexBuffer buffer, ClassDef classDef) {
+    this.buffer = buffer;
+    this.classDef = classDef;
+  }
+
+  public DexBuffer getBuffer() {
+    return buffer;
+  }
+
+  public ClassDef getClassDef() {
+    return classDef;
+  }
+
+  public int getTypeIndex() {
+    return classDef.getTypeIndex();
+  }
+
+  /**
+   * Assigns this type's depth if the depths of its supertype and implemented
+   * interfaces are known. Returns false if the depth couldn't be computed
+   * yet.
+   */
+  public boolean tryAssignDepth(SortableType[] types) {
+    int max;
+    if (classDef.getSupertypeIndex() == ClassDef.NO_INDEX) {
+      max = 0; // this is Object.class or an interface
+    } else {
+      SortableType sortableSupertype = types[classDef.getSupertypeIndex()];
+      if (sortableSupertype == null) {
+        max = 1; // unknown, so assume it's a root.
+      } else if (sortableSupertype.depth == -1) {
+        return false;
+      } else {
+        max = sortableSupertype.depth;
+      }
     }
 
-    public DexBuffer getBuffer() {
-        return buffer;
+    for (short interfaceIndex : classDef.getInterfaces()) {
+      SortableType implemented = types[interfaceIndex];
+      if (implemented == null) {
+        max = Math.max(max, 1); // unknown, so assume it's a root.
+      } else if (implemented.depth == -1) {
+        return false;
+      } else {
+        max = Math.max(max, implemented.depth);
+      }
     }
 
-    public ClassDef getClassDef() {
-        return classDef;
-    }
+    depth = max + 1;
+    return true;
+  }
 
-    public int getTypeIndex() {
-        return classDef.getTypeIndex();
-    }
-
-    /**
-     * Assigns this type's depth if the depths of its supertype and implemented
-     * interfaces are known. Returns false if the depth couldn't be computed
-     * yet.
-     */
-    public boolean tryAssignDepth(SortableType[] types) {
-        int max;
-        if (classDef.getSupertypeIndex() == ClassDef.NO_INDEX) {
-            max = 0; // this is Object.class or an interface
-        } else {
-            SortableType sortableSupertype = types[classDef.getSupertypeIndex()];
-            if (sortableSupertype == null) {
-                max = 1; // unknown, so assume it's a root.
-            } else if (sortableSupertype.depth == -1) {
-                return false;
-            } else {
-                max = sortableSupertype.depth;
-            }
-        }
-
-        for (short interfaceIndex : classDef.getInterfaces()) {
-            SortableType implemented = types[interfaceIndex];
-            if (implemented == null) {
-                max = Math.max(max, 1); // unknown, so assume it's a root.
-            } else if (implemented.depth == -1) {
-                return false;
-            } else {
-                max = Math.max(max, implemented.depth);
-            }
-        }
-
-        depth = max + 1;
-        return true;
-    }
-
-    public boolean isDepthAssigned() {
-        return depth != -1;
-    }
+  public boolean isDepthAssigned() {
+    return depth != -1;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/merge/TypeList.java b/dx/src/com/android/jack/dx/merge/TypeList.java
index a34d000..0c5b4f9 100644
--- a/dx/src/com/android/jack/dx/merge/TypeList.java
+++ b/dx/src/com/android/jack/dx/merge/TypeList.java
@@ -19,40 +19,43 @@
 import com.android.jack.dx.io.DexBuffer;
 import com.android.jack.dx.util.Unsigned;
 
-import java.util.Arrays;
-
+/**
+ * TODO(jack team)
+ */
 public final class TypeList implements Comparable<TypeList> {
 
-    public static final TypeList EMPTY = new TypeList(null, new short[0]);
+  public static final TypeList EMPTY = new TypeList(null, new short[0]);
 
-    private final DexBuffer buffer;
-    private final short[] types;
+  private final DexBuffer buffer;
+  private final short[] types;
 
-    public TypeList(DexBuffer buffer, short[] types) {
-        this.buffer = buffer;
-        this.types = types;
+  public TypeList(DexBuffer buffer, short[] types) {
+    this.buffer = buffer;
+    this.types = types;
+  }
+
+  public short[] getTypes() {
+    return types;
+  }
+
+  @Override
+  public int compareTo(TypeList other) {
+    for (int i = 0; i < types.length && i < other.types.length; i++) {
+      if (types[i] != other.types[i]) {
+        return Unsigned.compare(types[i], other.types[i]);
+      }
     }
+    return Unsigned.compare(types.length, other.types.length);
+  }
 
-    public short[] getTypes() {
-        return types;
+  @Override
+  public String toString() {
+    StringBuilder result = new StringBuilder();
+    result.append("(");
+    for (int i = 0, typesLength = types.length; i < typesLength; i++) {
+      result.append(buffer != null ? buffer.typeNames().get(types[i]) : types[i]);
     }
-
-    public int compareTo(TypeList other) {
-        for (int i = 0; i < types.length && i < other.types.length; i++) {
-            if (types[i] != other.types[i]) {
-                return Unsigned.compare(types[i], other.types[i]);
-            }
-        }
-        return Unsigned.compare(types.length, other.types.length);
-    }
-
-    @Override public String toString() {
-        StringBuilder result = new StringBuilder();
-        result.append("(");
-        for (int i = 0, typesLength = types.length; i < typesLength; i++) {
-            result.append(buffer != null ? buffer.typeNames().get(types[i]) : types[i]);
-        }
-        result.append(")");
-        return result.toString();
-    }
+    result.append(")");
+    return result.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/annotation/Annotation.java b/dx/src/com/android/jack/dx/rop/annotation/Annotation.java
index ccf331e..a0453e8 100644
--- a/dx/src/com/android/jack/dx/rop/annotation/Annotation.java
+++ b/dx/src/com/android/jack/dx/rop/annotation/Annotation.java
@@ -31,194 +31,195 @@
  * associated type and additionally consist of a set of (name, value)
  * pairs, where the names are unique.
  */
-public final class Annotation extends MutabilityControl
-        implements Comparable<Annotation>, ToHuman {
-    /** {@code non-null;} type of the annotation */
-    private final CstType type;
+public final class Annotation extends MutabilityControl implements Comparable<Annotation>, ToHuman {
+  /** {@code non-null;} type of the annotation */
+  private final CstType type;
 
-    /** {@code non-null;} the visibility of the annotation */
-    private final AnnotationVisibility visibility;
+  /** {@code non-null;} the visibility of the annotation */
+  private final AnnotationVisibility visibility;
 
-    /** {@code non-null;} map from names to {@link NameValuePair} instances */
-    private final TreeMap<CstString, NameValuePair> elements;
+  /** {@code non-null;} map from names to {@link NameValuePair} instances */
+  private final TreeMap<CstString, NameValuePair> elements;
 
-    /**
-     * Construct an instance. It initially contains no elements.
-     *
-     * @param type {@code non-null;} type of the annotation
-     * @param visibility {@code non-null;} the visibility of the annotation
-     */
-    public Annotation(CstType type, AnnotationVisibility visibility) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
-
-        if (visibility == null) {
-            throw new NullPointerException("visibility == null");
-        }
-
-        this.type = type;
-        this.visibility = visibility;
-        this.elements = new TreeMap<CstString, NameValuePair>();
+  /**
+   * Construct an instance. It initially contains no elements.
+   *
+   * @param type {@code non-null;} type of the annotation
+   * @param visibility {@code non-null;} the visibility of the annotation
+   */
+  public Annotation(CstType type, AnnotationVisibility visibility) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (! (other instanceof Annotation)) {
-            return false;
-        }
-
-        Annotation otherAnnotation = (Annotation) other;
-
-        if (! (type.equals(otherAnnotation.type)
-                        && (visibility == otherAnnotation.visibility))) {
-            return false;
-        }
-
-        return elements.equals(otherAnnotation.elements);
+    if (visibility == null) {
+      throw new NullPointerException("visibility == null");
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        int hash = type.hashCode();
-        hash = (hash * 31) + elements.hashCode();
-        hash = (hash * 31) + visibility.hashCode();
-        return hash;
+    this.type = type;
+    this.visibility = visibility;
+    this.elements = new TreeMap<CstString, NameValuePair>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof Annotation)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(Annotation other) {
-        int result = type.compareTo(other.type);
+    Annotation otherAnnotation = (Annotation) other;
 
-        if (result != 0) {
-            return result;
-        }
-
-        result = visibility.compareTo(other.visibility);
-
-        if (result != 0) {
-            return result;
-        }
-
-        Iterator<NameValuePair> thisIter = elements.values().iterator();
-        Iterator<NameValuePair> otherIter = other.elements.values().iterator();
-
-        while (thisIter.hasNext() && otherIter.hasNext()) {
-            NameValuePair thisOne = thisIter.next();
-            NameValuePair otherOne = otherIter.next();
-
-            result = thisOne.compareTo(otherOne);
-            if (result != 0) {
-                return result;
-            }
-        }
-
-        if (thisIter.hasNext()) {
-            return 1;
-        } else if (otherIter.hasNext()) {
-            return -1;
-        }
-
-        return 0;
+    if (!(type.equals(otherAnnotation.type) && (visibility == otherAnnotation.visibility))) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return toHuman();
+    return elements.equals(otherAnnotation.elements);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    int hash = type.hashCode();
+    hash = (hash * 31) + elements.hashCode();
+    hash = (hash * 31) + visibility.hashCode();
+    return hash;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(Annotation other) {
+    int result = type.compareTo(other.type);
+
+    if (result != 0) {
+      return result;
     }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        StringBuilder sb = new StringBuilder();
+    result = visibility.compareTo(other.visibility);
 
-        sb.append(visibility.toHuman());
-        sb.append("-annotation ");
-        sb.append(type.toHuman());
-        sb.append(" {");
-
-        boolean first = true;
-        for (NameValuePair pair : elements.values()) {
-            if (first) {
-                first = false;
-            } else {
-                sb.append(", ");
-            }
-            sb.append(pair.getName().toHuman());
-            sb.append(": ");
-            sb.append(pair.getValue().toHuman());
-        }
-
-        sb.append("}");
-        return sb.toString();
+    if (result != 0) {
+      return result;
     }
 
-    /**
-     * Gets the type of this instance.
-     *
-     * @return {@code non-null;} the type
-     */
-    public CstType getType() {
-        return type;
+    Iterator<NameValuePair> thisIter = elements.values().iterator();
+    Iterator<NameValuePair> otherIter = other.elements.values().iterator();
+
+    while (thisIter.hasNext() && otherIter.hasNext()) {
+      NameValuePair thisOne = thisIter.next();
+      NameValuePair otherOne = otherIter.next();
+
+      result = thisOne.compareTo(otherOne);
+      if (result != 0) {
+        return result;
+      }
     }
 
-    /**
-     * Gets the visibility of this instance.
-     *
-     * @return {@code non-null;} the visibility
-     */
-    public AnnotationVisibility getVisibility() {
-        return visibility;
+    if (thisIter.hasNext()) {
+      return 1;
+    } else if (otherIter.hasNext()) {
+      return -1;
     }
 
-    /**
-     * Put an element into the set of (name, value) pairs for this instance.
-     * If there is a preexisting element with the same name, it will be
-     * replaced by this method.
-     *
-     * @param pair {@code non-null;} the (name, value) pair to place into this instance
-     */
-    public void put(NameValuePair pair) {
-        throwIfImmutable();
+    return 0;
+  }
 
-        if (pair == null) {
-            throw new NullPointerException("pair == null");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return toHuman();
+  }
 
-        elements.put(pair.getName(), pair);
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    StringBuilder sb = new StringBuilder();
+
+    sb.append(visibility.toHuman());
+    sb.append("-annotation ");
+    sb.append(type.toHuman());
+    sb.append(" {");
+
+    boolean first = true;
+    for (NameValuePair pair : elements.values()) {
+      if (first) {
+        first = false;
+      } else {
+        sb.append(", ");
+      }
+      sb.append(pair.getName().toHuman());
+      sb.append(": ");
+      sb.append(pair.getValue().toHuman());
     }
 
-    /**
-     * Add an element to the set of (name, value) pairs for this instance.
-     * It is an error to call this method if there is a preexisting element
-     * with the same name.
-     *
-     * @param pair {@code non-null;} the (name, value) pair to add to this instance
-     */
-    public void add(NameValuePair pair) {
-        throwIfImmutable();
+    sb.append("}");
+    return sb.toString();
+  }
 
-        if (pair == null) {
-            throw new NullPointerException("pair == null");
-        }
+  /**
+   * Gets the type of this instance.
+   *
+   * @return {@code non-null;} the type
+   */
+  public CstType getType() {
+    return type;
+  }
 
-        CstString name = pair.getName();
+  /**
+   * Gets the visibility of this instance.
+   *
+   * @return {@code non-null;} the visibility
+   */
+  public AnnotationVisibility getVisibility() {
+    return visibility;
+  }
 
-        if (elements.get(name) != null) {
-            throw new IllegalArgumentException("name already added: " + name);
-        }
+  /**
+   * Put an element into the set of (name, value) pairs for this instance.
+   * If there is a preexisting element with the same name, it will be
+   * replaced by this method.
+   *
+   * @param pair {@code non-null;} the (name, value) pair to place into this instance
+   */
+  public void put(NameValuePair pair) {
+    throwIfImmutable();
 
-        elements.put(name, pair);
+    if (pair == null) {
+      throw new NullPointerException("pair == null");
     }
 
-    /**
-     * Gets the set of name-value pairs contained in this instance. The
-     * result is always unmodifiable.
-     *
-     * @return {@code non-null;} the set of name-value pairs
-     */
-    public Collection<NameValuePair> getNameValuePairs() {
-        return Collections.unmodifiableCollection(elements.values());
+    elements.put(pair.getName(), pair);
+  }
+
+  /**
+   * Add an element to the set of (name, value) pairs for this instance.
+   * It is an error to call this method if there is a preexisting element
+   * with the same name.
+   *
+   * @param pair {@code non-null;} the (name, value) pair to add to this instance
+   */
+  public void add(NameValuePair pair) {
+    throwIfImmutable();
+
+    if (pair == null) {
+      throw new NullPointerException("pair == null");
     }
+
+    CstString name = pair.getName();
+
+    if (elements.get(name) != null) {
+      throw new IllegalArgumentException("name already added: " + name);
+    }
+
+    elements.put(name, pair);
+  }
+
+  /**
+   * Gets the set of name-value pairs contained in this instance. The
+   * result is always unmodifiable.
+   *
+   * @return {@code non-null;} the set of name-value pairs
+   */
+  public Collection<NameValuePair> getNameValuePairs() {
+    return Collections.unmodifiableCollection(elements.values());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/annotation/AnnotationVisibility.java b/dx/src/com/android/jack/dx/rop/annotation/AnnotationVisibility.java
index e8ca504..874de4e 100644
--- a/dx/src/com/android/jack/dx/rop/annotation/AnnotationVisibility.java
+++ b/dx/src/com/android/jack/dx/rop/annotation/AnnotationVisibility.java
@@ -22,25 +22,23 @@
  * Visibility scope of an annotation.
  */
 public enum AnnotationVisibility implements ToHuman {
-    RUNTIME("runtime"),
-    BUILD("build"),
-    SYSTEM("system"),
-    EMBEDDED("embedded");
+  RUNTIME("runtime"), BUILD("build"), SYSTEM("system"), EMBEDDED("embedded");
 
-    /** {@code non-null;} the human-oriented string representation */
-    private final String human;
+  /** {@code non-null;} the human-oriented string representation */
+  private final String human;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param human {@code non-null;} the human-oriented string representation
-     */
-    private AnnotationVisibility(String human) {
-        this.human = human;
-    }
+  /**
+   * Constructs an instance.
+   *
+   * @param human {@code non-null;} the human-oriented string representation
+   */
+  private AnnotationVisibility(String human) {
+    this.human = human;
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return human;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return human;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/annotation/Annotations.java b/dx/src/com/android/jack/dx/rop/annotation/Annotations.java
index 9f9f92b..626f963 100644
--- a/dx/src/com/android/jack/dx/rop/annotation/Annotations.java
+++ b/dx/src/com/android/jack/dx/rop/annotation/Annotations.java
@@ -27,187 +27,186 @@
 /**
  * List of {@link Annotation} instances.
  */
-public final class Annotations extends MutabilityControl
-        implements Comparable<Annotations> {
-    /** {@code non-null;} immutable empty instance */
-    public static final Annotations EMPTY = new Annotations();
+public final class Annotations extends MutabilityControl implements Comparable<Annotations> {
+  /** {@code non-null;} immutable empty instance */
+  public static final Annotations EMPTY = new Annotations();
 
-    static {
-        EMPTY.setImmutable();
+  static {
+    EMPTY.setImmutable();
+  }
+
+  /** {@code non-null;} map from types to annotations */
+  private final TreeMap<CstType, Annotation> annotations;
+
+  /**
+   * Constructs an immutable instance which is the combination of the
+   * two given instances. The two instances must contain disjoint sets
+   * of types.
+   *
+   * @param a1 {@code non-null;} an instance
+   * @param a2 {@code non-null;} the other instance
+   * @return {@code non-null;} the combination
+   * @throws IllegalArgumentException thrown if there is a duplicate type
+   */
+  public static Annotations combine(Annotations a1, Annotations a2) {
+    Annotations result = new Annotations();
+
+    result.addAll(a1);
+    result.addAll(a2);
+    result.setImmutable();
+
+    return result;
+  }
+
+  /**
+   * Constructs an immutable instance which is the combination of the
+   * given instance with the given additional annotation. The latter's
+   * type must not already appear in the former.
+   *
+   * @param annotations {@code non-null;} the instance to augment
+   * @param annotation {@code non-null;} the additional annotation
+   * @return {@code non-null;} the combination
+   * @throws IllegalArgumentException thrown if there is a duplicate type
+   */
+  public static Annotations combine(Annotations annotations, Annotation annotation) {
+    Annotations result = new Annotations();
+
+    result.addAll(annotations);
+    result.add(annotation);
+    result.setImmutable();
+
+    return result;
+  }
+
+  /**
+   * Constructs an empty instance.
+   */
+  public Annotations() {
+    annotations = new TreeMap<CstType, Annotation>();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return annotations.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof Annotations)) {
+      return false;
     }
 
-    /** {@code non-null;} map from types to annotations */
-    private final TreeMap<CstType, Annotation> annotations;
+    Annotations otherAnnotations = (Annotations) other;
 
-    /**
-     * Constructs an immutable instance which is the combination of the
-     * two given instances. The two instances must contain disjoint sets
-     * of types.
-     *
-     * @param a1 {@code non-null;} an instance
-     * @param a2 {@code non-null;} the other instance
-     * @return {@code non-null;} the combination
-     * @throws IllegalArgumentException thrown if there is a duplicate type
-     */
-    public static Annotations combine(Annotations a1, Annotations a2) {
-        Annotations result = new Annotations();
+    return annotations.equals(otherAnnotations.annotations);
+  }
 
-        result.addAll(a1);
-        result.addAll(a2);
-        result.setImmutable();
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(Annotations other) {
+    Iterator<Annotation> thisIter = annotations.values().iterator();
+    Iterator<Annotation> otherIter = other.annotations.values().iterator();
 
+    while (thisIter.hasNext() && otherIter.hasNext()) {
+      Annotation thisOne = thisIter.next();
+      Annotation otherOne = otherIter.next();
+
+      int result = thisOne.compareTo(otherOne);
+      if (result != 0) {
         return result;
+      }
     }
 
-    /**
-     * Constructs an immutable instance which is the combination of the
-     * given instance with the given additional annotation. The latter's
-     * type must not already appear in the former.
-     *
-     * @param annotations {@code non-null;} the instance to augment
-     * @param annotation {@code non-null;} the additional annotation
-     * @return {@code non-null;} the combination
-     * @throws IllegalArgumentException thrown if there is a duplicate type
-     */
-    public static Annotations combine(Annotations annotations,
-            Annotation annotation) {
-        Annotations result = new Annotations();
-
-        result.addAll(annotations);
-        result.add(annotation);
-        result.setImmutable();
-
-        return result;
+    if (thisIter.hasNext()) {
+      return 1;
+    } else if (otherIter.hasNext()) {
+      return -1;
     }
 
-    /**
-     * Constructs an empty instance.
-     */
-    public Annotations() {
-        annotations = new TreeMap<CstType, Annotation>();
+    return 0;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuilder sb = new StringBuilder();
+    boolean first = true;
+
+    sb.append("annotations{");
+
+    for (Annotation a : annotations.values()) {
+      if (first) {
+        first = false;
+      } else {
+        sb.append(", ");
+      }
+      sb.append(a.toHuman());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return annotations.hashCode();
+    sb.append("}");
+    return sb.toString();
+  }
+
+  /**
+   * Gets the number of elements in this instance.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int size() {
+    return annotations.size();
+  }
+
+  /**
+   * Adds an element to this instance. There must not already be an
+   * element of the same type.
+   *
+   * @param annotation {@code non-null;} the element to add
+   * @throws IllegalArgumentException thrown if there is a duplicate type
+   */
+  public void add(Annotation annotation) {
+    throwIfImmutable();
+
+    if (annotation == null) {
+      throw new NullPointerException("annotation == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (! (other instanceof Annotations)) {
-            return false;
-        }
+    CstType type = annotation.getType();
 
-        Annotations otherAnnotations = (Annotations) other;
-
-        return annotations.equals(otherAnnotations.annotations);
+    if (annotations.containsKey(type)) {
+      throw new IllegalArgumentException("duplicate type: " + type.toHuman());
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(Annotations other) {
-        Iterator<Annotation> thisIter = annotations.values().iterator();
-        Iterator<Annotation> otherIter = other.annotations.values().iterator();
+    annotations.put(type, annotation);
+  }
 
-        while (thisIter.hasNext() && otherIter.hasNext()) {
-            Annotation thisOne = thisIter.next();
-            Annotation otherOne = otherIter.next();
+  /**
+   * Adds all of the elements of the given instance to this one. The
+   * instances must not have any duplicate types.
+   *
+   * @param toAdd {@code non-null;} the annotations to add
+   * @throws IllegalArgumentException thrown if there is a duplicate type
+   */
+  public void addAll(Annotations toAdd) {
+    throwIfImmutable();
 
-            int result = thisOne.compareTo(otherOne);
-            if (result != 0) {
-                return result;
-            }
-        }
-
-        if (thisIter.hasNext()) {
-            return 1;
-        } else if (otherIter.hasNext()) {
-            return -1;
-        }
-
-        return 0;
+    if (toAdd == null) {
+      throw new NullPointerException("toAdd == null");
     }
 
-    /** {@inheritDoc} */
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        boolean first = true;
-
-        sb.append("annotations{");
-
-        for (Annotation a : annotations.values()) {
-            if (first) {
-                first = false;
-            } else {
-                sb.append(", ");
-            }
-            sb.append(a.toHuman());
-        }
-
-        sb.append("}");
-        return sb.toString();
+    for (Annotation a : toAdd.annotations.values()) {
+      add(a);
     }
+  }
 
-    /**
-     * Gets the number of elements in this instance.
-     *
-     * @return {@code >= 0;} the size
-     */
-    public int size() {
-        return annotations.size();
-    }
-
-    /**
-     * Adds an element to this instance. There must not already be an
-     * element of the same type.
-     *
-     * @param annotation {@code non-null;} the element to add
-     * @throws IllegalArgumentException thrown if there is a duplicate type
-     */
-    public void add(Annotation annotation) {
-        throwIfImmutable();
-
-        if (annotation == null) {
-            throw new NullPointerException("annotation == null");
-        }
-
-        CstType type = annotation.getType();
-
-        if (annotations.containsKey(type)) {
-            throw new IllegalArgumentException("duplicate type: " +
-                    type.toHuman());
-        }
-
-        annotations.put(type, annotation);
-    }
-
-    /**
-     * Adds all of the elements of the given instance to this one. The
-     * instances must not have any duplicate types.
-     *
-     * @param toAdd {@code non-null;} the annotations to add
-     * @throws IllegalArgumentException thrown if there is a duplicate type
-     */
-    public void addAll(Annotations toAdd) {
-        throwIfImmutable();
-
-        if (toAdd == null) {
-            throw new NullPointerException("toAdd == null");
-        }
-
-        for (Annotation a : toAdd.annotations.values()) {
-            add(a);
-        }
-    }
-
-    /**
-     * Gets the set of annotations contained in this instance. The
-     * result is always unmodifiable.
-     *
-     * @return {@code non-null;} the set of annotations
-     */
-    public Collection<Annotation> getAnnotations() {
-        return Collections.unmodifiableCollection(annotations.values());
-    }
+  /**
+   * Gets the set of annotations contained in this instance. The
+   * result is always unmodifiable.
+   *
+   * @return {@code non-null;} the set of annotations
+   */
+  public Collection<Annotation> getAnnotations() {
+    return Collections.unmodifiableCollection(annotations.values());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/annotation/AnnotationsList.java b/dx/src/com/android/jack/dx/rop/annotation/AnnotationsList.java
index a013673..dc0522f 100644
--- a/dx/src/com/android/jack/dx/rop/annotation/AnnotationsList.java
+++ b/dx/src/com/android/jack/dx/rop/annotation/AnnotationsList.java
@@ -21,71 +21,69 @@
 /**
  * List of {@link Annotations} instances.
  */
-public final class AnnotationsList
-        extends FixedSizeList {
-    /** {@code non-null;} immutable empty instance */
-    public static final AnnotationsList EMPTY = new AnnotationsList(0);
+public final class AnnotationsList extends FixedSizeList {
+  /** {@code non-null;} immutable empty instance */
+  public static final AnnotationsList EMPTY = new AnnotationsList(0);
 
-    /**
-     * Constructs an immutable instance which is the combination of
-     * the two given instances. The two instances must each have the
-     * same number of elements, and each pair of elements must contain
-     * disjoint sets of types.
-     *
-     * @param list1 {@code non-null;} an instance
-     * @param list2 {@code non-null;} the other instance
-     * @return {@code non-null;} the combination
-     */
-    public static AnnotationsList combine(AnnotationsList list1,
-            AnnotationsList list2) {
-        int size = list1.size();
+  /**
+   * Constructs an immutable instance which is the combination of
+   * the two given instances. The two instances must each have the
+   * same number of elements, and each pair of elements must contain
+   * disjoint sets of types.
+   *
+   * @param list1 {@code non-null;} an instance
+   * @param list2 {@code non-null;} the other instance
+   * @return {@code non-null;} the combination
+   */
+  public static AnnotationsList combine(AnnotationsList list1, AnnotationsList list2) {
+    int size = list1.size();
 
-        if (size != list2.size()) {
-            throw new IllegalArgumentException("list1.size() != list2.size()");
-        }
-
-        AnnotationsList result = new AnnotationsList(size);
-
-        for (int i = 0; i < size; i++) {
-            Annotations a1 = list1.get(i);
-            Annotations a2 = list2.get(i);
-            result.set(i, Annotations.combine(a1, a2));
-        }
-
-        result.setImmutable();
-        return result;
+    if (size != list2.size()) {
+      throw new IllegalArgumentException("list1.size() != list2.size()");
     }
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public AnnotationsList(int size) {
-        super(size);
+    AnnotationsList result = new AnnotationsList(size);
+
+    for (int i = 0; i < size; i++) {
+      Annotations a1 = list1.get(i);
+      Annotations a2 = list2.get(i);
+      result.set(i, Annotations.combine(a1, a2));
     }
 
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public Annotations get(int n) {
-        return (Annotations) get0(n);
-    }
+    result.setImmutable();
+    return result;
+  }
 
-    /**
-     * Sets the element at the given index. The given element must be
-     * immutable.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param a {@code null-ok;} the element to set at {@code n}
-     */
-    public void set(int n, Annotations a) {
-        a.throwIfMutable();
-        set0(n, a);
-    }
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public AnnotationsList(int size) {
+    super(size);
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Annotations get(int n) {
+    return (Annotations) get0(n);
+  }
+
+  /**
+   * Sets the element at the given index. The given element must be
+   * immutable.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param a {@code null-ok;} the element to set at {@code n}
+   */
+  public void set(int n, Annotations a) {
+    a.throwIfMutable();
+    set0(n, a);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/annotation/NameValuePair.java b/dx/src/com/android/jack/dx/rop/annotation/NameValuePair.java
index 7661fbf..018e299 100644
--- a/dx/src/com/android/jack/dx/rop/annotation/NameValuePair.java
+++ b/dx/src/com/android/jack/dx/rop/annotation/NameValuePair.java
@@ -23,84 +23,87 @@
  * A (name, value) pair. These are used as the contents of an annotation.
  */
 public final class NameValuePair implements Comparable<NameValuePair> {
-    /** {@code non-null;} the name */
-    private final CstString name;
+  /** {@code non-null;} the name */
+  private final CstString name;
 
-    /** {@code non-null;} the value */
-    private final Constant value;
+  /** {@code non-null;} the value */
+  private final Constant value;
 
-    /**
-     * Construct an instance.
-     *
-     * @param name {@code non-null;} the name
-     * @param value {@code non-null;} the value
-     */
-    public NameValuePair(CstString name, Constant value) {
-        if (name == null) {
-            throw new NullPointerException("name == null");
-        }
-
-        if (value == null) {
-            throw new NullPointerException("value == null");
-        }
-
-        this.name = name;
-        this.value = value;
+  /**
+   * Construct an instance.
+   *
+   * @param name {@code non-null;} the name
+   * @param value {@code non-null;} the value
+   */
+  public NameValuePair(CstString name, Constant value) {
+    if (name == null) {
+      throw new NullPointerException("name == null");
     }
 
-    /** {@inheritDoc} */
-    public String toString() {
-        return name.toHuman() + ":" + value;
+    if (value == null) {
+      throw new NullPointerException("value == null");
     }
 
-    /** {@inheritDoc} */
-    public int hashCode() {
-        return name.hashCode() * 31 + value.hashCode();
+    this.name = name;
+    this.value = value;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return name.toHuman() + ":" + value;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return name.hashCode() * 31 + value.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof NameValuePair)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    public boolean equals(Object other) {
-        if (! (other instanceof NameValuePair)) {
-            return false;
-        }
+    NameValuePair otherPair = (NameValuePair) other;
 
-        NameValuePair otherPair = (NameValuePair) other;
+    return name.equals(otherPair.name) && value.equals(otherPair.value);
+  }
 
-        return name.equals(otherPair.name)
-            && value.equals(otherPair.value);
+  /**
+   * {@inheritDoc}
+   *
+   * <p>Instances of this class compare in name-major and value-minor
+   * order.</p>
+   */
+  @Override
+  public int compareTo(NameValuePair other) {
+    int result = name.compareTo(other.name);
+
+    if (result != 0) {
+      return result;
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * <p>Instances of this class compare in name-major and value-minor
-     * order.</p>
-     */
-    public int compareTo(NameValuePair other) {
-        int result = name.compareTo(other.name);
+    return value.compareTo(other.value);
+  }
 
-        if (result != 0) {
-            return result;
-        }
+  /**
+   * Gets the name.
+   *
+   * @return {@code non-null;} the name
+   */
+  public CstString getName() {
+    return name;
+  }
 
-        return value.compareTo(other.value);
-    }
-
-    /**
-     * Gets the name.
-     *
-     * @return {@code non-null;} the name
-     */
-    public CstString getName() {
-        return name;
-    }
-
-    /**
-     * Gets the value.
-     *
-     * @return {@code non-null;} the value
-     */
-    public Constant getValue() {
-        return value;
-    }
+  /**
+   * Gets the value.
+   *
+   * @return {@code non-null;} the value
+   */
+  public Constant getValue() {
+    return value;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/AccessFlags.java b/dx/src/com/android/jack/dx/rop/code/AccessFlags.java
index 95385bd..7dc3a80 100644
--- a/dx/src/com/android/jack/dx/rop/code/AccessFlags.java
+++ b/dx/src/com/android/jack/dx/rop/code/AccessFlags.java
@@ -28,379 +28,373 @@
  * is only used in a very limited way.
  */
 public final class AccessFlags {
-    /** public member / class */
-    public static final int ACC_PUBLIC = 0x0001;
+  /** public member / class */
+  public static final int ACC_PUBLIC = 0x0001;
 
-    /** private member */
-    public static final int ACC_PRIVATE = 0x0002;
+  /** private member */
+  public static final int ACC_PRIVATE = 0x0002;
 
-    /** protected member */
-    public static final int ACC_PROTECTED = 0x0004;
+  /** protected member */
+  public static final int ACC_PROTECTED = 0x0004;
 
-    /** static member */
-    public static final int ACC_STATIC = 0x0008;
+  /** static member */
+  public static final int ACC_STATIC = 0x0008;
 
-    /** final member / class */
-    public static final int ACC_FINAL = 0x0010;
+  /** final member / class */
+  public static final int ACC_FINAL = 0x0010;
 
-    /**
-     * synchronized method; only valid in dex files for {@code native}
-     * methods
-     */
-    public static final int ACC_SYNCHRONIZED = 0x0020;
+  /**
+   * synchronized method; only valid in dex files for {@code native}
+   * methods
+   */
+  public static final int ACC_SYNCHRONIZED = 0x0020;
 
-    /**
-     * class with new-style {@code invokespecial} for superclass
-     * method access
-     */
-    public static final int ACC_SUPER = 0x0020;
+  /**
+   * class with new-style {@code invokespecial} for superclass
+   * method access
+   */
+  public static final int ACC_SUPER = 0x0020;
 
-    /** volatile field */
-    public static final int ACC_VOLATILE = 0x0040;
+  /** volatile field */
+  public static final int ACC_VOLATILE = 0x0040;
 
-    /** bridge method (generated) */
-    public static final int ACC_BRIDGE = 0x0040;
+  /** bridge method (generated) */
+  public static final int ACC_BRIDGE = 0x0040;
 
-    /** transient field */
-    public static final int ACC_TRANSIENT = 0x0080;
+  /** transient field */
+  public static final int ACC_TRANSIENT = 0x0080;
 
-    /** varargs method */
-    public static final int ACC_VARARGS = 0x0080;
+  /** varargs method */
+  public static final int ACC_VARARGS = 0x0080;
 
-    /** native method */
-    public static final int ACC_NATIVE = 0x0100;
+  /** native method */
+  public static final int ACC_NATIVE = 0x0100;
 
-    /** "class" is in fact an public static final interface */
-    public static final int ACC_INTERFACE = 0x0200;
+  /** "class" is in fact an public static final interface */
+  public static final int ACC_INTERFACE = 0x0200;
 
-    /** abstract method / class */
-    public static final int ACC_ABSTRACT = 0x0400;
+  /** abstract method / class */
+  public static final int ACC_ABSTRACT = 0x0400;
 
-    /**
-     * method with strict floating point ({@code strictfp})
-     * behavior
-     */
-    public static final int ACC_STRICT = 0x0800;
+  /**
+   * method with strict floating point ({@code strictfp})
+   * behavior
+   */
+  public static final int ACC_STRICT = 0x0800;
 
-    /** synthetic member */
-    public static final int ACC_SYNTHETIC = 0x1000;
+  /** synthetic member */
+  public static final int ACC_SYNTHETIC = 0x1000;
 
-    /** class is an annotation type */
-    public static final int ACC_ANNOTATION = 0x2000;
+  /** class is an annotation type */
+  public static final int ACC_ANNOTATION = 0x2000;
 
-    /**
-     * class is an enumerated type; field is an element of an enumerated
-     * type
-     */
-    public static final int ACC_ENUM = 0x4000;
+  /**
+   * class is an enumerated type; field is an element of an enumerated
+   * type
+   */
+  public static final int ACC_ENUM = 0x4000;
 
-    /** method is a constructor */
-    public static final int ACC_CONSTRUCTOR = 0x10000;
+  /** method is a constructor */
+  public static final int ACC_CONSTRUCTOR = 0x10000;
 
-    /**
-     * method was declared {@code synchronized}; has no effect on
-     * execution (other than inspecting this flag, per se)
-     */
-    public static final int ACC_DECLARED_SYNCHRONIZED = 0x20000;
+  /**
+   * method was declared {@code synchronized}; has no effect on
+   * execution (other than inspecting this flag, per se)
+   */
+  public static final int ACC_DECLARED_SYNCHRONIZED = 0x20000;
 
-    /** flags defined on classes */
-    public static final int CLASS_FLAGS =
-        ACC_PUBLIC | ACC_FINAL | ACC_SUPER | ACC_INTERFACE | ACC_ABSTRACT |
-        ACC_SYNTHETIC | ACC_ANNOTATION | ACC_ENUM;
+  /** flags defined on classes */
+  public static final int CLASS_FLAGS = ACC_PUBLIC | ACC_FINAL | ACC_SUPER | ACC_INTERFACE
+      | ACC_ABSTRACT | ACC_SYNTHETIC | ACC_ANNOTATION | ACC_ENUM;
 
-    /** flags defined on inner classes */
-    public static final int INNER_CLASS_FLAGS =
-        ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC | ACC_FINAL |
-        ACC_INTERFACE | ACC_ABSTRACT | ACC_SYNTHETIC | ACC_ANNOTATION |
-        ACC_ENUM;
+  /** flags defined on inner classes */
+  public static final int INNER_CLASS_FLAGS = ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC
+      | ACC_FINAL | ACC_INTERFACE | ACC_ABSTRACT | ACC_SYNTHETIC | ACC_ANNOTATION | ACC_ENUM;
 
-    /** flags defined on fields */
-    public static final int FIELD_FLAGS =
-        ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC | ACC_FINAL |
-        ACC_VOLATILE | ACC_TRANSIENT | ACC_SYNTHETIC | ACC_ENUM;
+  /** flags defined on fields */
+  public static final int FIELD_FLAGS = ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC
+      | ACC_FINAL | ACC_VOLATILE | ACC_TRANSIENT | ACC_SYNTHETIC | ACC_ENUM;
 
-    /** flags defined on methods */
-    public static final int METHOD_FLAGS =
-        ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC | ACC_FINAL |
-        ACC_SYNCHRONIZED | ACC_BRIDGE | ACC_VARARGS | ACC_NATIVE |
-        ACC_ABSTRACT | ACC_STRICT | ACC_SYNTHETIC | ACC_CONSTRUCTOR |
-        ACC_DECLARED_SYNCHRONIZED;
+  /** flags defined on methods */
+  public static final int METHOD_FLAGS = ACC_PUBLIC | ACC_PRIVATE | ACC_PROTECTED | ACC_STATIC
+      | ACC_FINAL | ACC_SYNCHRONIZED | ACC_BRIDGE | ACC_VARARGS | ACC_NATIVE | ACC_ABSTRACT
+      | ACC_STRICT | ACC_SYNTHETIC | ACC_CONSTRUCTOR | ACC_DECLARED_SYNCHRONIZED;
 
-    /** indicates conversion of class flags */
-    private static final int CONV_CLASS = 1;
+  /** indicates conversion of class flags */
+  private static final int CONV_CLASS = 1;
 
-    /** indicates conversion of field flags */
-    private static final int CONV_FIELD = 2;
+  /** indicates conversion of field flags */
+  private static final int CONV_FIELD = 2;
 
-    /** indicates conversion of method flags */
-    private static final int CONV_METHOD = 3;
+  /** indicates conversion of method flags */
+  private static final int CONV_METHOD = 3;
 
-    /**
-     * This class is uninstantiable.
-     */
-    private AccessFlags() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private AccessFlags() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Returns a human-oriented string representing the given access flags,
+   * as defined on classes (not fields or methods).
+   *
+   * @param flags the flags
+   * @return {@code non-null;} human-oriented string
+   */
+  public static String classString(int flags) {
+    return humanHelper(flags, CLASS_FLAGS, CONV_CLASS);
+  }
+
+  /**
+   * Returns a human-oriented string representing the given access flags,
+   * as defined on inner classes.
+   *
+   * @param flags the flags
+   * @return {@code non-null;} human-oriented string
+   */
+  public static String innerClassString(int flags) {
+    return humanHelper(flags, INNER_CLASS_FLAGS, CONV_CLASS);
+  }
+
+  /**
+   * Returns a human-oriented string representing the given access flags,
+   * as defined on fields (not classes or methods).
+   *
+   * @param flags the flags
+   * @return {@code non-null;} human-oriented string
+   */
+  public static String fieldString(int flags) {
+    return humanHelper(flags, FIELD_FLAGS, CONV_FIELD);
+  }
+
+  /**
+   * Returns a human-oriented string representing the given access flags,
+   * as defined on methods (not classes or fields).
+   *
+   * @param flags the flags
+   * @return {@code non-null;} human-oriented string
+   */
+  public static String methodString(int flags) {
+    return humanHelper(flags, METHOD_FLAGS, CONV_METHOD);
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_PUBLIC} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_PUBLIC} flag
+   */
+  public static boolean isPublic(int flags) {
+    return (flags & ACC_PUBLIC) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_PROTECTED} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_PROTECTED} flag
+   */
+  public static boolean isProtected(int flags) {
+    return (flags & ACC_PROTECTED) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_PRIVATE} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_PRIVATE} flag
+   */
+  public static boolean isPrivate(int flags) {
+    return (flags & ACC_PRIVATE) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_STATIC} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_STATIC} flag
+   */
+  public static boolean isStatic(int flags) {
+    return (flags & ACC_STATIC) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_CONSTRUCTOR} is on in
+   * the given flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_CONSTRUCTOR} flag
+   */
+  public static boolean isConstructor(int flags) {
+    return (flags & ACC_CONSTRUCTOR) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_INTERFACE} is on in
+   * the given flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_INTERFACE} flag
+   */
+  public static boolean isInterface(int flags) {
+    return (flags & ACC_INTERFACE) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_SYNCHRONIZED} is on in
+   * the given flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_SYNCHRONIZED} flag
+   */
+  public static boolean isSynchronized(int flags) {
+    return (flags & ACC_SYNCHRONIZED) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_ABSTRACT} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_ABSTRACT} flag
+   */
+  public static boolean isAbstract(int flags) {
+    return (flags & ACC_ABSTRACT) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_NATIVE} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_NATIVE} flag
+   */
+  public static boolean isNative(int flags) {
+    return (flags & ACC_NATIVE) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_ANNOTATION} is on in the given
+   * flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_ANNOTATION} flag
+   */
+  public static boolean isAnnotation(int flags) {
+    return (flags & ACC_ANNOTATION) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_DECLARED_SYNCHRONIZED} is
+   * on in the given flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_DECLARED_SYNCHRONIZED} flag
+   */
+  public static boolean isDeclaredSynchronized(int flags) {
+    return (flags & ACC_DECLARED_SYNCHRONIZED) != 0;
+  }
+
+  /**
+   * Returns whether the flag {@code ACC_ENUM} is on in the given flags.
+   *
+   * @param flags the flags to check
+   * @return the value of the {@code ACC_ENUM} flag
+   */
+  public static boolean isEnum(int flags) {
+    return (flags & ACC_ENUM) != 0;
+  }
+
+  /**
+   * Helper to return a human-oriented string representing the given
+   * access flags.
+   *
+   * @param flags the defined flags
+   * @param mask mask for the "defined" bits
+   * @param what what the flags represent (one of {@code CONV_*})
+   * @return {@code non-null;} human-oriented string
+   */
+  private static String humanHelper(int flags, int mask, int what) {
+    StringBuffer sb = new StringBuffer(80);
+    int extra = flags & ~mask;
+
+    flags &= mask;
+
+    if ((flags & ACC_PUBLIC) != 0) {
+      sb.append("|public");
+    }
+    if ((flags & ACC_PRIVATE) != 0) {
+      sb.append("|private");
+    }
+    if ((flags & ACC_PROTECTED) != 0) {
+      sb.append("|protected");
+    }
+    if ((flags & ACC_STATIC) != 0) {
+      sb.append("|static");
+    }
+    if ((flags & ACC_FINAL) != 0) {
+      sb.append("|final");
+    }
+    if ((flags & ACC_SYNCHRONIZED) != 0) {
+      if (what == CONV_CLASS) {
+        sb.append("|super");
+      } else {
+        sb.append("|synchronized");
+      }
+    }
+    if ((flags & ACC_VOLATILE) != 0) {
+      if (what == CONV_METHOD) {
+        sb.append("|bridge");
+      } else {
+        sb.append("|volatile");
+      }
+    }
+    if ((flags & ACC_TRANSIENT) != 0) {
+      if (what == CONV_METHOD) {
+        sb.append("|varargs");
+      } else {
+        sb.append("|transient");
+      }
+    }
+    if ((flags & ACC_NATIVE) != 0) {
+      sb.append("|native");
+    }
+    if ((flags & ACC_INTERFACE) != 0) {
+      sb.append("|interface");
+    }
+    if ((flags & ACC_ABSTRACT) != 0) {
+      sb.append("|abstract");
+    }
+    if ((flags & ACC_STRICT) != 0) {
+      sb.append("|strictfp");
+    }
+    if ((flags & ACC_SYNTHETIC) != 0) {
+      sb.append("|synthetic");
+    }
+    if ((flags & ACC_ANNOTATION) != 0) {
+      sb.append("|annotation");
+    }
+    if ((flags & ACC_ENUM) != 0) {
+      sb.append("|enum");
+    }
+    if ((flags & ACC_CONSTRUCTOR) != 0) {
+      sb.append("|constructor");
+    }
+    if ((flags & ACC_DECLARED_SYNCHRONIZED) != 0) {
+      sb.append("|declared_synchronized");
     }
 
-    /**
-     * Returns a human-oriented string representing the given access flags,
-     * as defined on classes (not fields or methods).
-     *
-     * @param flags the flags
-     * @return {@code non-null;} human-oriented string
-     */
-    public static String classString(int flags) {
-        return humanHelper(flags, CLASS_FLAGS, CONV_CLASS);
+    if ((extra != 0) || (sb.length() == 0)) {
+      sb.append('|');
+      sb.append(Hex.u2(extra));
     }
 
-    /**
-     * Returns a human-oriented string representing the given access flags,
-     * as defined on inner classes.
-     *
-     * @param flags the flags
-     * @return {@code non-null;} human-oriented string
-     */
-    public static String innerClassString(int flags) {
-        return humanHelper(flags, INNER_CLASS_FLAGS, CONV_CLASS);
-    }
-
-    /**
-     * Returns a human-oriented string representing the given access flags,
-     * as defined on fields (not classes or methods).
-     *
-     * @param flags the flags
-     * @return {@code non-null;} human-oriented string
-     */
-    public static String fieldString(int flags) {
-        return humanHelper(flags, FIELD_FLAGS, CONV_FIELD);
-    }
-
-    /**
-     * Returns a human-oriented string representing the given access flags,
-     * as defined on methods (not classes or fields).
-     *
-     * @param flags the flags
-     * @return {@code non-null;} human-oriented string
-     */
-    public static String methodString(int flags) {
-        return humanHelper(flags, METHOD_FLAGS, CONV_METHOD);
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_PUBLIC} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_PUBLIC} flag
-     */
-    public static boolean isPublic(int flags) {
-        return (flags & ACC_PUBLIC) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_PROTECTED} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_PROTECTED} flag
-     */
-    public static boolean isProtected(int flags) {
-        return (flags & ACC_PROTECTED) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_PRIVATE} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_PRIVATE} flag
-     */
-    public static boolean isPrivate(int flags) {
-        return (flags & ACC_PRIVATE) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_STATIC} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_STATIC} flag
-     */
-    public static boolean isStatic(int flags) {
-        return (flags & ACC_STATIC) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_CONSTRUCTOR} is on in
-     * the given flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_CONSTRUCTOR} flag
-     */
-    public static boolean isConstructor(int flags) {
-        return (flags & ACC_CONSTRUCTOR) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_INTERFACE} is on in
-     * the given flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_INTERFACE} flag
-     */
-    public static boolean isInterface(int flags) {
-        return (flags & ACC_INTERFACE) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_SYNCHRONIZED} is on in
-     * the given flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_SYNCHRONIZED} flag
-     */
-    public static boolean isSynchronized(int flags) {
-        return (flags & ACC_SYNCHRONIZED) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_ABSTRACT} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_ABSTRACT} flag
-     */
-    public static boolean isAbstract(int flags) {
-        return (flags & ACC_ABSTRACT) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_NATIVE} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_NATIVE} flag
-     */
-    public static boolean isNative(int flags) {
-        return (flags & ACC_NATIVE) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_ANNOTATION} is on in the given
-     * flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_ANNOTATION} flag
-     */
-    public static boolean isAnnotation(int flags) {
-        return (flags & ACC_ANNOTATION) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_DECLARED_SYNCHRONIZED} is
-     * on in the given flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_DECLARED_SYNCHRONIZED} flag
-     */
-    public static boolean isDeclaredSynchronized(int flags) {
-        return (flags & ACC_DECLARED_SYNCHRONIZED) != 0;
-    }
-
-    /**
-     * Returns whether the flag {@code ACC_ENUM} is on in the given flags.
-     *
-     * @param flags the flags to check
-     * @return the value of the {@code ACC_ENUM} flag
-     */
-    public static boolean isEnum(int flags) {
-        return (flags & ACC_ENUM) != 0;
-    }
-
-    /**
-     * Helper to return a human-oriented string representing the given
-     * access flags.
-     *
-     * @param flags the defined flags
-     * @param mask mask for the "defined" bits
-     * @param what what the flags represent (one of {@code CONV_*})
-     * @return {@code non-null;} human-oriented string
-     */
-    private static String humanHelper(int flags, int mask, int what) {
-        StringBuffer sb = new StringBuffer(80);
-        int extra = flags & ~mask;
-
-        flags &= mask;
-
-        if ((flags & ACC_PUBLIC) != 0) {
-            sb.append("|public");
-        }
-        if ((flags & ACC_PRIVATE) != 0) {
-            sb.append("|private");
-        }
-        if ((flags & ACC_PROTECTED) != 0) {
-            sb.append("|protected");
-        }
-        if ((flags & ACC_STATIC) != 0) {
-            sb.append("|static");
-        }
-        if ((flags & ACC_FINAL) != 0) {
-            sb.append("|final");
-        }
-        if ((flags & ACC_SYNCHRONIZED) != 0) {
-            if (what == CONV_CLASS) {
-                sb.append("|super");
-            } else {
-                sb.append("|synchronized");
-            }
-        }
-        if ((flags & ACC_VOLATILE) != 0) {
-            if (what == CONV_METHOD) {
-                sb.append("|bridge");
-            } else {
-                sb.append("|volatile");
-            }
-        }
-        if ((flags & ACC_TRANSIENT) != 0) {
-            if (what == CONV_METHOD) {
-                sb.append("|varargs");
-            } else {
-                sb.append("|transient");
-            }
-        }
-        if ((flags & ACC_NATIVE) != 0) {
-            sb.append("|native");
-        }
-        if ((flags & ACC_INTERFACE) != 0) {
-            sb.append("|interface");
-        }
-        if ((flags & ACC_ABSTRACT) != 0) {
-            sb.append("|abstract");
-        }
-        if ((flags & ACC_STRICT) != 0) {
-            sb.append("|strictfp");
-        }
-        if ((flags & ACC_SYNTHETIC) != 0) {
-            sb.append("|synthetic");
-        }
-        if ((flags & ACC_ANNOTATION) != 0) {
-            sb.append("|annotation");
-        }
-        if ((flags & ACC_ENUM) != 0) {
-            sb.append("|enum");
-        }
-        if ((flags & ACC_CONSTRUCTOR) != 0) {
-            sb.append("|constructor");
-        }
-        if ((flags & ACC_DECLARED_SYNCHRONIZED) != 0) {
-            sb.append("|declared_synchronized");
-        }
-
-        if ((extra != 0) || (sb.length() == 0)) {
-            sb.append('|');
-            sb.append(Hex.u2(extra));
-        }
-
-        return sb.substring(1);
-    }
+    return sb.substring(1);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/BasicBlock.java b/dx/src/com/android/jack/dx/rop/code/BasicBlock.java
index c87fc52..6fa8306 100644
--- a/dx/src/com/android/jack/dx/rop/code/BasicBlock.java
+++ b/dx/src/com/android/jack/dx/rop/code/BasicBlock.java
@@ -25,257 +25,254 @@
  * Basic block of register-based instructions.
  */
 public final class BasicBlock implements LabeledItem {
-    /** {@code >= 0;} target label for this block */
-    private final int label;
+  /** {@code >= 0;} target label for this block */
+  private final int label;
 
-    /** {@code non-null;} list of instructions in this block */
-    private final InsnList insns;
+  /** {@code non-null;} list of instructions in this block */
+  private final InsnList insns;
 
-    /**
-     * {@code non-null;} full list of successors that this block may
-     * branch to
-     */
-    private final IntList successors;
+  /**
+   * {@code non-null;} full list of successors that this block may
+   * branch to
+   */
+  private final IntList successors;
 
-    /**
-     * {@code >= -1;} the primary / standard-flow / "default" successor, or
-     * {@code -1} if this block has no successors (that is, it
-     * exits the function/method)
-     */
-    private final int primarySuccessor;
+  /**
+   * {@code >= -1;} the primary / standard-flow / "default" successor, or
+   * {@code -1} if this block has no successors (that is, it
+   * exits the function/method)
+   */
+  private final int primarySuccessor;
 
-    /**
-     * Constructs an instance. The predecessor set is set to {@code null}.
-     *
-     * @param label {@code >= 0;} target label for this block
-     * @param insns {@code non-null;} list of instructions in this block
-     * @param successors {@code non-null;} full list of successors that this
-     * block may branch to
-     * @param primarySuccessor {@code >= -1;} the primary / standard-flow /
-     * "default" successor, or {@code -1} if this block has no
-     * successors (that is, it exits the function/method or is an
-     * unconditional throw)
-     */
-    public BasicBlock(int label, InsnList insns, IntList successors,
-                      int primarySuccessor) {
-        if (label < 0) {
-            throw new IllegalArgumentException("label < 0");
-        }
-
-        try {
-            insns.throwIfMutable();
-        } catch (NullPointerException ex) {
-            // Elucidate exception.
-            throw new NullPointerException("insns == null");
-        }
-
-        int sz = insns.size();
-
-        if (sz == 0) {
-            throw new IllegalArgumentException("insns.size() == 0");
-        }
-
-        for (int i = sz - 2; i >= 0; i--) {
-            Rop one = insns.get(i).getOpcode();
-            if (one.getBranchingness() != Rop.BRANCH_NONE) {
-                throw new IllegalArgumentException("insns[" + i + "] is a " +
-                                                   "branch or can throw");
-            }
-        }
-
-        Insn lastInsn = insns.get(sz - 1);
-        if (lastInsn.getOpcode().getBranchingness() == Rop.BRANCH_NONE) {
-            throw new IllegalArgumentException("insns does not end with " +
-                                               "a branch or throwing " +
-                                               "instruction");
-        }
-
-        try {
-            successors.throwIfMutable();
-        } catch (NullPointerException ex) {
-            // Elucidate exception.
-            throw new NullPointerException("successors == null");
-        }
-
-        if (primarySuccessor < -1) {
-            throw new IllegalArgumentException("primarySuccessor < -1");
-        }
-
-        if (primarySuccessor >= 0 && !successors.contains(primarySuccessor)) {
-            throw new IllegalArgumentException(
-                    "primarySuccessor " + primarySuccessor + " not in successors " + successors);
-        }
-
-        this.label = label;
-        this.insns = insns;
-        this.successors = successors;
-        this.primarySuccessor = primarySuccessor;
+  /**
+   * Constructs an instance. The predecessor set is set to {@code null}.
+   *
+   * @param label {@code >= 0;} target label for this block
+   * @param insns {@code non-null;} list of instructions in this block
+   * @param successors {@code non-null;} full list of successors that this
+   * block may branch to
+   * @param primarySuccessor {@code >= -1;} the primary / standard-flow /
+   * "default" successor, or {@code -1} if this block has no
+   * successors (that is, it exits the function/method or is an
+   * unconditional throw)
+   */
+  public BasicBlock(int label, InsnList insns, IntList successors, int primarySuccessor) {
+    if (label < 0) {
+      throw new IllegalArgumentException("label < 0");
     }
 
+    try {
+      insns.throwIfMutable();
+    } catch (NullPointerException ex) {
+      // Elucidate exception.
+      throw new NullPointerException("insns == null");
+    }
+
+    int sz = insns.size();
+
+    if (sz == 0) {
+      throw new IllegalArgumentException("insns.size() == 0");
+    }
+
+    for (int i = sz - 2; i >= 0; i--) {
+      Rop one = insns.get(i).getOpcode();
+      if (one.getBranchingness() != Rop.BRANCH_NONE) {
+        throw new IllegalArgumentException("insns[" + i + "] is a " + "branch or can throw");
+      }
+    }
+
+    Insn lastInsn = insns.get(sz - 1);
+    if (lastInsn.getOpcode().getBranchingness() == Rop.BRANCH_NONE) {
+      throw new IllegalArgumentException(
+          "insns does not end with " + "a branch or throwing " + "instruction");
+    }
+
+    try {
+      successors.throwIfMutable();
+    } catch (NullPointerException ex) {
+      // Elucidate exception.
+      throw new NullPointerException("successors == null");
+    }
+
+    if (primarySuccessor < -1) {
+      throw new IllegalArgumentException("primarySuccessor < -1");
+    }
+
+    if (primarySuccessor >= 0 && !successors.contains(primarySuccessor)) {
+      throw new IllegalArgumentException(
+          "primarySuccessor " + primarySuccessor + " not in successors " + successors);
+    }
+
+    this.label = label;
+    this.insns = insns;
+    this.successors = successors;
+    this.primarySuccessor = primarySuccessor;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Instances of this class compare by identity. That is,
+   * {@code x.equals(y)} is only true if {@code x == y}.
+   */
+  @Override
+  public boolean equals(Object other) {
+    return (this == other);
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Return the identity hashcode of this instance. This is proper,
+   * since instances of this class compare by identity (see {@link #equals}).
+   */
+  @Override
+  public int hashCode() {
+    return System.identityHashCode(this);
+  }
+
+  /**
+   * Gets the target label of this block.
+   *
+   * @return {@code >= 0;} the label
+   */
+  @Override
+  public int getLabel() {
+    return label;
+  }
+
+  /**
+   * Gets the list of instructions inside this block.
+   *
+   * @return {@code non-null;} the instruction list
+   */
+  public InsnList getInsns() {
+    return insns;
+  }
+
+  /**
+   * Gets the list of successors that this block may branch to.
+   *
+   * @return {@code non-null;} the successors list
+   */
+  public IntList getSuccessors() {
+    return successors;
+  }
+
+  /**
+   * Gets the primary successor of this block.
+   *
+   * @return {@code >= -1;} the primary successor, or {@code -1} if this
+   * block has no successors at all
+   */
+  public int getPrimarySuccessor() {
+    return primarySuccessor;
+  }
+
+  /**
+   * Gets the secondary successor of this block. It is only valid to call
+   * this method on blocks that have exactly two successors.
+   *
+   * @return {@code >= 0;} the secondary successor
+   */
+  public int getSecondarySuccessor() {
+    if (successors.size() != 2) {
+      throw new UnsupportedOperationException("block doesn't have exactly two successors");
+    }
+
+    int succ = successors.get(0);
+    if (succ == primarySuccessor) {
+      succ = successors.get(1);
+    }
+
+    return succ;
+  }
+
+  /**
+   * Gets the first instruction of this block. This is just a
+   * convenient shorthand for {@code getInsns().get(0)}.
+   *
+   * @return {@code non-null;} the first instruction
+   */
+  public Insn getFirstInsn() {
+    return insns.get(0);
+  }
+
+  /**
+   * Gets the last instruction of this block. This is just a
+   * convenient shorthand for {@code getInsns().getLast()}.
+   *
+   * @return {@code non-null;} the last instruction
+   */
+  public Insn getLastInsn() {
+    return insns.getLast();
+  }
+
+  /**
+   * Returns whether this block might throw an exception. This is
+   * just a convenient shorthand for {@code getLastInsn().canThrow()}.
+   *
+   * @return {@code true} iff this block might throw an
+   * exception
+   */
+  public boolean canThrow() {
+    return insns.getLast().canThrow();
+  }
+
+  /**
+   * Returns whether this block has any associated exception handlers.
+   * This is just a shorthand for inspecting the last instruction in
+   * the block to see if it could throw, and if so, whether it in fact
+   * has any associated handlers.
+   *
+   * @return {@code true} iff this block has any associated
+   * exception handlers
+   */
+  public boolean hasExceptionHandlers() {
+    Insn lastInsn = insns.getLast();
+    return lastInsn.getCatches().size() != 0;
+  }
+
+  /**
+   * Returns the exception handler types associated with this block,
+   * if any. This is just a shorthand for inspecting the last
+   * instruction in the block to see if it could throw, and if so,
+   * grabbing the catch list out of it. If not, this returns an
+   * empty list (not {@code null}).
+   *
+   * @return {@code non-null;} the exception handler types associated with
+   * this block
+   */
+  public TypeList getExceptionHandlerTypes() {
+    Insn lastInsn = insns.getLast();
+    return lastInsn.getCatches();
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the registers in each instruction are offset by the given
+   * amount.
+   *
+   * @param delta the amount to offset register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public BasicBlock withRegisterOffset(int delta) {
+    return new BasicBlock(label, insns.withRegisterOffset(delta), successors, primarySuccessor);
+  }
+
+  @Override
+  public String toString() {
+    return '{' + Hex.u2(label) + '}';
+  }
+
+  /**
+   * BasicBlock visitor interface
+   */
+  public interface Visitor {
     /**
-     * {@inheritDoc}
-     *
-     * Instances of this class compare by identity. That is,
-     * {@code x.equals(y)} is only true if {@code x == y}.
+     * Visits a basic block
+     * @param b block visited
      */
-    @Override
-    public boolean equals(Object other) {
-        return (this == other);
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * Return the identity hashcode of this instance. This is proper,
-     * since instances of this class compare by identity (see {@link #equals}).
-     */
-    @Override
-    public int hashCode() {
-        return System.identityHashCode(this);
-    }
-
-    /**
-     * Gets the target label of this block.
-     *
-     * @return {@code >= 0;} the label
-     */
-    public int getLabel() {
-        return label;
-    }
-
-    /**
-     * Gets the list of instructions inside this block.
-     *
-     * @return {@code non-null;} the instruction list
-     */
-    public InsnList getInsns() {
-        return insns;
-    }
-
-    /**
-     * Gets the list of successors that this block may branch to.
-     *
-     * @return {@code non-null;} the successors list
-     */
-    public IntList getSuccessors() {
-        return successors;
-    }
-
-    /**
-     * Gets the primary successor of this block.
-     *
-     * @return {@code >= -1;} the primary successor, or {@code -1} if this
-     * block has no successors at all
-     */
-    public int getPrimarySuccessor() {
-        return primarySuccessor;
-    }
-
-    /**
-     * Gets the secondary successor of this block. It is only valid to call
-     * this method on blocks that have exactly two successors.
-     *
-     * @return {@code >= 0;} the secondary successor
-     */
-    public int getSecondarySuccessor() {
-        if (successors.size() != 2) {
-            throw new UnsupportedOperationException(
-                    "block doesn't have exactly two successors");
-        }
-
-        int succ = successors.get(0);
-        if (succ == primarySuccessor) {
-            succ = successors.get(1);
-        }
-
-        return succ;
-    }
-
-    /**
-     * Gets the first instruction of this block. This is just a
-     * convenient shorthand for {@code getInsns().get(0)}.
-     *
-     * @return {@code non-null;} the first instruction
-     */
-    public Insn getFirstInsn() {
-        return insns.get(0);
-    }
-
-    /**
-     * Gets the last instruction of this block. This is just a
-     * convenient shorthand for {@code getInsns().getLast()}.
-     *
-     * @return {@code non-null;} the last instruction
-     */
-    public Insn getLastInsn() {
-        return insns.getLast();
-    }
-
-    /**
-     * Returns whether this block might throw an exception. This is
-     * just a convenient shorthand for {@code getLastInsn().canThrow()}.
-     *
-     * @return {@code true} iff this block might throw an
-     * exception
-     */
-    public boolean canThrow() {
-        return insns.getLast().canThrow();
-    }
-
-    /**
-     * Returns whether this block has any associated exception handlers.
-     * This is just a shorthand for inspecting the last instruction in
-     * the block to see if it could throw, and if so, whether it in fact
-     * has any associated handlers.
-     *
-     * @return {@code true} iff this block has any associated
-     * exception handlers
-     */
-    public boolean hasExceptionHandlers() {
-        Insn lastInsn = insns.getLast();
-        return lastInsn.getCatches().size() != 0;
-    }
-
-    /**
-     * Returns the exception handler types associated with this block,
-     * if any. This is just a shorthand for inspecting the last
-     * instruction in the block to see if it could throw, and if so,
-     * grabbing the catch list out of it. If not, this returns an
-     * empty list (not {@code null}).
-     *
-     * @return {@code non-null;} the exception handler types associated with
-     * this block
-     */
-    public TypeList getExceptionHandlerTypes() {
-        Insn lastInsn = insns.getLast();
-        return lastInsn.getCatches();
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the registers in each instruction are offset by the given
-     * amount.
-     *
-     * @param delta the amount to offset register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public BasicBlock withRegisterOffset(int delta) {
-        return new BasicBlock(label, insns.withRegisterOffset(delta),
-                              successors, primarySuccessor);
-    }
-
-    public String toString() {
-        return '{' + Hex.u2(label) + '}';
-    }
-
-    /**
-     * BasicBlock visitor interface
-     */
-    public interface Visitor {
-        /**
-         * Visits a basic block
-         * @param b block visited
-         */
-        public void visitBlock (BasicBlock b);
-    }
+    public void visitBlock(BasicBlock b);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/BasicBlockList.java b/dx/src/com/android/jack/dx/rop/code/BasicBlockList.java
index 3d5ddca..150dbe2 100644
--- a/dx/src/com/android/jack/dx/rop/code/BasicBlockList.java
+++ b/dx/src/com/android/jack/dx/rop/code/BasicBlockList.java
@@ -26,371 +26,374 @@
  * List of {@link BasicBlock} instances.
  */
 public final class BasicBlockList extends LabeledList {
-    /**
-     * {@code >= -1;} the count of registers required by this method or
-     * {@code -1} if not yet calculated
-     */
+  /**
+   * {@code >= -1;} the count of registers required by this method or
+   * {@code -1} if not yet calculated
+   */
+  private int regCount;
+
+  /**
+   * Constructs an instance. All indices initially contain {@code null},
+   * and the first-block label is initially {@code -1}.
+   *
+   * @param size the size of the list
+   */
+  public BasicBlockList(int size) {
+    super(size);
+
+    regCount = -1;
+  }
+
+  /**
+   * Constructs a mutable copy for {@code getMutableCopy()}.
+   *
+   * @param old block to copy
+   */
+  private BasicBlockList(BasicBlockList old) {
+    super(old);
+    regCount = old.regCount;
+  }
+
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public BasicBlock get(int n) {
+    return (BasicBlock) get0(n);
+  }
+
+  /**
+   * Sets the basic block at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param bb {@code null-ok;} the element to set at {@code n}
+   */
+  public void set(int n, BasicBlock bb) {
+    super.set(n, bb);
+
+    // Reset regCount, since it will need to be recalculated.
+    regCount = -1;
+  }
+
+  /**
+   * Returns how many registers this method requires. This is simply
+   * the maximum of register-number-plus-category referred to by this
+   * instance's instructions (indirectly through {@link BasicBlock}
+   * instances).
+   *
+   * @return {@code >= 0;} the register count
+   */
+  public int getRegCount() {
+    if (regCount == -1) {
+      RegCountVisitor visitor = new RegCountVisitor();
+      forEachInsn(visitor);
+      regCount = visitor.getRegCount();
+    }
+
+    return regCount;
+  }
+
+  /**
+   * Gets the total instruction count for this instance. This is the
+   * sum of the instruction counts of each block.
+   *
+   * @return {@code >= 0;} the total instruction count
+   */
+  public int getInstructionCount() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = (BasicBlock) getOrNull0(i);
+      if (one != null) {
+        result += one.getInsns().size();
+      }
+    }
+
+    return result;
+  }
+
+  /**
+   * Gets the total instruction count for this instance, ignoring
+   * mark-local instructions which are not actually emitted.
+   *
+   * @return {@code >= 0;} the total instruction count
+   */
+  public int getEffectiveInstructionCount() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = (BasicBlock) getOrNull0(i);
+      if (one != null) {
+        InsnList insns = one.getInsns();
+        int insnsSz = insns.size();
+
+        for (int j = 0; j < insnsSz; j++) {
+          Insn insn = insns.get(j);
+
+          if (insn.getOpcode().getOpcode() != RegOps.MARK_LOCAL) {
+            result++;
+          }
+        }
+      }
+    }
+
+    return result;
+  }
+
+  /**
+   * Gets the first block in the list with the given label, if any.
+   *
+   * @param label {@code >= 0;} the label to look for
+   * @return {@code non-null;} the so-labelled block
+   * @throws IllegalArgumentException thrown if the label isn't found
+   */
+  public BasicBlock labelToBlock(int label) {
+    int idx = indexOfLabel(label);
+
+    if (idx < 0) {
+      throw new IllegalArgumentException("no such label: " + Hex.u2(label));
+    }
+
+    return get(idx);
+  }
+
+  /**
+   * Visits each instruction of each block in the list, in order.
+   *
+   * @param visitor {@code non-null;} visitor to use
+   */
+  public void forEachInsn(Insn.Visitor visitor) {
+    int sz = size();
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = get(i);
+      InsnList insns = one.getInsns();
+      insns.forEach(visitor);
+    }
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the registers in each instruction are offset by the given
+   * amount. Mutability of the result is inherited from the
+   * original.
+   *
+   * @param delta the amount to offset register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public BasicBlockList withRegisterOffset(int delta) {
+    int sz = size();
+    BasicBlockList result = new BasicBlockList(sz);
+
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = (BasicBlock) get0(i);
+      if (one != null) {
+        result.set(i, one.withRegisterOffset(delta));
+      }
+    }
+
+    if (isImmutable()) {
+      result.setImmutable();
+    }
+
+    return result;
+  }
+
+  /**
+   * Returns a mutable copy of this list.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public BasicBlockList getMutableCopy() {
+    return new BasicBlockList(this);
+  }
+
+  /**
+   * Gets the preferred successor for the given block. If the block
+   * only has one successor, then that is the preferred successor.
+   * Otherwise, if the block has a primay successor, then that is
+   * the preferred successor. If the block has no successors, then
+   * this returns {@code null}.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code null-ok;} the preferred successor, if any
+   */
+  public BasicBlock preferredSuccessorOf(BasicBlock block) {
+    int primarySuccessor = block.getPrimarySuccessor();
+    IntList successors = block.getSuccessors();
+    int succSize = successors.size();
+
+    switch (succSize) {
+      case 0: {
+        return null;
+      }
+      case 1: {
+        return labelToBlock(successors.get(0));
+      }
+    }
+
+    if (primarySuccessor != -1) {
+      return labelToBlock(primarySuccessor);
+    } else {
+      return labelToBlock(successors.get(0));
+    }
+  }
+
+  /**
+   * Compares the catches of two blocks for equality. This includes
+   * both the catch types and target labels.
+   *
+   * @param block1 {@code non-null;} one block to compare
+   * @param block2 {@code non-null;} the other block to compare
+   * @return {@code true} if the two blocks' non-primary successors
+   * are identical
+   */
+  public boolean catchesEqual(BasicBlock block1, BasicBlock block2) {
+    TypeList catches1 = block1.getExceptionHandlerTypes();
+    TypeList catches2 = block2.getExceptionHandlerTypes();
+
+    if (!StdTypeList.equalContents(catches1, catches2)) {
+      return false;
+    }
+
+    IntList succ1 = block1.getSuccessors();
+    IntList succ2 = block2.getSuccessors();
+    int size = succ1.size(); // Both are guaranteed to be the same size.
+
+    int primary1 = block1.getPrimarySuccessor();
+    int primary2 = block2.getPrimarySuccessor();
+
+    if (((primary1 == -1) || (primary2 == -1)) && (primary1 != primary2)) {
+      /*
+       * For the current purpose, both blocks in question must
+       * either both have a primary or both not have a primary to
+       * be considered equal, and it turns out here that that's not
+       * the case.
+       */
+      return false;
+    }
+
+    for (int i = 0; i < size; i++) {
+      int label1 = succ1.get(i);
+      int label2 = succ2.get(i);
+
+      if (label1 == primary1) {
+        /*
+         * It should be the case that block2's primary is at the
+         * same index. If not, we consider the blocks unequal for
+         * the current purpose.
+         */
+        if (label2 != primary2) {
+          return false;
+        }
+        continue;
+      }
+
+      if (label1 != label2) {
+        return false;
+      }
+    }
+
+    return true;
+  }
+
+  /**
+   * Instruction visitor class for counting registers used.
+   */
+  private static class RegCountVisitor implements Insn.Visitor {
+    /** {@code >= 0;} register count in-progress */
     private int regCount;
 
     /**
-     * Constructs an instance. All indices initially contain {@code null},
-     * and the first-block label is initially {@code -1}.
-     *
-     * @param size the size of the list
+     * Constructs an instance.
      */
-    public BasicBlockList(int size) {
-        super(size);
-
-        regCount = -1;
+    public RegCountVisitor() {
+      regCount = 0;
     }
 
     /**
-     * Constructs a mutable copy for {@code getMutableCopy()}.
+     * Gets the register count.
      *
-     * @param old block to copy
-     */
-    private BasicBlockList(BasicBlockList old) {
-        super(old);
-        regCount = old.regCount;
-    }
-
-
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public BasicBlock get(int n) {
-        return (BasicBlock) get0(n);
-    }
-
-    /**
-     * Sets the basic block at the given index.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param bb {@code null-ok;} the element to set at {@code n}
-     */
-    public void set(int n, BasicBlock bb) {
-        super.set(n, bb);
-
-        // Reset regCount, since it will need to be recalculated.
-        regCount = -1;
-    }
-
-    /**
-     * Returns how many registers this method requires. This is simply
-     * the maximum of register-number-plus-category referred to by this
-     * instance's instructions (indirectly through {@link BasicBlock}
-     * instances).
-     *
-     * @return {@code >= 0;} the register count
+     * @return {@code >= 0;} the count
      */
     public int getRegCount() {
-        if (regCount == -1) {
-            RegCountVisitor visitor = new RegCountVisitor();
-            forEachInsn(visitor);
-            regCount = visitor.getRegCount();
-        }
+      return regCount;
+    }
 
-        return regCount;
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainInsn(PlainInsn insn) {
+      visit(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitPlainCstInsn(PlainCstInsn insn) {
+      visit(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitSwitchInsn(SwitchInsn insn) {
+      visit(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingCstInsn(ThrowingCstInsn insn) {
+      visit(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingInsn(ThrowingInsn insn) {
+      visit(insn);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
+      visit(insn);
     }
 
     /**
-     * Gets the total instruction count for this instance. This is the
-     * sum of the instruction counts of each block.
+     * Helper for all the {@code visit*} methods.
      *
-     * @return {@code >= 0;} the total instruction count
+     * @param insn {@code non-null;} instruction being visited
      */
-    public int getInstructionCount() {
-        int sz = size();
-        int result = 0;
+    private void visit(Insn insn) {
+      RegisterSpec result = insn.getResult();
 
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = (BasicBlock) getOrNull0(i);
-            if (one != null) {
-                result += one.getInsns().size();
-            }
-        }
+      if (result != null) {
+        processReg(result);
+      }
 
-        return result;
+      RegisterSpecList sources = insn.getSources();
+      int sz = sources.size();
+
+      for (int i = 0; i < sz; i++) {
+        processReg(sources.get(i));
+      }
     }
 
     /**
-     * Gets the total instruction count for this instance, ignoring
-     * mark-local instructions which are not actually emitted.
+     * Processes the given register spec.
      *
-     * @return {@code >= 0;} the total instruction count
+     * @param spec {@code non-null;} the register spec
      */
-    public int getEffectiveInstructionCount() {
-        int sz = size();
-        int result = 0;
+    private void processReg(RegisterSpec spec) {
+      int reg = spec.getNextReg();
 
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = (BasicBlock) getOrNull0(i);
-            if (one != null) {
-                InsnList insns = one.getInsns();
-                int insnsSz = insns.size();
-
-                for (int j = 0; j < insnsSz; j++) {
-                    Insn insn = insns.get(j);
-
-                    if (insn.getOpcode().getOpcode() != RegOps.MARK_LOCAL) {
-                        result++;
-                    }
-                }
-            }
-        }
-
-        return result;
+      if (reg > regCount) {
+        regCount = reg;
+      }
     }
-
-    /**
-     * Gets the first block in the list with the given label, if any.
-     *
-     * @param label {@code >= 0;} the label to look for
-     * @return {@code non-null;} the so-labelled block
-     * @throws IllegalArgumentException thrown if the label isn't found
-     */
-    public BasicBlock labelToBlock(int label) {
-        int idx = indexOfLabel(label);
-
-        if (idx < 0) {
-            throw new IllegalArgumentException("no such label: "
-                    + Hex.u2(label));
-        }
-
-        return get(idx);
-    }
-
-    /**
-     * Visits each instruction of each block in the list, in order.
-     *
-     * @param visitor {@code non-null;} visitor to use
-     */
-    public void forEachInsn(Insn.Visitor visitor) {
-        int sz = size();
-
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = get(i);
-            InsnList insns = one.getInsns();
-            insns.forEach(visitor);
-        }
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the registers in each instruction are offset by the given
-     * amount. Mutability of the result is inherited from the
-     * original.
-     *
-     * @param delta the amount to offset register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public BasicBlockList withRegisterOffset(int delta) {
-        int sz = size();
-        BasicBlockList result = new BasicBlockList(sz);
-
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = (BasicBlock) get0(i);
-            if (one != null) {
-                result.set(i, one.withRegisterOffset(delta));
-            }
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
-    }
-
-    /**
-     * Returns a mutable copy of this list.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public BasicBlockList getMutableCopy() {
-        return new BasicBlockList(this);
-    }
-
-    /**
-     * Gets the preferred successor for the given block. If the block
-     * only has one successor, then that is the preferred successor.
-     * Otherwise, if the block has a primay successor, then that is
-     * the preferred successor. If the block has no successors, then
-     * this returns {@code null}.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code null-ok;} the preferred successor, if any
-     */
-    public BasicBlock preferredSuccessorOf(BasicBlock block) {
-        int primarySuccessor = block.getPrimarySuccessor();
-        IntList successors = block.getSuccessors();
-        int succSize = successors.size();
-
-        switch (succSize) {
-            case 0: {
-                return null;
-            }
-            case 1: {
-                return labelToBlock(successors.get(0));
-            }
-        }
-
-        if (primarySuccessor != -1) {
-            return labelToBlock(primarySuccessor);
-        } else {
-            return labelToBlock(successors.get(0));
-        }
-    }
-
-    /**
-     * Compares the catches of two blocks for equality. This includes
-     * both the catch types and target labels.
-     *
-     * @param block1 {@code non-null;} one block to compare
-     * @param block2 {@code non-null;} the other block to compare
-     * @return {@code true} if the two blocks' non-primary successors
-     * are identical
-     */
-    public boolean catchesEqual(BasicBlock block1, BasicBlock block2) {
-        TypeList catches1 = block1.getExceptionHandlerTypes();
-        TypeList catches2 = block2.getExceptionHandlerTypes();
-
-        if (!StdTypeList.equalContents(catches1, catches2)) {
-            return false;
-        }
-
-        IntList succ1 = block1.getSuccessors();
-        IntList succ2 = block2.getSuccessors();
-        int size = succ1.size(); // Both are guaranteed to be the same size.
-
-        int primary1 = block1.getPrimarySuccessor();
-        int primary2 = block2.getPrimarySuccessor();
-
-        if (((primary1 == -1) || (primary2 == -1))
-                && (primary1 != primary2)) {
-            /*
-             * For the current purpose, both blocks in question must
-             * either both have a primary or both not have a primary to
-             * be considered equal, and it turns out here that that's not
-             * the case.
-             */
-            return false;
-        }
-
-        for (int i = 0; i < size; i++) {
-            int label1 = succ1.get(i);
-            int label2 = succ2.get(i);
-
-            if (label1 == primary1) {
-                /*
-                 * It should be the case that block2's primary is at the
-                 * same index. If not, we consider the blocks unequal for
-                 * the current purpose.
-                 */
-                if (label2 != primary2) {
-                    return false;
-                }
-                continue;
-            }
-
-            if (label1 != label2) {
-                return false;
-            }
-        }
-
-        return true;
-    }
-
-    /**
-     * Instruction visitor class for counting registers used.
-     */
-    private static class RegCountVisitor
-            implements Insn.Visitor {
-        /** {@code >= 0;} register count in-progress */
-        private int regCount;
-
-        /**
-         * Constructs an instance.
-         */
-        public RegCountVisitor() {
-            regCount = 0;
-        }
-
-        /**
-         * Gets the register count.
-         *
-         * @return {@code >= 0;} the count
-         */
-        public int getRegCount() {
-            return regCount;
-        }
-
-        /** {@inheritDoc} */
-        public void visitPlainInsn(PlainInsn insn) {
-            visit(insn);
-        }
-
-        /** {@inheritDoc} */
-        public void visitPlainCstInsn(PlainCstInsn insn) {
-            visit(insn);
-        }
-
-        /** {@inheritDoc} */
-        public void visitSwitchInsn(SwitchInsn insn) {
-            visit(insn);
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingCstInsn(ThrowingCstInsn insn) {
-            visit(insn);
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingInsn(ThrowingInsn insn) {
-            visit(insn);
-        }
-
-        /** {@inheritDoc} */
-        public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
-            visit(insn);
-        }
-
-        /**
-         * Helper for all the {@code visit*} methods.
-         *
-         * @param insn {@code non-null;} instruction being visited
-         */
-        private void visit(Insn insn) {
-            RegisterSpec result = insn.getResult();
-
-            if (result != null) {
-                processReg(result);
-            }
-
-            RegisterSpecList sources = insn.getSources();
-            int sz = sources.size();
-
-            for (int i = 0; i < sz; i++) {
-                processReg(sources.get(i));
-            }
-        }
-
-        /**
-         * Processes the given register spec.
-         *
-         * @param spec {@code non-null;} the register spec
-         */
-        private void processReg(RegisterSpec spec) {
-            int reg = spec.getNextReg();
-
-            if (reg > regCount) {
-                regCount = reg;
-            }
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/ConservativeTranslationAdvice.java b/dx/src/com/android/jack/dx/rop/code/ConservativeTranslationAdvice.java
index 6a4ee22..3077f81 100644
--- a/dx/src/com/android/jack/dx/rop/code/ConservativeTranslationAdvice.java
+++ b/dx/src/com/android/jack/dx/rop/code/ConservativeTranslationAdvice.java
@@ -20,33 +20,32 @@
  * Implementation of {@link TranslationAdvice} which conservatively answers
  * {@code false} to all methods.
  */
-public final class ConservativeTranslationAdvice
-        implements TranslationAdvice {
-    /** {@code non-null;} standard instance of this class */
-    public static final ConservativeTranslationAdvice THE_ONE =
-        new ConservativeTranslationAdvice();
+public final class ConservativeTranslationAdvice implements TranslationAdvice {
+  /** {@code non-null;} standard instance of this class */
+  public static final ConservativeTranslationAdvice THE_ONE = new ConservativeTranslationAdvice();
 
-    /**
-     * This class is not publicly instantiable. Use {@link #THE_ONE}.
-     */
-    private ConservativeTranslationAdvice() {
-        // This space intentionally left blank.
-    }
+  /**
+   * This class is not publicly instantiable. Use {@link #THE_ONE}.
+   */
+  private ConservativeTranslationAdvice() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    public boolean hasConstantOperation(Rop opcode,
-            RegisterSpec sourceA, RegisterSpec sourceB) {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean hasConstantOperation(Rop opcode, RegisterSpec sourceA, RegisterSpec sourceB) {
+    return false;
+  }
 
-    /** {@inheritDoc} */
-    public boolean requiresSourcesInOrder(Rop opcode,
-            RegisterSpecList sources) {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean requiresSourcesInOrder(Rop opcode, RegisterSpecList sources) {
+    return false;
+  }
 
-    /** {@inheritDoc} */
-    public int getMaxOptimalRegisterCount() {
-        return Integer.MAX_VALUE;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int getMaxOptimalRegisterCount() {
+    return Integer.MAX_VALUE;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/CstInsn.java b/dx/src/com/android/jack/dx/rop/code/CstInsn.java
index 4e5a7fe..c639863 100644
--- a/dx/src/com/android/jack/dx/rop/code/CstInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/CstInsn.java
@@ -21,54 +21,52 @@
 /**
  * Instruction which contains an explicit reference to a constant.
  */
-public abstract class CstInsn
-        extends Insn {
-    /** {@code non-null;} the constant */
-    private final Constant cst;
+public abstract class CstInsn extends Insn {
+  /** {@code non-null;} the constant */
+  private final Constant cst;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param sources {@code non-null;} specs for all the sources
-     * @param cst {@code non-null;} constant
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param sources {@code non-null;} specs for all the sources
+   * @param cst {@code non-null;} constant
+   */
+  public CstInsn(Rop opcode, SourcePosition position, RegisterSpec result, RegisterSpecList sources,
+      Constant cst) {
+    super(opcode, position, result, sources);
+
+    if (cst == null) {
+      throw new NullPointerException("cst == null");
+    }
+
+    this.cst = cst;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String getInlineString() {
+    return cst.toHuman();
+  }
+
+  /**
+   * Gets the constant.
+   *
+   * @return {@code non-null;} the constant
+   */
+  public Constant getConstant() {
+    return cst;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean contentEquals(Insn b) {
+    /*
+     * The cast (CstInsn)b below should always succeed since
+     * Insn.contentEquals compares classes of this and b.
      */
-    public CstInsn(Rop opcode, SourcePosition position, RegisterSpec result,
-                   RegisterSpecList sources, Constant cst) {
-        super(opcode, position, result, sources);
-
-        if (cst == null) {
-            throw new NullPointerException("cst == null");
-        }
-
-        this.cst = cst;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String getInlineString() {
-        return cst.toHuman();
-    }
-
-    /**
-     * Gets the constant.
-     *
-     * @return {@code non-null;} the constant
-     */
-    public Constant getConstant() {
-        return cst;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean contentEquals(Insn b) {
-        /*
-         * The cast (CstInsn)b below should always succeed since
-         * Insn.contentEquals compares classes of this and b.
-         */
-        return super.contentEquals(b)
-                && cst.equals(((CstInsn)b).getConstant());
-    }
+    return super.contentEquals(b) && cst.equals(((CstInsn) b).getConstant());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/DexTranslationAdvice.java b/dx/src/com/android/jack/dx/rop/code/DexTranslationAdvice.java
index 4654a39..10d647f 100644
--- a/dx/src/com/android/jack/dx/rop/code/DexTranslationAdvice.java
+++ b/dx/src/com/android/jack/dx/rop/code/DexTranslationAdvice.java
@@ -23,108 +23,105 @@
  * Implementation of {@link TranslationAdvice} which represents what
  * the dex format will be able to represent.
  */
-public final class DexTranslationAdvice
-        implements TranslationAdvice {
-    /** {@code non-null;} standard instance of this class */
-    public static final DexTranslationAdvice THE_ONE =
-        new DexTranslationAdvice();
+public final class DexTranslationAdvice implements TranslationAdvice {
+  /** {@code non-null;} standard instance of this class */
+  public static final DexTranslationAdvice THE_ONE = new DexTranslationAdvice();
 
-    /** debug advice for disabling invoke-range optimization */
-    public static final DexTranslationAdvice NO_SOURCES_IN_ORDER =
-        new DexTranslationAdvice(true);
+  /** debug advice for disabling invoke-range optimization */
+  public static final DexTranslationAdvice NO_SOURCES_IN_ORDER = new DexTranslationAdvice(true);
 
-    /**
-     * The minimum source width, in register units, for an invoke
-     * instruction that requires its sources to be in order and contiguous.
-     */
-    private static final int MIN_INVOKE_IN_ORDER = 6;
+  /**
+   * The minimum source width, in register units, for an invoke
+   * instruction that requires its sources to be in order and contiguous.
+   */
+  private static final int MIN_INVOKE_IN_ORDER = 6;
 
-    /** when true: always returns false for requiresSourcesInOrder */
-    private final boolean disableSourcesInOrder;
+  /** when true: always returns false for requiresSourcesInOrder */
+  private final boolean disableSourcesInOrder;
 
-    /**
-     * This class is not publicly instantiable. Use {@link #THE_ONE}.
-     */
-    private DexTranslationAdvice() {
-        disableSourcesInOrder = false;
+  /**
+   * This class is not publicly instantiable. Use {@link #THE_ONE}.
+   */
+  private DexTranslationAdvice() {
+    disableSourcesInOrder = false;
+  }
+
+  private DexTranslationAdvice(boolean disableInvokeRange) {
+    this.disableSourcesInOrder = disableInvokeRange;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean hasConstantOperation(Rop opcode, RegisterSpec sourceA, RegisterSpec sourceB) {
+    if (sourceA.getType() != Type.INT) {
+      return false;
     }
 
-    private DexTranslationAdvice(boolean disableInvokeRange) {
-        this.disableSourcesInOrder = disableInvokeRange;
+    // Return false if second source isn't a constant
+    if (!(sourceB.getTypeBearer() instanceof CstInteger)) {
+      // Except for rsub-int (reverse sub) where first source is constant
+      if (sourceA.getTypeBearer() instanceof CstInteger && opcode.getOpcode() == RegOps.SUB) {
+        CstInteger cst = (CstInteger) sourceA.getTypeBearer();
+        return cst.fitsIn16Bits();
+      } else {
+        return false;
+      }
     }
 
-    /** {@inheritDoc} */
-    public boolean hasConstantOperation(Rop opcode,
-            RegisterSpec sourceA, RegisterSpec sourceB) {
-        if (sourceA.getType() != Type.INT) {
-            return false;
-        }
+    CstInteger cst = (CstInteger) sourceB.getTypeBearer();
 
-        // Return false if second source isn't a constant
-        if (! (sourceB.getTypeBearer() instanceof CstInteger)) {
-            // Except for rsub-int (reverse sub) where first source is constant
-            if (sourceA.getTypeBearer() instanceof CstInteger &&
-                    opcode.getOpcode() == RegOps.SUB) {
-                CstInteger cst = (CstInteger) sourceA.getTypeBearer();
-                return cst.fitsIn16Bits();
-            } else {
-                return false;
-            }
-        }
+    switch (opcode.getOpcode()) {
+    // These have 8 and 16 bit cst representations
+      case RegOps.REM:
+      case RegOps.ADD:
+      case RegOps.MUL:
+      case RegOps.DIV:
+      case RegOps.AND:
+      case RegOps.OR:
+      case RegOps.XOR:
+        return cst.fitsIn16Bits();
+    // These only have 8 bit cst reps
+      case RegOps.SHL:
+      case RegOps.SHR:
+      case RegOps.USHR:
+        return cst.fitsIn8Bits();
+    // No sub-const insn, so check if equivalent add-const fits
+      case RegOps.SUB:
+        CstInteger cst2 = CstInteger.make(-cst.getValue());
+        return cst2.fitsIn16Bits();
+      default:
+        return false;
+    }
+  }
 
-        CstInteger cst = (CstInteger) sourceB.getTypeBearer();
+  /** {@inheritDoc} */
+  @Override
+  public boolean requiresSourcesInOrder(Rop opcode, RegisterSpecList sources) {
 
-        switch (opcode.getOpcode()) {
-            // These have 8 and 16 bit cst representations
-            case RegOps.REM:
-            case RegOps.ADD:
-            case RegOps.MUL:
-            case RegOps.DIV:
-            case RegOps.AND:
-            case RegOps.OR:
-            case RegOps.XOR:
-                return cst.fitsIn16Bits();
-            // These only have 8 bit cst reps
-            case RegOps.SHL:
-            case RegOps.SHR:
-            case RegOps.USHR:
-                return cst.fitsIn8Bits();
-            // No sub-const insn, so check if equivalent add-const fits
-            case RegOps.SUB:
-                CstInteger cst2 = CstInteger.make(-cst.getValue());
-                return cst2.fitsIn16Bits();
-            default:
-                return false;
-        }
+    return !disableSourcesInOrder && opcode.isCallLike()
+        && totalRopWidth(sources) >= MIN_INVOKE_IN_ORDER;
+  }
+
+  /**
+   * Calculates the total rop width of the list of SSA registers
+   *
+   * @param sources {@code non-null;} list of SSA registers
+   * @return {@code >= 0;} rop-form width in register units
+   */
+  private int totalRopWidth(RegisterSpecList sources) {
+    int sz = sources.size();
+    int total = 0;
+
+    for (int i = 0; i < sz; i++) {
+      total += sources.get(i).getCategory();
     }
 
-    /** {@inheritDoc} */
-    public boolean requiresSourcesInOrder(Rop opcode,
-            RegisterSpecList sources) {
+    return total;
+  }
 
-        return !disableSourcesInOrder && opcode.isCallLike()
-                && totalRopWidth(sources) >= MIN_INVOKE_IN_ORDER;
-    }
-
-    /**
-     * Calculates the total rop width of the list of SSA registers
-     *
-     * @param sources {@code non-null;} list of SSA registers
-     * @return {@code >= 0;} rop-form width in register units
-     */
-    private int totalRopWidth(RegisterSpecList sources) {
-        int sz = sources.size();
-        int total = 0;
-
-        for (int i = 0; i < sz; i++) {
-            total += sources.get(i).getCategory();
-        }
-
-        return total;
-    }
-
-    /** {@inheritDoc} */
-    public int getMaxOptimalRegisterCount() {
-        return 16;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int getMaxOptimalRegisterCount() {
+    return 16;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/Exceptions.java b/dx/src/com/android/jack/dx/rop/code/Exceptions.java
index f91f459..ff2fe73 100644
--- a/dx/src/com/android/jack/dx/rop/code/Exceptions.java
+++ b/dx/src/com/android/jack/dx/rop/code/Exceptions.java
@@ -23,111 +23,103 @@
  * Common exception types.
  */
 public final class Exceptions {
-    /** {@code non-null;} the type {@code java.lang.ArithmeticException} */
-    public static final Type TYPE_ArithmeticException =
-        Type.intern("Ljava/lang/ArithmeticException;");
+  /** {@code non-null;} the type {@code java.lang.ArithmeticException} */
+  public static final Type TYPE_ArithmeticException =
+      Type.intern("Ljava/lang/ArithmeticException;");
 
-    /**
-     * {@code non-null;} the type
-     * {@code java.lang.ArrayIndexOutOfBoundsException}
-     */
-    public static final Type TYPE_ArrayIndexOutOfBoundsException =
-        Type.intern("Ljava/lang/ArrayIndexOutOfBoundsException;");
+  /**
+   * {@code non-null;} the type
+   * {@code java.lang.ArrayIndexOutOfBoundsException}
+   */
+  public static final Type TYPE_ArrayIndexOutOfBoundsException =
+      Type.intern("Ljava/lang/ArrayIndexOutOfBoundsException;");
 
-    /** {@code non-null;} the type {@code java.lang.ArrayStoreException} */
-    public static final Type TYPE_ArrayStoreException =
-        Type.intern("Ljava/lang/ArrayStoreException;");
+  /** {@code non-null;} the type {@code java.lang.ArrayStoreException} */
+  public static final Type TYPE_ArrayStoreException =
+      Type.intern("Ljava/lang/ArrayStoreException;");
 
-    /** {@code non-null;} the type {@code java.lang.ClassCastException} */
-    public static final Type TYPE_ClassCastException =
-        Type.intern("Ljava/lang/ClassCastException;");
+  /** {@code non-null;} the type {@code java.lang.ClassCastException} */
+  public static final Type TYPE_ClassCastException = Type.intern("Ljava/lang/ClassCastException;");
 
-    /** {@code non-null;} the type {@code java.lang.Error} */
-    public static final Type TYPE_Error = Type.intern("Ljava/lang/Error;");
+  /** {@code non-null;} the type {@code java.lang.Error} */
+  public static final Type TYPE_Error = Type.intern("Ljava/lang/Error;");
 
-    /**
-     * {@code non-null;} the type
-     * {@code java.lang.IllegalMonitorStateException}
-     */
-    public static final Type TYPE_IllegalMonitorStateException =
-        Type.intern("Ljava/lang/IllegalMonitorStateException;");
+  /**
+   * {@code non-null;} the type
+   * {@code java.lang.IllegalMonitorStateException}
+   */
+  public static final Type TYPE_IllegalMonitorStateException =
+      Type.intern("Ljava/lang/IllegalMonitorStateException;");
 
-    /** {@code non-null;} the type {@code java.lang.NegativeArraySizeException} */
-    public static final Type TYPE_NegativeArraySizeException =
-        Type.intern("Ljava/lang/NegativeArraySizeException;");
+  /** {@code non-null;} the type {@code java.lang.NegativeArraySizeException} */
+  public static final Type TYPE_NegativeArraySizeException =
+      Type.intern("Ljava/lang/NegativeArraySizeException;");
 
-    /** {@code non-null;} the type {@code java.lang.NullPointerException} */
-    public static final Type TYPE_NullPointerException =
-        Type.intern("Ljava/lang/NullPointerException;");
+  /** {@code non-null;} the type {@code java.lang.NullPointerException} */
+  public static final Type TYPE_NullPointerException =
+      Type.intern("Ljava/lang/NullPointerException;");
 
-    /** {@code non-null;} the list {@code [java.lang.Error]} */
-    public static final StdTypeList LIST_Error = StdTypeList.make(TYPE_Error);
+  /** {@code non-null;} the list {@code [java.lang.Error]} */
+  public static final StdTypeList LIST_Error = StdTypeList.make(TYPE_Error);
 
-    /**
-     * {@code non-null;} the list {@code[java.lang.Error,
-     * java.lang.ArithmeticException]}
-     */
-    public static final StdTypeList LIST_Error_ArithmeticException =
-        StdTypeList.make(TYPE_Error, TYPE_ArithmeticException);
+  /**
+   * {@code non-null;} the list {@code[java.lang.Error,
+   * java.lang.ArithmeticException]}
+   */
+  public static final StdTypeList LIST_Error_ArithmeticException =
+      StdTypeList.make(TYPE_Error, TYPE_ArithmeticException);
 
-    /**
-     * {@code non-null;} the list {@code[java.lang.Error,
-     * java.lang.ClassCastException]}
-     */
-    public static final StdTypeList LIST_Error_ClassCastException =
-        StdTypeList.make(TYPE_Error, TYPE_ClassCastException);
+  /**
+   * {@code non-null;} the list {@code[java.lang.Error,
+   * java.lang.ClassCastException]}
+   */
+  public static final StdTypeList LIST_Error_ClassCastException =
+      StdTypeList.make(TYPE_Error, TYPE_ClassCastException);
 
-    /**
-     * {@code non-null;} the list {@code [java.lang.Error,
-     * java.lang.NegativeArraySizeException]}
-     */
-    public static final StdTypeList LIST_Error_NegativeArraySizeException =
-        StdTypeList.make(TYPE_Error, TYPE_NegativeArraySizeException);
+  /**
+   * {@code non-null;} the list {@code [java.lang.Error,
+   * java.lang.NegativeArraySizeException]}
+   */
+  public static final StdTypeList LIST_Error_NegativeArraySizeException =
+      StdTypeList.make(TYPE_Error, TYPE_NegativeArraySizeException);
 
-    /**
-     * {@code non-null;} the list {@code [java.lang.Error,
-     * java.lang.NullPointerException]}
-     */
-    public static final StdTypeList LIST_Error_NullPointerException =
-        StdTypeList.make(TYPE_Error, TYPE_NullPointerException);
+  /**
+   * {@code non-null;} the list {@code [java.lang.Error,
+   * java.lang.NullPointerException]}
+   */
+  public static final StdTypeList LIST_Error_NullPointerException =
+      StdTypeList.make(TYPE_Error, TYPE_NullPointerException);
 
-    /**
-     * {@code non-null;} the list {@code [java.lang.Error,
-     * java.lang.NullPointerException,
-     * java.lang.ArrayIndexOutOfBoundsException]}
-     */
-    public static final StdTypeList LIST_Error_Null_ArrayIndexOutOfBounds =
-        StdTypeList.make(TYPE_Error,
-                      TYPE_NullPointerException,
-                      TYPE_ArrayIndexOutOfBoundsException);
+  /**
+   * {@code non-null;} the list {@code [java.lang.Error,
+   * java.lang.NullPointerException,
+   * java.lang.ArrayIndexOutOfBoundsException]}
+   */
+  public static final StdTypeList LIST_Error_Null_ArrayIndexOutOfBounds =
+      StdTypeList.make(TYPE_Error, TYPE_NullPointerException, TYPE_ArrayIndexOutOfBoundsException);
 
-    /**
-     * {@code non-null;} the list {@code [java.lang.Error,
-     * java.lang.NullPointerException,
-     * java.lang.ArrayIndexOutOfBoundsException,
-     * java.lang.ArrayStoreException]}
-     */
-    public static final StdTypeList LIST_Error_Null_ArrayIndex_ArrayStore =
-        StdTypeList.make(TYPE_Error,
-                      TYPE_NullPointerException,
-                      TYPE_ArrayIndexOutOfBoundsException,
-                      TYPE_ArrayStoreException);
+  /**
+   * {@code non-null;} the list {@code [java.lang.Error,
+   * java.lang.NullPointerException,
+   * java.lang.ArrayIndexOutOfBoundsException,
+   * java.lang.ArrayStoreException]}
+   */
+  public static final StdTypeList LIST_Error_Null_ArrayIndex_ArrayStore = StdTypeList.make(
+      TYPE_Error, TYPE_NullPointerException, TYPE_ArrayIndexOutOfBoundsException,
+      TYPE_ArrayStoreException);
 
-    /**
-     * {@code non-null;} the list {@code [java.lang.Error,
-     * java.lang.NullPointerException,
-     * java.lang.IllegalMonitorStateException]}
-     */
-    public static final StdTypeList
-        LIST_Error_Null_IllegalMonitorStateException =
-        StdTypeList.make(TYPE_Error,
-                      TYPE_NullPointerException,
-                      TYPE_IllegalMonitorStateException);
+  /**
+   * {@code non-null;} the list {@code [java.lang.Error,
+   * java.lang.NullPointerException,
+   * java.lang.IllegalMonitorStateException]}
+   */
+  public static final StdTypeList LIST_Error_Null_IllegalMonitorStateException =
+      StdTypeList.make(TYPE_Error, TYPE_NullPointerException, TYPE_IllegalMonitorStateException);
 
-    /**
-     * This class is uninstantiable.
-     */
-    private Exceptions() {
-        // This space intentionally left blank.
-    }
+  /**
+   * This class is uninstantiable.
+   */
+  private Exceptions() {
+    // This space intentionally left blank.
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/FillArrayDataInsn.java b/dx/src/com/android/jack/dx/rop/code/FillArrayDataInsn.java
index f92fd71..fb0ebb3 100644
--- a/dx/src/com/android/jack/dx/rop/code/FillArrayDataInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/FillArrayDataInsn.java
@@ -27,90 +27,84 @@
  * Instruction which fills a newly created array with a predefined list of
  * constant values.
  */
-public final class FillArrayDataInsn
-        extends Insn {
+public final class FillArrayDataInsn extends Insn {
 
-    /** non-null: initial values to fill the newly created array */
-    private final ArrayList<Constant> initValues;
+  /** non-null: initial values to fill the newly created array */
+  private final ArrayList<Constant> initValues;
 
-    /**
-     * non-null: type of the array. Will be used to determine the width of
-     * elements in the array-data table.
-     */
-    private final Constant arrayType;
+  /**
+   * non-null: type of the array. Will be used to determine the width of
+   * elements in the array-data table.
+   */
+  private final Constant arrayType;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param sources {@code non-null;} specs for all the sources
-     * @param initValues {@code non-null;} list of initial values to fill the array
-     * @param cst {@code non-null;} type of the new array
-     */
-    public FillArrayDataInsn(Rop opcode, SourcePosition position,
-                             RegisterSpecList sources,
-                             ArrayList<Constant> initValues,
-                             Constant cst) {
-        super(opcode, position, null, sources);
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param sources {@code non-null;} specs for all the sources
+   * @param initValues {@code non-null;} list of initial values to fill the array
+   * @param cst {@code non-null;} type of the new array
+   */
+  public FillArrayDataInsn(Rop opcode, SourcePosition position, RegisterSpecList sources,
+      ArrayList<Constant> initValues, Constant cst) {
+    super(opcode, position, null, sources);
 
-        if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
-
-        this.initValues = initValues;
-        this.arrayType = cst;
+    if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
 
+    this.initValues = initValues;
+    this.arrayType = cst;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return StdTypeList.EMPTY;
-    }
 
-    /**
-     * Return the list of init values
-     * @return {@code non-null;} list of init values
-     */
-    public ArrayList<Constant> getInitValues() {
-        return initValues;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return StdTypeList.EMPTY;
+  }
 
-    /**
-     * Return the type of the newly created array
-     * @return {@code non-null;} array type
-     */
-    public Constant getConstant() {
-        return arrayType;
-    }
+  /**
+   * Return the list of init values
+   * @return {@code non-null;} list of init values
+   */
+  public ArrayList<Constant> getInitValues() {
+    return initValues;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitFillArrayDataInsn(this);
-    }
+  /**
+   * Return the type of the newly created array
+   * @return {@code non-null;} array type
+   */
+  public Constant getConstant() {
+    return arrayType;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        throw new  UnsupportedOperationException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitFillArrayDataInsn(this);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new FillArrayDataInsn(getOpcode(), getPosition(),
-                                     getSources().withOffset(delta),
-                                     initValues, arrayType);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    throw new UnsupportedOperationException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new FillArrayDataInsn(getOpcode(), getPosition(), getSources().withOffset(delta),
+        initValues, arrayType);
+  }
 
-        return new FillArrayDataInsn(getOpcode(), getPosition(),
-                                     sources, initValues, arrayType);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
+
+    return new FillArrayDataInsn(getOpcode(), getPosition(), sources, initValues, arrayType);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/Insn.java b/dx/src/com/android/jack/dx/rop/code/Insn.java
index 312f051..11475a6 100644
--- a/dx/src/com/android/jack/dx/rop/code/Insn.java
+++ b/dx/src/com/android/jack/dx/rop/code/Insn.java
@@ -28,429 +28,432 @@
  * information.
  */
 public abstract class Insn implements ToHuman {
-    /** {@code non-null;} opcode */
-    private final Rop opcode;
+  /** {@code non-null;} opcode */
+  private final Rop opcode;
 
-    /** {@code non-null;} source position */
-    private final SourcePosition position;
+  /** {@code non-null;} source position */
+  private final SourcePosition position;
 
-    /** {@code null-ok;} spec for the result of this instruction, if any */
-    private final RegisterSpec result;
+  /** {@code null-ok;} spec for the result of this instruction, if any */
+  private final RegisterSpec result;
 
-    /** {@code non-null;} specs for all the sources of this instruction */
-    private final RegisterSpecList sources;
+  /** {@code non-null;} specs for all the sources of this instruction */
+  private final RegisterSpecList sources;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param sources {@code non-null;} specs for all the sources
-     */
-    public Insn(Rop opcode, SourcePosition position, RegisterSpec result,
-                RegisterSpecList sources) {
-        if (opcode == null) {
-            throw new NullPointerException("opcode == null");
-        }
-
-        if (position == null) {
-            throw new NullPointerException("position == null");
-        }
-
-        if (sources == null) {
-            throw new NullPointerException("sources == null");
-        }
-
-        this.opcode = opcode;
-        this.position = position;
-        this.result = result;
-        this.sources = sources;
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param sources {@code non-null;} specs for all the sources
+   */
+  public Insn(Rop opcode, SourcePosition position, RegisterSpec result, RegisterSpecList sources) {
+    if (opcode == null) {
+      throw new NullPointerException("opcode == null");
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * Instances of this class compare by identity. That is,
-     * {@code x.equals(y)} is only true if {@code x == y}.
-     */
-    @Override
-    public final boolean equals(Object other) {
-        return (this == other);
+    if (position == null) {
+      throw new NullPointerException("position == null");
     }
 
+    if (sources == null) {
+      throw new NullPointerException("sources == null");
+    }
+
+    this.opcode = opcode;
+    this.position = position;
+    this.result = result;
+    this.sources = sources;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Instances of this class compare by identity. That is,
+   * {@code x.equals(y)} is only true if {@code x == y}.
+   */
+  @Override
+  public final boolean equals(Object other) {
+    return (this == other);
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * This implementation returns the identity hashcode of this
+   * instance. This is proper, since instances of this class compare
+   * by identity (see {@link #equals}).
+   */
+  @Override
+  public final int hashCode() {
+    return System.identityHashCode(this);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return toStringWithInline(getInlineString());
+  }
+
+  /**
+   * Gets a human-oriented (and slightly lossy) string for this instance.
+   *
+   * @return {@code non-null;} the human string form
+   */
+  @Override
+  public String toHuman() {
+    return toHumanWithInline(getInlineString());
+  }
+
+  /**
+   * Gets an "inline" string portion for toHuman(), if available. This
+   * is the portion that appears after the Rop opcode
+   *
+   * @return {@code null-ok;} if non-null, the inline text for toHuman()
+   */
+  public String getInlineString() {
+    return null;
+  }
+
+  /**
+   * Gets the opcode.
+   *
+   * @return {@code non-null;} the opcode
+   */
+  public final Rop getOpcode() {
+    return opcode;
+  }
+
+  /**
+   * Gets the source position.
+   *
+   * @return {@code non-null;} the source position
+   */
+  public final SourcePosition getPosition() {
+    return position;
+  }
+
+  /**
+   * Gets the result spec, if any. A return value of {@code null}
+   * means this instruction returns nothing.
+   *
+   * @return {@code null-ok;} the result spec, if any
+   */
+  public final RegisterSpec getResult() {
+    return result;
+  }
+
+  /**
+   * Gets the spec of a local variable assignment that occurs at this
+   * instruction, or null if no local variable assignment occurs. This
+   * may be the result register, or for {@code mark-local} insns
+   * it may be the source.
+   *
+   * @return {@code null-ok;} a named register spec or null
+   */
+  public final RegisterSpec getLocalAssignment() {
+    RegisterSpec assignment;
+    if (opcode.getOpcode() == RegOps.MARK_LOCAL) {
+      assignment = sources.get(0);
+    } else {
+      assignment = result;
+    }
+
+    if (assignment == null) {
+      return null;
+    }
+
+    LocalItem localItem = assignment.getLocalItem();
+
+    if (localItem == null) {
+      return null;
+    }
+
+    return assignment;
+  }
+
+  /**
+   * Gets the source specs.
+   *
+   * @return {@code non-null;} the source specs
+   */
+  public final RegisterSpecList getSources() {
+    return sources;
+  }
+
+  /**
+   * Gets whether this instruction can possibly throw an exception. This
+   * is just a convenient wrapper for {@code getOpcode().canThrow()}.
+   *
+   * @return {@code true} iff this instruction can possibly throw
+   */
+  public final boolean canThrow() {
+    return opcode.canThrow();
+  }
+
+  /**
+   * Gets the list of possibly-caught exceptions. This returns {@link
+   * StdTypeList#EMPTY} if this instruction has no handlers,
+   * which can be <i>either</i> if this instruction can't possibly
+   * throw or if it merely doesn't handle any of its possible
+   * exceptions. To determine whether this instruction can throw,
+   * use {@link #canThrow}.
+   *
+   * @return {@code non-null;} the catches list
+   */
+  public abstract TypeList getCatches();
+
+  /**
+   * Calls the appropriate method on the given visitor, depending on the
+   * class of this instance. Subclasses must override this.
+   *
+   * @param visitor {@code non-null;} the visitor to call on
+   */
+  public abstract void accept(Visitor visitor);
+
+  /**
+   * Returns an instance that is just like this one, except that it
+   * has a catch list with the given item appended to the end. This
+   * method throws an exception if this instance can't possibly
+   * throw. To determine whether this instruction can throw, use
+   * {@link #canThrow}.
+   *
+   * @param type {@code non-null;} type to append to the catch list
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract Insn withAddedCatch(Type type);
+
+  /**
+   * Returns an instance that is just like this one, except that all
+   * register references have been offset by the given delta.
+   *
+   * @param delta the amount to offset register references by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract Insn withRegisterOffset(int delta);
+
+  /**
+   * Returns an instance that is just like this one, except that, if
+   * possible, the insn is converted into a version in which a source
+   * (if it is a constant) is represented directly rather than as a
+   * register reference. {@code this} is returned in cases where the
+   * translation is not possible.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public Insn withSourceLiteral() {
+    return this;
+  }
+
+  /**
+   * Returns an exact copy of this Insn
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public Insn copy() {
+    return withRegisterOffset(0);
+  }
+
+
+  /**
+   * Compares, handling nulls safely
+   *
+   * @param a first object
+   * @param b second object
+   * @return true if they're equal or both null.
+   */
+  private static boolean equalsHandleNulls(Object a, Object b) {
+    return (a == b) || ((a != null) && a.equals(b));
+  }
+
+  /**
+   * Compares Insn contents, since {@code Insn.equals()} is defined
+   * to be an identity compare. Insn's are {@code contentEquals()}
+   * if they have the same opcode, registers, source position, and other
+   * metadata.
+   *
+   * @return true in the case described above
+   */
+  public boolean contentEquals(Insn b) {
+    return opcode == b.getOpcode() && position.equals(b.getPosition())
+        && (getClass() == b.getClass()) && equalsHandleNulls(result, b.getResult())
+        && equalsHandleNulls(sources, b.getSources())
+        && StdTypeList.equalContents(getCatches(), b.getCatches());
+  }
+
+  /**
+   * Returns an instance that is just like this one, except
+   * with new result and source registers.
+   *
+   * @param result {@code null-ok;} new result register
+   * @param sources {@code non-null;} new sources registers
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public abstract Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources);
+
+  /**
+   * Returns the string form of this instance, with the given bit added in
+   * the standard location for an inline argument.
+   *
+   * @param extra {@code null-ok;} the inline argument string
+   * @return {@code non-null;} the string form
+   */
+  protected final String toStringWithInline(String extra) {
+    StringBuffer sb = new StringBuffer(80);
+
+    sb.append("Insn{");
+    sb.append(position);
+    sb.append(' ');
+    sb.append(opcode);
+
+    if (extra != null) {
+      sb.append(' ');
+      sb.append(extra);
+    }
+
+    sb.append(" :: ");
+
+    if (result != null) {
+      sb.append(result);
+      sb.append(" <- ");
+    }
+
+    sb.append(sources);
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /**
+   * Returns the human string form of this instance, with the given
+   * bit added in the standard location for an inline argument.
+   *
+   * @param extra {@code null-ok;} the inline argument string
+   * @return {@code non-null;} the human string form
+   */
+  protected final String toHumanWithInline(String extra) {
+    StringBuffer sb = new StringBuffer(80);
+
+    sb.append(position);
+    sb.append(": ");
+    sb.append(opcode.getNickname());
+
+    if (extra != null) {
+      sb.append("(");
+      sb.append(extra);
+      sb.append(")");
+    }
+
+    if (result == null) {
+      sb.append(" .");
+    } else {
+      sb.append(" ");
+      sb.append(result.toHuman());
+    }
+
+    sb.append(" <-");
+
+    int sz = sources.size();
+    if (sz == 0) {
+      sb.append(" .");
+    } else {
+      for (int i = 0; i < sz; i++) {
+        sb.append(" ");
+        sb.append(sources.get(i).toHuman());
+      }
+    }
+
+    return sb.toString();
+  }
+
+
+  /**
+   * Visitor interface for this (outer) class.
+   */
+  public static interface Visitor {
     /**
-     * {@inheritDoc}
+     * Visits a {@link PlainInsn}.
      *
-     * This implementation returns the identity hashcode of this
-     * instance. This is proper, since instances of this class compare
-     * by identity (see {@link #equals}).
+     * @param insn {@code non-null;} the instruction to visit
      */
+    public void visitPlainInsn(PlainInsn insn);
+
+    /**
+     * Visits a {@link PlainCstInsn}.
+     *
+     * @param insn {@code non-null;} the instruction to visit
+     */
+    public void visitPlainCstInsn(PlainCstInsn insn);
+
+    /**
+     * Visits a {@link SwitchInsn}.
+     *
+     * @param insn {@code non-null;} the instruction to visit
+     */
+    public void visitSwitchInsn(SwitchInsn insn);
+
+    /**
+     * Visits a {@link ThrowingCstInsn}.
+     *
+     * @param insn {@code non-null;} the instruction to visit
+     */
+    public void visitThrowingCstInsn(ThrowingCstInsn insn);
+
+    /**
+     * Visits a {@link ThrowingInsn}.
+     *
+     * @param insn {@code non-null;} the instruction to visit
+     */
+    public void visitThrowingInsn(ThrowingInsn insn);
+
+    /**
+     * Visits a {@link FillArrayDataInsn}.
+     *
+     * @param insn {@code non-null;} the instruction to visit
+     */
+    public void visitFillArrayDataInsn(FillArrayDataInsn insn);
+  }
+
+  /**
+   * Base implementation of {@link Visitor}, which has empty method
+   * bodies for all methods.
+   */
+  public static class BaseVisitor implements Visitor {
+    /** {@inheritDoc} */
     @Override
-    public final int hashCode() {
-        return System.identityHashCode(this);
+    public void visitPlainInsn(PlainInsn insn) {
+      // This space intentionally left blank.
     }
 
     /** {@inheritDoc} */
     @Override
-    public String toString() {
-        return toStringWithInline(getInlineString());
+    public void visitPlainCstInsn(PlainCstInsn insn) {
+      // This space intentionally left blank.
     }
 
-    /**
-     * Gets a human-oriented (and slightly lossy) string for this instance.
-     *
-     * @return {@code non-null;} the human string form
-     */
-    public String toHuman() {
-        return toHumanWithInline(getInlineString());
+    /** {@inheritDoc} */
+    @Override
+    public void visitSwitchInsn(SwitchInsn insn) {
+      // This space intentionally left blank.
     }
 
-    /**
-     * Gets an "inline" string portion for toHuman(), if available. This
-     * is the portion that appears after the Rop opcode
-     *
-     * @return {@code null-ok;} if non-null, the inline text for toHuman()
-     */
-    public String getInlineString() {
-        return null;
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingCstInsn(ThrowingCstInsn insn) {
+      // This space intentionally left blank.
     }
 
-    /**
-     * Gets the opcode.
-     *
-     * @return {@code non-null;} the opcode
-     */
-    public final Rop getOpcode() {
-        return opcode;
+    /** {@inheritDoc} */
+    @Override
+    public void visitThrowingInsn(ThrowingInsn insn) {
+      // This space intentionally left blank.
     }
 
-    /**
-     * Gets the source position.
-     *
-     * @return {@code non-null;} the source position
-     */
-    public final SourcePosition getPosition() {
-        return position;
+    /** {@inheritDoc} */
+    @Override
+    public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
+      // This space intentionally left blank.
     }
-
-    /**
-     * Gets the result spec, if any. A return value of {@code null}
-     * means this instruction returns nothing.
-     *
-     * @return {@code null-ok;} the result spec, if any
-     */
-    public final RegisterSpec getResult() {
-        return result;
-    }
-
-    /**
-     * Gets the spec of a local variable assignment that occurs at this
-     * instruction, or null if no local variable assignment occurs. This
-     * may be the result register, or for {@code mark-local} insns
-     * it may be the source.
-     *
-     * @return {@code null-ok;} a named register spec or null
-     */
-    public final RegisterSpec getLocalAssignment() {
-        RegisterSpec assignment;
-        if (opcode.getOpcode() == RegOps.MARK_LOCAL) {
-            assignment = sources.get(0);
-        } else {
-            assignment = result;
-        }
-
-        if (assignment == null) {
-            return null;
-        }
-
-        LocalItem localItem = assignment.getLocalItem();
-
-        if (localItem == null) {
-            return null;
-        }
-
-        return assignment;
-    }
-
-    /**
-     * Gets the source specs.
-     *
-     * @return {@code non-null;} the source specs
-     */
-    public final RegisterSpecList getSources() {
-        return sources;
-    }
-
-    /**
-     * Gets whether this instruction can possibly throw an exception. This
-     * is just a convenient wrapper for {@code getOpcode().canThrow()}.
-     *
-     * @return {@code true} iff this instruction can possibly throw
-     */
-    public final boolean canThrow() {
-        return opcode.canThrow();
-    }
-
-    /**
-     * Gets the list of possibly-caught exceptions. This returns {@link
-     * StdTypeList#EMPTY} if this instruction has no handlers,
-     * which can be <i>either</i> if this instruction can't possibly
-     * throw or if it merely doesn't handle any of its possible
-     * exceptions. To determine whether this instruction can throw,
-     * use {@link #canThrow}.
-     *
-     * @return {@code non-null;} the catches list
-     */
-    public abstract TypeList getCatches();
-
-    /**
-     * Calls the appropriate method on the given visitor, depending on the
-     * class of this instance. Subclasses must override this.
-     *
-     * @param visitor {@code non-null;} the visitor to call on
-     */
-    public abstract void accept(Visitor visitor);
-
-    /**
-     * Returns an instance that is just like this one, except that it
-     * has a catch list with the given item appended to the end. This
-     * method throws an exception if this instance can't possibly
-     * throw. To determine whether this instruction can throw, use
-     * {@link #canThrow}.
-     *
-     * @param type {@code non-null;} type to append to the catch list
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract Insn withAddedCatch(Type type);
-
-    /**
-     * Returns an instance that is just like this one, except that all
-     * register references have been offset by the given delta.
-     *
-     * @param delta the amount to offset register references by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract Insn withRegisterOffset(int delta);
-
-    /**
-     * Returns an instance that is just like this one, except that, if
-     * possible, the insn is converted into a version in which a source
-     * (if it is a constant) is represented directly rather than as a
-     * register reference. {@code this} is returned in cases where the
-     * translation is not possible.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public Insn withSourceLiteral() {
-        return this;
-    }
-
-    /**
-     * Returns an exact copy of this Insn
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public Insn copy() {
-        return withRegisterOffset(0);
-    }
-
-
-    /**
-     * Compares, handling nulls safely
-     *
-     * @param a first object
-     * @param b second object
-     * @return true if they're equal or both null.
-     */
-    private static boolean equalsHandleNulls (Object a, Object b) {
-        return (a == b) || ((a != null) && a.equals(b));
-    }
-
-    /**
-     * Compares Insn contents, since {@code Insn.equals()} is defined
-     * to be an identity compare. Insn's are {@code contentEquals()}
-     * if they have the same opcode, registers, source position, and other
-     * metadata.
-     *
-     * @return true in the case described above
-     */
-    public boolean contentEquals(Insn b) {
-        return opcode == b.getOpcode()
-                && position.equals(b.getPosition())
-                && (getClass() == b.getClass())
-                && equalsHandleNulls(result, b.getResult())
-                && equalsHandleNulls(sources, b.getSources())
-                && StdTypeList.equalContents(getCatches(), b.getCatches());
-    }
-
-    /**
-     * Returns an instance that is just like this one, except
-     * with new result and source registers.
-     *
-     * @param result {@code null-ok;} new result register
-     * @param sources {@code non-null;} new sources registers
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public abstract Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources);
-
-    /**
-     * Returns the string form of this instance, with the given bit added in
-     * the standard location for an inline argument.
-     *
-     * @param extra {@code null-ok;} the inline argument string
-     * @return {@code non-null;} the string form
-     */
-    protected final String toStringWithInline(String extra) {
-        StringBuffer sb = new StringBuffer(80);
-
-        sb.append("Insn{");
-        sb.append(position);
-        sb.append(' ');
-        sb.append(opcode);
-
-        if (extra != null) {
-            sb.append(' ');
-            sb.append(extra);
-        }
-
-        sb.append(" :: ");
-
-        if (result != null) {
-            sb.append(result);
-            sb.append(" <- ");
-        }
-
-        sb.append(sources);
-        sb.append('}');
-
-        return sb.toString();
-    }
-
-    /**
-     * Returns the human string form of this instance, with the given
-     * bit added in the standard location for an inline argument.
-     *
-     * @param extra {@code null-ok;} the inline argument string
-     * @return {@code non-null;} the human string form
-     */
-    protected final String toHumanWithInline(String extra) {
-        StringBuffer sb = new StringBuffer(80);
-
-        sb.append(position);
-        sb.append(": ");
-        sb.append(opcode.getNickname());
-
-        if (extra != null) {
-            sb.append("(");
-            sb.append(extra);
-            sb.append(")");
-        }
-
-        if (result == null) {
-            sb.append(" .");
-        } else {
-            sb.append(" ");
-            sb.append(result.toHuman());
-        }
-
-        sb.append(" <-");
-
-        int sz = sources.size();
-        if (sz == 0) {
-            sb.append(" .");
-        } else {
-            for (int i = 0; i < sz; i++) {
-                sb.append(" ");
-                sb.append(sources.get(i).toHuman());
-            }
-        }
-
-        return sb.toString();
-    }
-
-
-    /**
-     * Visitor interface for this (outer) class.
-     */
-    public static interface Visitor {
-        /**
-         * Visits a {@link PlainInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitPlainInsn(PlainInsn insn);
-
-        /**
-         * Visits a {@link PlainCstInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitPlainCstInsn(PlainCstInsn insn);
-
-        /**
-         * Visits a {@link SwitchInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitSwitchInsn(SwitchInsn insn);
-
-        /**
-         * Visits a {@link ThrowingCstInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitThrowingCstInsn(ThrowingCstInsn insn);
-
-        /**
-         * Visits a {@link ThrowingInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitThrowingInsn(ThrowingInsn insn);
-
-        /**
-         * Visits a {@link FillArrayDataInsn}.
-         *
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitFillArrayDataInsn(FillArrayDataInsn insn);
-    }
-
-    /**
-     * Base implementation of {@link Visitor}, which has empty method
-     * bodies for all methods.
-     */
-    public static class BaseVisitor implements Visitor {
-        /** {@inheritDoc} */
-        public void visitPlainInsn(PlainInsn insn) {
-            // This space intentionally left blank.
-        }
-
-        /** {@inheritDoc} */
-        public void visitPlainCstInsn(PlainCstInsn insn) {
-            // This space intentionally left blank.
-        }
-
-        /** {@inheritDoc} */
-        public void visitSwitchInsn(SwitchInsn insn) {
-            // This space intentionally left blank.
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingCstInsn(ThrowingCstInsn insn) {
-            // This space intentionally left blank.
-        }
-
-        /** {@inheritDoc} */
-        public void visitThrowingInsn(ThrowingInsn insn) {
-            // This space intentionally left blank.
-        }
-
-        /** {@inheritDoc} */
-        public void visitFillArrayDataInsn(FillArrayDataInsn insn) {
-            // This space intentionally left blank.
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/InsnList.java b/dx/src/com/android/jack/dx/rop/code/InsnList.java
index fb78741..0d55c67 100644
--- a/dx/src/com/android/jack/dx/rop/code/InsnList.java
+++ b/dx/src/com/android/jack/dx/rop/code/InsnList.java
@@ -21,110 +21,113 @@
 /**
  * List of {@link Insn} instances.
  */
-public final class InsnList
-        extends FixedSizeList {
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public InsnList(int size) {
-        super(size);
+public final class InsnList extends FixedSizeList {
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public InsnList(int size) {
+    super(size);
+  }
+
+  /**
+   * Gets the element at the given index. It is an error to call
+   * this with the index for an element which was never set; if you
+   * do that, this will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @return {@code non-null;} element at that index
+   */
+  public Insn get(int n) {
+    return (Insn) get0(n);
+  }
+
+  /**
+   * Sets the instruction at the given index.
+   *
+   * @param n {@code >= 0, < size();} which index
+   * @param insn {@code non-null;} the instruction to set at {@code n}
+   */
+  public void set(int n, Insn insn) {
+    set0(n, insn);
+  }
+
+  /**
+   * Gets the last instruction. This is just a convenient shorthand for
+   * {@code get(size() - 1)}.
+   *
+   * @return {@code non-null;} the last instruction
+   */
+  public Insn getLast() {
+    return get(size() - 1);
+  }
+
+  /**
+   * Visits each instruction in the list, in order.
+   *
+   * @param visitor {@code non-null;} visitor to use
+   */
+  public void forEach(Insn.Visitor visitor) {
+    int sz = size();
+
+    for (int i = 0; i < sz; i++) {
+      get(i).accept(visitor);
+    }
+  }
+
+  /**
+   * Compares the contents of this {@code InsnList} with another.
+   * The blocks must have the same number of insns, and each Insn must
+   * also return true to {@code Insn.contentEquals()}.
+   *
+   * @param b to compare
+   * @return true in the case described above.
+   */
+  public boolean contentEquals(InsnList b) {
+    if (b == null) {
+      return false;
     }
 
-    /**
-     * Gets the element at the given index. It is an error to call
-     * this with the index for an element which was never set; if you
-     * do that, this will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @return {@code non-null;} element at that index
-     */
-    public Insn get(int n) {
-        return (Insn) get0(n);
+    int sz = size();
+
+    if (sz != b.size()) {
+      return false;
     }
 
-    /**
-     * Sets the instruction at the given index.
-     *
-     * @param n {@code >= 0, < size();} which index
-     * @param insn {@code non-null;} the instruction to set at {@code n}
-     */
-    public void set(int n, Insn insn) {
-        set0(n, insn);
+    for (int i = 0; i < sz; i++) {
+      if (!get(i).contentEquals(b.get(i))) {
+        return false;
+      }
     }
 
-    /**
-     * Gets the last instruction. This is just a convenient shorthand for
-     * {@code get(size() - 1)}.
-     *
-     * @return {@code non-null;} the last instruction
-     */
-    public Insn getLast() {
-        return get(size() - 1);
+    return true;
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the registers in each instruction are offset by the given
+   * amount. Mutability of the result is inherited from the
+   * original.
+   *
+   * @param delta the amount to offset register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public InsnList withRegisterOffset(int delta) {
+    int sz = size();
+    InsnList result = new InsnList(sz);
+
+    for (int i = 0; i < sz; i++) {
+      Insn one = (Insn) get0(i);
+      if (one != null) {
+        result.set0(i, one.withRegisterOffset(delta));
+      }
     }
 
-    /**
-     * Visits each instruction in the list, in order.
-     *
-     * @param visitor {@code non-null;} visitor to use
-     */
-    public void forEach(Insn.Visitor visitor) {
-        int sz = size();
-
-        for (int i = 0; i < sz; i++) {
-            get(i).accept(visitor);
-        }
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Compares the contents of this {@code InsnList} with another.
-     * The blocks must have the same number of insns, and each Insn must
-     * also return true to {@code Insn.contentEquals()}.
-     *
-     * @param b to compare
-     * @return true in the case described above.
-     */
-    public boolean contentEquals(InsnList b) {
-        if (b == null) return false;
-
-        int sz = size();
-
-        if (sz != b.size()) return false;
-
-        for (int i = 0; i < sz; i++) {
-            if (!get(i).contentEquals(b.get(i))) {
-                return false;
-            }
-        }
-
-        return true;
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the registers in each instruction are offset by the given
-     * amount. Mutability of the result is inherited from the
-     * original.
-     *
-     * @param delta the amount to offset register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public InsnList withRegisterOffset(int delta) {
-        int sz = size();
-        InsnList result = new InsnList(sz);
-
-        for (int i = 0; i < sz; i++) {
-            Insn one = (Insn) get0(i);
-            if (one != null) {
-                result.set0(i, one.withRegisterOffset(delta));
-            }
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
-    }
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/LocalItem.java b/dx/src/com/android/jack/dx/rop/code/LocalItem.java
index fd9c952..9ebf093 100644
--- a/dx/src/com/android/jack/dx/rop/code/LocalItem.java
+++ b/dx/src/com/android/jack/dx/rop/code/LocalItem.java
@@ -23,35 +23,35 @@
  * A local variable item: either a name or a signature or both.
  */
 public class LocalItem implements Comparable<LocalItem> {
-    /** {@code null-ok;} local variable name */
-    private final CstString name;
+  /** {@code null-ok;} local variable name */
+  private final CstString name;
 
-    /** {@code null-ok;} local variable type */
-    private final CstType type;
+  /** {@code null-ok;} local variable type */
+  private final CstType type;
 
-    /** {@code null-ok;} local variable signature */
-    private final CstString signature;
+  /** {@code null-ok;} local variable signature */
+  private final CstString signature;
 
-    /**
-   * Make a new item. If both name and type are null, null is returned.
-   *
-   * TODO: intern these
-   *
-   * @param name {@code null-ok;} local variable name
-   * @param type {@code null-ok;} local variable type
-   * @param signature {@code null-ok;} local variable signature which will be referenced as-is by
-   *        the sig_idx in the debug_info_item (cf. the documentation for debug_info_item and the
-   *        discussion under {@code dalvik.annotation.Signature} in "dex-format.html")
-   * @return {@code null-ok;} appropriate instance.
-   */
-    public static LocalItem make(CstString name, CstType type, CstString signature) {
-        if (name == null && type == null) {
-            return null;
-        }
-
-        return new LocalItem (name, type, signature);
+  /**
+  * Make a new item. If both name and type are null, null is returned.
+  *
+  * TODO(dx team): intern these
+  *
+  * @param name {@code null-ok;} local variable name
+  * @param type {@code null-ok;} local variable type
+  * @param signature {@code null-ok;} local variable signature which will be referenced as-is by
+  *        the sig_idx in the debug_info_item (cf. the documentation for debug_info_item and the
+  *        discussion under {@code dalvik.annotation.Signature} in "dex-format.html")
+  * @return {@code null-ok;} appropriate instance.
+  */
+  public static LocalItem make(CstString name, CstType type, CstString signature) {
+    if (name == null && type == null) {
+      return null;
     }
 
+    return new LocalItem(name, type, signature);
+  }
+
   /**
    * Constructs instance.
    *
@@ -59,131 +59,131 @@
    * @param type {@code null-ok;} local variable type
    * @param signature {@code null-ok;} local variable signature
    */
-    private LocalItem(CstString name, CstType type, CstString signature) {
-        this.name = name;
-        this.type = type;
-        this.signature = signature;
+  private LocalItem(CstString name, CstType type, CstString signature) {
+    this.name = name;
+    this.type = type;
+    this.signature = signature;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof LocalItem)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof LocalItem)) {
-            return false;
-        }
+    LocalItem local = (LocalItem) other;
 
-        LocalItem local = (LocalItem) other;
+    return 0 == compareTo(local);
+  }
 
-        return 0 == compareTo(local);
+  /**
+   * Compares two strings like String.compareTo(), excepts treats a null
+   * as the least-possible string value.
+   *
+   * @return negative integer, zero, or positive integer in accordance
+   * with Comparable.compareTo()
+   */
+  private static int compareHandlesNulls(CstString a, CstString b) {
+    if (a == b) {
+      return 0;
+    } else if (a == null) {
+      return -1;
+    } else if (b == null) {
+      return 1;
+    } else {
+      return a.compareTo(b);
+    }
+  }
+
+  /**
+   * Compares two CstType like CstType.compareTo(), excepts treats a null
+   * as the least-possible string value.
+   *
+   * @return negative integer, zero, or positive integer in accordance
+   * with Comparable.compareTo()
+   */
+  private static int compareHandlesNulls(CstType a, CstType b) {
+    if (a == b) {
+      return 0;
+    } else if (a == null) {
+      return -1;
+    } else if (b == null) {
+      return 1;
+    } else {
+      return a.compareTo(b);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(LocalItem local) {
+    int ret;
+
+    ret = compareHandlesNulls(name, local.name);
+
+    if (ret != 0) {
+      return ret;
     }
 
-    /**
-     * Compares two strings like String.compareTo(), excepts treats a null
-     * as the least-possible string value.
-     *
-     * @return negative integer, zero, or positive integer in accordance
-     * with Comparable.compareTo()
-     */
-    private static int compareHandlesNulls(CstString a, CstString b) {
-        if (a == b) {
-            return 0;
-        } else if (a == null) {
-            return -1;
-        } else if (b == null) {
-            return 1;
-        } else {
-            return a.compareTo(b);
-        }
+    ret = compareHandlesNulls(type, local.type);
+
+    if (ret != 0) {
+      return ret;
     }
 
-    /**
-     * Compares two CstType like CstType.compareTo(), excepts treats a null
-     * as the least-possible string value.
-     *
-     * @return negative integer, zero, or positive integer in accordance
-     * with Comparable.compareTo()
-     */
-    private static int compareHandlesNulls(CstType a, CstType b) {
-        if (a == b) {
-            return 0;
-        } else if (a == null) {
-            return -1;
-        } else if (b == null) {
-            return 1;
-        } else {
-            return a.compareTo(b);
-        }
+    ret = compareHandlesNulls(signature, local.signature);
+
+    return ret;
+  }
+
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return (name == null ? 0 : name.hashCode()) * 31 + (type == null ? 0 : type.hashCode())
+        + (signature == null ? 0 : signature.hashCode()) * 17;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    if (name != null && type == null && signature == null) {
+      return name.toQuoted();
+    } else if (name == null && type == null && signature == null) {
+      return "";
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(LocalItem local) {
-        int ret;
+    return "[" + (name == null ? "" : name.toQuoted()) + "|"
+        + (type == null ? "" : type.getDescriptor().toQuoted()) + "|"
+        + (signature == null ? "" : signature.toQuoted());
+  }
 
-        ret = compareHandlesNulls(name, local.name);
+  /**
+   * Gets name.
+   *
+   * @return {@code null-ok;} name
+   */
+  public CstString getName() {
+    return name;
+  }
 
-        if (ret != 0) {
-            return ret;
-        }
+  /**
+  * Gets the signature that must be represented to successfully implement the source language's
+  * semantics (cf. the discussion under {@code dalvik.annotation.Signature} in "dex-format.html")
+  *
+  * @return signature
+  */
+  public CstString getSignature() {
+    return signature;
+  }
 
-        ret = compareHandlesNulls(type, local.type);
-
-        if (ret != 0) {
-            return ret;
-        }
-
-        ret = compareHandlesNulls(signature, local.signature);
-
-        return ret;
-    }
-
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return (name == null ? 0 : name.hashCode()) * 31
-                + (type == null ? 0 : type.hashCode())
-                + (signature == null ? 0 : signature.hashCode()) * 17;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        if (name != null && type == null && signature == null) {
-            return name.toQuoted();
-        } else if (name == null && type == null && signature == null) {
-            return "";
-        }
-
-        return "[" + (name == null ? "" : name.toQuoted())
-                + "|" + (type == null ? "" : type.getDescriptor().toQuoted())
-                + "|" + (signature == null ? "" : signature.toQuoted());
-    }
-
-    /**
-     * Gets name.
-     *
-     * @return {@code null-ok;} name
-     */
-    public CstString getName() {
-        return name;
-    }
-
-    /**
-    * Gets the signature that must be represented to successfully implement the source language's
-    * semantics (cf. the discussion under {@code dalvik.annotation.Signature} in "dex-format.html")
-    *
-    * @return signature
-    */
-    public CstString getSignature() {
-        return signature;
-    }
-
-    /**
-     * Gets type.
-     *
-     * @return {@code null-ok;} type.
-     */
-    public CstType getType() {
-        return type;
-    }
+  /**
+   * Gets type.
+   *
+   * @return {@code null-ok;} type.
+   */
+  public CstType getType() {
+    return type;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/LocalVariableExtractor.java b/dx/src/com/android/jack/dx/rop/code/LocalVariableExtractor.java
index 6420d38..739150c 100644
--- a/dx/src/com/android/jack/dx/rop/code/LocalVariableExtractor.java
+++ b/dx/src/com/android/jack/dx/rop/code/LocalVariableExtractor.java
@@ -24,168 +24,162 @@
  * a method.
  */
 public final class LocalVariableExtractor {
-    /** {@code non-null;} method being extracted from */
-    private final RopMethod method;
+  /** {@code non-null;} method being extracted from */
+  private final RopMethod method;
 
-    /** {@code non-null;} block list for the method */
-    private final BasicBlockList blocks;
+  /** {@code non-null;} block list for the method */
+  private final BasicBlockList blocks;
 
-    /** {@code non-null;} result in-progress */
-    private final LocalVariableInfo resultInfo;
+  /** {@code non-null;} result in-progress */
+  private final LocalVariableInfo resultInfo;
 
-    /** {@code non-null;} work set indicating blocks needing to be processed */
-    private final int[] workSet;
+  /** {@code non-null;} work set indicating blocks needing to be processed */
+  private final int[] workSet;
 
-    /**
-     * Extracts out all the local variable information from the given method.
-     *
-     * @param method {@code non-null;} the method to extract from
-     * @return {@code non-null;} the extracted information
-     */
-    public static LocalVariableInfo extract(RopMethod method) {
-        LocalVariableExtractor lve = new LocalVariableExtractor(method);
-        return lve.doit();
+  /**
+   * Extracts out all the local variable information from the given method.
+   *
+   * @param method {@code non-null;} the method to extract from
+   * @return {@code non-null;} the extracted information
+   */
+  public static LocalVariableInfo extract(RopMethod method) {
+    LocalVariableExtractor lve = new LocalVariableExtractor(method);
+    return lve.doit();
+  }
+
+  /**
+   * Constructs an instance. This method is private. Use {@link #extract}.
+   *
+   * @param method {@code non-null;} the method to extract from
+   */
+  private LocalVariableExtractor(RopMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /**
-     * Constructs an instance. This method is private. Use {@link #extract}.
-     *
-     * @param method {@code non-null;} the method to extract from
-     */
-    private LocalVariableExtractor(RopMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
+    BasicBlockList blocks = method.getBlocks();
+    int maxLabel = blocks.getMaxLabel();
 
-        BasicBlockList blocks = method.getBlocks();
-        int maxLabel = blocks.getMaxLabel();
+    this.method = method;
+    this.blocks = blocks;
+    this.resultInfo = new LocalVariableInfo(method);
+    this.workSet = Bits.makeBitSet(maxLabel);
+  }
 
-        this.method = method;
-        this.blocks = blocks;
-        this.resultInfo = new LocalVariableInfo(method);
-        this.workSet = Bits.makeBitSet(maxLabel);
+  /**
+   * Does the extraction.
+   *
+   * @return {@code non-null;} the extracted information
+   */
+  private LocalVariableInfo doit() {
+    for (int label = method.getFirstLabel(); label >= 0; label = Bits.findFirst(workSet, 0)) {
+      Bits.clear(workSet, label);
+      processBlock(label);
     }
 
-    /**
-     * Does the extraction.
-     *
-     * @return {@code non-null;} the extracted information
+    resultInfo.setImmutable();
+    return resultInfo;
+  }
+
+  /**
+   * Processes a single block.
+   *
+   * @param label {@code >= 0;} label of the block to process
+   */
+  private void processBlock(int label) {
+    RegisterSpecSet primaryState = resultInfo.mutableCopyOfStarts(label);
+    BasicBlock block = blocks.labelToBlock(label);
+    InsnList insns = block.getInsns();
+    int insnSz = insns.size();
+
+    /*
+     * We may have to treat the last instruction specially: If it
+     * can (but doesn't always) throw, and the exception can be
+     * caught within the same method, then we need to use the
+     * state *before* executing it to be what is merged into
+     * exception targets.
      */
-    private LocalVariableInfo doit() {
-        for (int label = method.getFirstLabel();
-             label >= 0;
-             label = Bits.findFirst(workSet, 0)) {
-            Bits.clear(workSet, label);
-            processBlock(label);
-        }
+    boolean canThrowDuringLastInsn =
+        block.hasExceptionHandlers() && (insns.getLast().getResult() != null);
+    int freezeSecondaryStateAt = insnSz - 1;
+    RegisterSpecSet secondaryState = primaryState;
 
-        resultInfo.setImmutable();
-        return resultInfo;
-    }
-
-    /**
-     * Processes a single block.
-     *
-     * @param label {@code >= 0;} label of the block to process
+    /*
+     * Iterate over the instructions, adding information for each place
+     * that the active variable set changes.
      */
-    private void processBlock(int label) {
-        RegisterSpecSet primaryState = resultInfo.mutableCopyOfStarts(label);
-        BasicBlock block = blocks.labelToBlock(label);
-        InsnList insns = block.getInsns();
-        int insnSz = insns.size();
 
-        /*
-         * We may have to treat the last instruction specially: If it
-         * can (but doesn't always) throw, and the exception can be
-         * caught within the same method, then we need to use the
-         * state *before* executing it to be what is merged into
-         * exception targets.
-         */
-        boolean canThrowDuringLastInsn = block.hasExceptionHandlers() &&
-            (insns.getLast().getResult() != null);
-        int freezeSecondaryStateAt = insnSz - 1;
-        RegisterSpecSet secondaryState = primaryState;
-
-        /*
-         * Iterate over the instructions, adding information for each place
-         * that the active variable set changes.
-         */
-
-        for (int i = 0; i < insnSz; i++) {
-            if (canThrowDuringLastInsn && (i == freezeSecondaryStateAt)) {
-                // Until this point, primaryState == secondaryState.
-                primaryState.setImmutable();
-                primaryState = primaryState.mutableCopy();
-            }
-
-            Insn insn = insns.get(i);
-            RegisterSpec result;
-
-            result = insn.getLocalAssignment();
-
-            if (result == null) {
-                /*
-                 * If an assignment assigns over an existing local, make
-                 * sure to mark the local as going out of scope.
-                 */
-
-                result = insn.getResult();
-
-                if (result != null
-                        && primaryState.get(result.getReg()) != null) {
-                    primaryState.remove(primaryState.get(result.getReg()));
-                }
-                continue;
-            }
-
-            result = result.withSimpleType();
-
-            RegisterSpec already = primaryState.get(result);
-            /*
-             * The equals() check ensures we only add new info if
-             * the instruction causes a change to the set of
-             * active variables.
-             */
-            if (!result.equals(already)) {
-                /*
-                 * If this insn represents a local moving from one register
-                 * to another, remove the association between the old register
-                 * and the local.
-                 */
-                RegisterSpec previous
-                        = primaryState.localItemToSpec(result.getLocalItem());
-
-                if (previous != null
-                        && (previous.getReg() != result.getReg())) {
-
-                    primaryState.remove(previous);
-                }
-
-                resultInfo.addAssignment(insn, result);
-                primaryState.put(result);
-            }
-        }
-
+for (int i = 0; i < insnSz; i++) {
+      if (canThrowDuringLastInsn && (i == freezeSecondaryStateAt)) {
+        // Until this point, primaryState == secondaryState.
         primaryState.setImmutable();
+        primaryState = primaryState.mutableCopy();
+      }
 
+      Insn insn = insns.get(i);
+      RegisterSpec result;
+
+      result = insn.getLocalAssignment();
+
+      if (result == null) {
         /*
-         * Merge this state into the start state for each successor,
-         * and update the work set where required (that is, in cases
-         * where the start state for a block changes).
+         * If an assignment assigns over an existing local, make
+         * sure to mark the local as going out of scope.
          */
 
-        IntList successors = block.getSuccessors();
-        int succSz = successors.size();
-        int primarySuccessor = block.getPrimarySuccessor();
+result = insn.getResult();
 
-        for (int i = 0; i < succSz; i++) {
-            int succ = successors.get(i);
-            RegisterSpecSet state = (succ == primarySuccessor) ?
-                primaryState : secondaryState;
-
-            if (resultInfo.mergeStarts(succ, state)) {
-                Bits.set(workSet, succ);
-            }
+        if (result != null && primaryState.get(result.getReg()) != null) {
+          primaryState.remove(primaryState.get(result.getReg()));
         }
+        continue;
+      }
+
+      result = result.withSimpleType();
+
+      RegisterSpec already = primaryState.get(result);
+      /*
+       * The equals() check ensures we only add new info if
+       * the instruction causes a change to the set of
+       * active variables.
+       */
+      if (!result.equals(already)) {
+        /*
+         * If this insn represents a local moving from one register
+         * to another, remove the association between the old register
+         * and the local.
+         */
+        RegisterSpec previous = primaryState.localItemToSpec(result.getLocalItem());
+
+        if (previous != null && (previous.getReg() != result.getReg())) {
+
+          primaryState.remove(previous);
+        }
+
+        resultInfo.addAssignment(insn, result);
+        primaryState.put(result);
+      }
     }
+
+    primaryState.setImmutable();
+
+    /*
+     * Merge this state into the start state for each successor,
+     * and update the work set where required (that is, in cases
+     * where the start state for a block changes).
+     */
+
+IntList successors = block.getSuccessors();
+    int succSz = successors.size();
+    int primarySuccessor = block.getPrimarySuccessor();
+
+    for (int i = 0; i < succSz; i++) {
+      int succ = successors.get(i);
+      RegisterSpecSet state = (succ == primarySuccessor) ? primaryState : secondaryState;
+
+      if (resultInfo.mergeStarts(succ, state)) {
+        Bits.set(workSet, succ);
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/LocalVariableInfo.java b/dx/src/com/android/jack/dx/rop/code/LocalVariableInfo.java
index a15402f..f476154 100644
--- a/dx/src/com/android/jack/dx/rop/code/LocalVariableInfo.java
+++ b/dx/src/com/android/jack/dx/rop/code/LocalVariableInfo.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.dx.rop.code;
 
-import com.android.jack.dx.rop.type.TypeBearer;
 import com.android.jack.dx.util.MutabilityControl;
 
 import java.util.HashMap;
@@ -25,230 +24,226 @@
  * Container for local variable information for a particular {@link
  * RopMethod}.
  */
-public final class LocalVariableInfo
-        extends MutabilityControl {
-    /** {@code >= 0;} the register count for the method */
-    private final int regCount;
+public final class LocalVariableInfo extends MutabilityControl {
+  /** {@code >= 0;} the register count for the method */
+  private final int regCount;
 
-    /**
-     * {@code non-null;} {@link RegisterSpecSet} to use when indicating a block
-     * that has no locals; it is empty and immutable but has an appropriate
-     * max size for the method
-     */
-    private final RegisterSpecSet emptySet;
+  /**
+   * {@code non-null;} {@link RegisterSpecSet} to use when indicating a block
+   * that has no locals; it is empty and immutable but has an appropriate
+   * max size for the method
+   */
+  private final RegisterSpecSet emptySet;
 
-    /**
-     * {@code non-null;} array consisting of register sets representing the
-     * sets of variables already assigned upon entry to each block,
-     * where array indices correspond to block labels
-     */
-    private final RegisterSpecSet[] blockStarts;
+  /**
+   * {@code non-null;} array consisting of register sets representing the
+   * sets of variables already assigned upon entry to each block,
+   * where array indices correspond to block labels
+   */
+  private final RegisterSpecSet[] blockStarts;
 
-    /** {@code non-null;} map from instructions to the variable each assigns */
-    private final HashMap<Insn, RegisterSpec> insnAssignments;
+  /** {@code non-null;} map from instructions to the variable each assigns */
+  private final HashMap<Insn, RegisterSpec> insnAssignments;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the method being represented by this instance
-     */
-    public LocalVariableInfo(RopMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        BasicBlockList blocks = method.getBlocks();
-        int maxLabel = blocks.getMaxLabel();
-
-        this.regCount = blocks.getRegCount();
-        this.emptySet = new RegisterSpecSet(regCount);
-        this.blockStarts = new RegisterSpecSet[maxLabel];
-        this.insnAssignments =
-            new HashMap<Insn, RegisterSpec>(blocks.getInstructionCount());
-
-        emptySet.setImmutable();
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the method being represented by this instance
+   */
+  public LocalVariableInfo(RopMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /**
-     * Sets the register set associated with the start of the block with
-     * the given label.
-     *
-     * @param label {@code >= 0;} the block label
-     * @param specs {@code non-null;} the register set to associate with the block
-     */
-    public void setStarts(int label, RegisterSpecSet specs) {
-        throwIfImmutable();
+    BasicBlockList blocks = method.getBlocks();
+    int maxLabel = blocks.getMaxLabel();
 
-        if (specs == null) {
-            throw new NullPointerException("specs == null");
-        }
+    this.regCount = blocks.getRegCount();
+    this.emptySet = new RegisterSpecSet(regCount);
+    this.blockStarts = new RegisterSpecSet[maxLabel];
+    this.insnAssignments = new HashMap<Insn, RegisterSpec>(blocks.getInstructionCount());
 
-        try {
-            blockStarts[label] = specs;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus label");
-        }
+    emptySet.setImmutable();
+  }
+
+  /**
+   * Sets the register set associated with the start of the block with
+   * the given label.
+   *
+   * @param label {@code >= 0;} the block label
+   * @param specs {@code non-null;} the register set to associate with the block
+   */
+  public void setStarts(int label, RegisterSpecSet specs) {
+    throwIfImmutable();
+
+    if (specs == null) {
+      throw new NullPointerException("specs == null");
     }
 
-    /**
-     * Merges the given register set into the set for the block with the
-     * given label. If there was not already an associated set, then this
-     * is the same as calling {@link #setStarts}. Otherwise, this will
-     * merge the two sets and call {@link #setStarts} on the result of the
-     * merge.
-     *
-     * @param label {@code >= 0;} the block label
-     * @param specs {@code non-null;} the register set to merge into the start set
-     * for the block
-     * @return {@code true} if the merge resulted in an actual change
-     * to the associated set (including storing one for the first time) or
-     * {@code false} if there was no change
-     */
-    public boolean mergeStarts(int label, RegisterSpecSet specs) {
-        RegisterSpecSet start = getStarts0(label);
-        boolean changed = false;
+    try {
+      blockStarts[label] = specs;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus label");
+    }
+  }
 
-        if (start == null) {
-            setStarts(label, specs);
-            return true;
-        }
+  /**
+   * Merges the given register set into the set for the block with the
+   * given label. If there was not already an associated set, then this
+   * is the same as calling {@link #setStarts}. Otherwise, this will
+   * merge the two sets and call {@link #setStarts} on the result of the
+   * merge.
+   *
+   * @param label {@code >= 0;} the block label
+   * @param specs {@code non-null;} the register set to merge into the start set
+   * for the block
+   * @return {@code true} if the merge resulted in an actual change
+   * to the associated set (including storing one for the first time) or
+   * {@code false} if there was no change
+   */
+  public boolean mergeStarts(int label, RegisterSpecSet specs) {
+    RegisterSpecSet start = getStarts0(label);
 
-        RegisterSpecSet newStart = start.mutableCopy();
-        if (start.size() != 0) {
-            newStart.intersect(specs, true);
-        } else {
-            newStart = specs.mutableCopy();
-        }
-
-        if (start.equals(newStart)) {
-            return false;
-        }
-
-        newStart.setImmutable();
-        setStarts(label, newStart);
-
-        return true;
+    if (start == null) {
+      setStarts(label, specs);
+      return true;
     }
 
-    /**
-     * Gets the register set associated with the start of the block
-     * with the given label. This returns an empty set with the appropriate
-     * max size if no set was associated with the block in question.
-     *
-     * @param label {@code >= 0;} the block label
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet getStarts(int label) {
-        RegisterSpecSet result = getStarts0(label);
-
-        return (result != null) ? result : emptySet;
+    RegisterSpecSet newStart = start.mutableCopy();
+    if (start.size() != 0) {
+      newStart.intersect(specs, true);
+    } else {
+      newStart = specs.mutableCopy();
     }
 
-    /**
-     * Gets the register set associated with the start of the given
-     * block. This is just convenient shorthand for
-     * {@code getStarts(block.getLabel())}.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet getStarts(BasicBlock block) {
-        return getStarts(block.getLabel());
+    if (start.equals(newStart)) {
+      return false;
     }
 
-    /**
-     * Gets a mutable copy of the register set associated with the
-     * start of the block with the given label. This returns a
-     * newly-allocated empty {@link RegisterSpecSet} of appropriate
-     * max size if there is not yet any set associated with the block.
-     *
-     * @param label {@code >= 0;} the block label
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet mutableCopyOfStarts(int label) {
-        RegisterSpecSet result = getStarts0(label);
+    newStart.setImmutable();
+    setStarts(label, newStart);
 
-        return (result != null) ?
-            result.mutableCopy() : new RegisterSpecSet(regCount);
+    return true;
+  }
+
+  /**
+   * Gets the register set associated with the start of the block
+   * with the given label. This returns an empty set with the appropriate
+   * max size if no set was associated with the block in question.
+   *
+   * @param label {@code >= 0;} the block label
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet getStarts(int label) {
+    RegisterSpecSet result = getStarts0(label);
+
+    return (result != null) ? result : emptySet;
+  }
+
+  /**
+   * Gets the register set associated with the start of the given
+   * block. This is just convenient shorthand for
+   * {@code getStarts(block.getLabel())}.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet getStarts(BasicBlock block) {
+    return getStarts(block.getLabel());
+  }
+
+  /**
+   * Gets a mutable copy of the register set associated with the
+   * start of the block with the given label. This returns a
+   * newly-allocated empty {@link RegisterSpecSet} of appropriate
+   * max size if there is not yet any set associated with the block.
+   *
+   * @param label {@code >= 0;} the block label
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet mutableCopyOfStarts(int label) {
+    RegisterSpecSet result = getStarts0(label);
+
+    return (result != null) ? result.mutableCopy() : new RegisterSpecSet(regCount);
+  }
+
+  /**
+   * Adds an assignment association for the given instruction and
+   * register spec. This throws an exception if the instruction
+   * doesn't actually perform a named variable assignment.
+   *
+   * <b>Note:</b> Although the instruction contains its own spec for
+   * the result, it still needs to be passed in explicitly to this
+   * method, since the spec that is stored here should always have a
+   * simple type and the one in the instruction can be an arbitrary
+   * {@link TypeBearer} (such as a constant value).
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @param spec {@code non-null;} the associated register spec
+   */
+  public void addAssignment(Insn insn, RegisterSpec spec) {
+    throwIfImmutable();
+
+    if (insn == null) {
+      throw new NullPointerException("insn == null");
     }
 
-    /**
-     * Adds an assignment association for the given instruction and
-     * register spec. This throws an exception if the instruction
-     * doesn't actually perform a named variable assignment.
-     *
-     * <b>Note:</b> Although the instruction contains its own spec for
-     * the result, it still needs to be passed in explicitly to this
-     * method, since the spec that is stored here should always have a
-     * simple type and the one in the instruction can be an arbitrary
-     * {@link TypeBearer} (such as a constant value).
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @param spec {@code non-null;} the associated register spec
-     */
-    public void addAssignment(Insn insn, RegisterSpec spec) {
-        throwIfImmutable();
-
-        if (insn == null) {
-            throw new NullPointerException("insn == null");
-        }
-
-        if (spec == null) {
-            throw new NullPointerException("spec == null");
-        }
-
-        insnAssignments.put(insn, spec);
+    if (spec == null) {
+      throw new NullPointerException("spec == null");
     }
 
-    /**
-     * Gets the named register being assigned by the given instruction, if
-     * previously stored in this instance.
-     *
-     * @param insn {@code non-null;} instruction in question
-     * @return {@code null-ok;} the named register being assigned, if any
-     */
-    public RegisterSpec getAssignment(Insn insn) {
-        return insnAssignments.get(insn);
-    }
+    insnAssignments.put(insn, spec);
+  }
 
-    /**
-     * Gets the number of assignments recorded by this instance.
-     *
-     * @return {@code >= 0;} the number of assignments
-     */
-    public int getAssignmentCount() {
-        return insnAssignments.size();
-    }
+  /**
+   * Gets the named register being assigned by the given instruction, if
+   * previously stored in this instance.
+   *
+   * @param insn {@code non-null;} instruction in question
+   * @return {@code null-ok;} the named register being assigned, if any
+   */
+  public RegisterSpec getAssignment(Insn insn) {
+    return insnAssignments.get(insn);
+  }
 
-    public void debugDump() {
-        for (int label = 0 ; label < blockStarts.length; label++) {
-            if (blockStarts[label] == null) {
-                continue;
-            }
+  /**
+   * Gets the number of assignments recorded by this instance.
+   *
+   * @return {@code >= 0;} the number of assignments
+   */
+  public int getAssignmentCount() {
+    return insnAssignments.size();
+  }
 
-            if (blockStarts[label] == emptySet) {
-                System.out.printf("%04x: empty set\n", label);
-            } else {
-                System.out.printf("%04x: %s\n", label, blockStarts[label]);
-            }
-        }
-    }
+  public void debugDump() {
+    for (int label = 0; label < blockStarts.length; label++) {
+      if (blockStarts[label] == null) {
+        continue;
+      }
 
-    /**
-     * Helper method, to get the starts for a label, throwing the
-     * right exception for range problems.
-     *
-     * @param label {@code >= 0;} the block label
-     * @return {@code null-ok;} associated register set or {@code null} if there
-     * is none
-     */
-    private RegisterSpecSet getStarts0(int label) {
-        try {
-            return blockStarts[label];
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus label");
-        }
+      if (blockStarts[label] == emptySet) {
+        System.out.printf("%04x: empty set\n", label);
+      } else {
+        System.out.printf("%04x: %s\n", label, blockStarts[label]);
+      }
     }
+  }
+
+  /**
+   * Helper method, to get the starts for a label, throwing the
+   * right exception for range problems.
+   *
+   * @param label {@code >= 0;} the block label
+   * @return {@code null-ok;} associated register set or {@code null} if there
+   * is none
+   */
+  private RegisterSpecSet getStarts0(int label) {
+    try {
+      return blockStarts[label];
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus label");
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/PlainCstInsn.java b/dx/src/com/android/jack/dx/rop/code/PlainCstInsn.java
index 597b92d..2220d4a 100644
--- a/dx/src/com/android/jack/dx/rop/code/PlainCstInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/PlainCstInsn.java
@@ -25,63 +25,55 @@
  * Instruction which contains an explicit reference to a constant
  * but which cannot throw an exception.
  */
-public final class PlainCstInsn
-        extends CstInsn {
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param sources {@code non-null;} specs for all the sources
-     * @param cst {@code non-null;} the constant
-     */
-    public PlainCstInsn(Rop opcode, SourcePosition position,
-                        RegisterSpec result, RegisterSpecList sources,
-                        Constant cst) {
-        super(opcode, position, result, sources, cst);
+public final class PlainCstInsn extends CstInsn {
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param sources {@code non-null;} specs for all the sources
+   * @param cst {@code non-null;} the constant
+   */
+  public PlainCstInsn(Rop opcode, SourcePosition position, RegisterSpec result,
+      RegisterSpecList sources, Constant cst) {
+    super(opcode, position, result, sources, cst);
 
-        if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
+    if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return StdTypeList.EMPTY;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return StdTypeList.EMPTY;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitPlainCstInsn(this);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitPlainCstInsn(this);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        throw new UnsupportedOperationException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    throw new UnsupportedOperationException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new PlainCstInsn(getOpcode(), getPosition(),
-                                getResult().withOffset(delta),
-                                getSources().withOffset(delta),
-                                getConstant());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new PlainCstInsn(getOpcode(), getPosition(), getResult().withOffset(delta),
+        getSources().withOffset(delta), getConstant());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
 
-        return new PlainCstInsn(getOpcode(), getPosition(),
-                                result,
-                                sources,
-                                getConstant());
+    return new PlainCstInsn(getOpcode(), getPosition(), result, sources, getConstant());
 
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/PlainInsn.java b/dx/src/com/android/jack/dx/rop/code/PlainInsn.java
index a674537..3a31840 100644
--- a/dx/src/com/android/jack/dx/rop/code/PlainInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/PlainInsn.java
@@ -27,131 +27,121 @@
  * Plain instruction, which has no embedded data and which cannot possibly
  * throw an exception.
  */
-public final class PlainInsn
-        extends Insn {
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param sources {@code non-null;} specs for all the sources
-     */
-    public PlainInsn(Rop opcode, SourcePosition position,
-                     RegisterSpec result, RegisterSpecList sources) {
-        super(opcode, position, result, sources);
+public final class PlainInsn extends Insn {
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param sources {@code non-null;} specs for all the sources
+   */
+  public PlainInsn(Rop opcode, SourcePosition position, RegisterSpec result,
+      RegisterSpecList sources) {
+    super(opcode, position, result, sources);
 
-        switch (opcode.getBranchingness()) {
-            case Rop.BRANCH_SWITCH:
-            case Rop.BRANCH_THROW: {
-                throw new IllegalArgumentException("bogus branchingness");
-            }
+    switch (opcode.getBranchingness()) {
+      case Rop.BRANCH_SWITCH:
+      case Rop.BRANCH_THROW: {
+        throw new IllegalArgumentException("bogus branchingness");
+      }
+    }
+
+    if (result != null && opcode.getBranchingness() != Rop.BRANCH_NONE) {
+      // move-result-pseudo is required here
+      throw new IllegalArgumentException("can't mix branchingness with result");
+    }
+  }
+
+  /**
+   * Constructs a single-source instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param source {@code non-null;} spec for the source
+   */
+  public PlainInsn(Rop opcode, SourcePosition position, RegisterSpec result, RegisterSpec source) {
+    this(opcode, position, result, RegisterSpecList.make(source));
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return StdTypeList.EMPTY;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitPlainInsn(this);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    throw new UnsupportedOperationException("unsupported");
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new PlainInsn(getOpcode(), getPosition(), getResult().withOffset(delta),
+        getSources().withOffset(delta));
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn withSourceLiteral() {
+    RegisterSpecList sources = getSources();
+    int szSources = sources.size();
+
+    if (szSources == 0) {
+      return this;
+    }
+
+    TypeBearer lastType = sources.get(szSources - 1).getTypeBearer();
+
+    if (!lastType.isConstant()) {
+      // Check for reverse subtraction, where first source is constant
+      TypeBearer firstType = sources.get(0).getTypeBearer();
+      if (szSources == 2 && firstType.isConstant()) {
+        Constant cst = (Constant) firstType;
+        RegisterSpecList newSources = sources.withoutFirst();
+        Rop newRop = Rops.ropFor(getOpcode().getOpcode(), getResult(), newSources, cst);
+        return new PlainCstInsn(newRop, getPosition(), getResult(), newSources, cst);
+      }
+      return this;
+    } else {
+
+      Constant cst = (Constant) lastType;
+
+      RegisterSpecList newSources = sources.withoutLast();
+
+      Rop newRop;
+      try {
+        // Check for constant subtraction and flip it to be addition
+        int opcode = getOpcode().getOpcode();
+        if (opcode == RegOps.SUB && cst instanceof CstInteger) {
+          opcode = RegOps.ADD;
+          cst = CstInteger.make(-((CstInteger) cst).getValue());
         }
+        newRop = Rops.ropFor(opcode, getResult(), newSources, cst);
+      } catch (IllegalArgumentException ex) {
+        // There's no rop for this case
+        return this;
+      }
 
-        if (result != null && opcode.getBranchingness() != Rop.BRANCH_NONE) {
-            // move-result-pseudo is required here
-            throw new IllegalArgumentException
-                    ("can't mix branchingness with result");
-        }
+      return new PlainCstInsn(newRop, getPosition(), getResult(), newSources, cst);
     }
-
-    /**
-     * Constructs a single-source instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param source {@code non-null;} spec for the source
-     */
-    public PlainInsn(Rop opcode, SourcePosition position, RegisterSpec result,
-                     RegisterSpec source) {
-        this(opcode, position, result, RegisterSpecList.make(source));
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return StdTypeList.EMPTY;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitPlainInsn(this);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        throw new UnsupportedOperationException("unsupported");
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new PlainInsn(getOpcode(), getPosition(),
-                             getResult().withOffset(delta),
-                             getSources().withOffset(delta));
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public Insn withSourceLiteral() {
-        RegisterSpecList sources = getSources();
-        int szSources = sources.size();
-
-        if (szSources == 0) {
-            return this;
-        }
-
-        TypeBearer lastType = sources.get(szSources - 1).getTypeBearer();
-
-        if (!lastType.isConstant()) {
-            // Check for reverse subtraction, where first source is constant
-            TypeBearer firstType = sources.get(0).getTypeBearer();
-            if (szSources == 2 && firstType.isConstant()) {
-                Constant cst = (Constant) firstType;
-                RegisterSpecList newSources = sources.withoutFirst();
-                Rop newRop = Rops.ropFor(getOpcode().getOpcode(), getResult(),
-                                             newSources, cst);
-                return new PlainCstInsn(newRop, getPosition(), getResult(),
-                                            newSources, cst);
-            }
-            return this;
-        } else {
-
-            Constant cst = (Constant) lastType;
-
-            RegisterSpecList newSources = sources.withoutLast();
-
-            Rop newRop;
-            try {
-                // Check for constant subtraction and flip it to be addition
-                int opcode = getOpcode().getOpcode();
-                if (opcode == RegOps.SUB && cst instanceof CstInteger) {
-                    opcode = RegOps.ADD;
-                    cst = CstInteger.make(-((CstInteger)cst).getValue());
-                }
-                newRop = Rops.ropFor(opcode, getResult(), newSources, cst);
-            } catch (IllegalArgumentException ex) {
-                // There's no rop for this case
-                return this;
-            }
-
-            return new PlainCstInsn(newRop, getPosition(),
-                    getResult(), newSources, cst);
-        }
-    }
+  }
 
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
 
-        return new PlainInsn(getOpcode(), getPosition(),
-                             result,
-                             sources);
+    return new PlainInsn(getOpcode(), getPosition(), result, sources);
 
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/RegOps.java b/dx/src/com/android/jack/dx/rop/code/RegOps.java
index a863a89..4587a04 100644
--- a/dx/src/com/android/jack/dx/rop/code/RegOps.java
+++ b/dx/src/com/android/jack/dx/rop/code/RegOps.java
@@ -29,371 +29,427 @@
  * each of the values.
  */
 public final class RegOps {
-    /** {@code nop()} */
-    public static final int NOP = 1;
+  /** {@code nop()} */
+  public static final int NOP = 1;
 
-    /** {@code T: any type; r,x: T :: r = x;} */
-    public static final int MOVE = 2;
+  /** {@code T: any type; r,x: T :: r = x;} */
+  public static final int MOVE = 2;
 
-    /** {@code T: any type; r,param(x): T :: r = param(x)} */
-    public static final int MOVE_PARAM = 3;
+  /** {@code T: any type; r,param(x): T :: r = param(x)} */
+  public static final int MOVE_PARAM = 3;
 
-    /**
-     * {@code T: Throwable; r: T :: r = caught_exception}.
-     * <b>Note:</b> This opcode should only ever be used in the
-     * first instruction of a block, and such blocks must be
-     * the start of an exception handler.
-     */
-    public static final int MOVE_EXCEPTION = 4;
+  /**
+   * {@code T: Throwable; r: T :: r = caught_exception}.
+   * <b>Note:</b> This opcode should only ever be used in the
+   * first instruction of a block, and such blocks must be
+   * the start of an exception handler.
+   */
+  public static final int MOVE_EXCEPTION = 4;
 
-    /** {@code T: any type; r, literal: T :: r = literal;} */
-    public static final int CONST = 5;
+  /** {@code T: any type; r, literal: T :: r = literal;} */
+  public static final int CONST = 5;
 
-    /** {@code goto label} */
-    public static final int GOTO = 6;
+  /** {@code goto label} */
+  public static final int GOTO = 6;
 
-    /**
-     * {@code T: int or Object; x,y: T :: if (x == y) goto
-     * label}
-     */
-    public static final int IF_EQ = 7;
+  /**
+   * {@code T: int or Object; x,y: T :: if (x == y) goto
+   * label}
+   */
+  public static final int IF_EQ = 7;
 
-    /**
-     * {@code T: int or Object; x,y: T :: if (x != y) goto
-     * label}
-     */
-    public static final int IF_NE = 8;
+  /**
+   * {@code T: int or Object; x,y: T :: if (x != y) goto
+   * label}
+   */
+  public static final int IF_NE = 8;
 
-    /** {@code x,y: int :: if (x < y) goto label} */
-    public static final int IF_LT = 9;
+  /** {@code x,y: int :: if (x < y) goto label} */
+  public static final int IF_LT = 9;
 
-    /** {@code x,y: int :: if (x >= y) goto label} */
-    public static final int IF_GE = 10;
+  /** {@code x,y: int :: if (x >= y) goto label} */
+  public static final int IF_GE = 10;
 
-    /** {@code x,y: int :: if (x <= y) goto label} */
-    public static final int IF_LE = 11;
+  /** {@code x,y: int :: if (x <= y) goto label} */
+  public static final int IF_LE = 11;
 
-    /** {@code x,y: int :: if (x > y) goto label} */
-    public static final int IF_GT = 12;
+  /** {@code x,y: int :: if (x > y) goto label} */
+  public static final int IF_GT = 12;
 
-    /** {@code x: int :: goto table[x]} */
-    public static final int SWITCH = 13;
+  /** {@code x: int :: goto table[x]} */
+  public static final int SWITCH = 13;
 
-    /** {@code T: any numeric type; r,x,y: T :: r = x + y} */
-    public static final int ADD = 14;
+  /** {@code T: any numeric type; r,x,y: T :: r = x + y} */
+  public static final int ADD = 14;
 
-    /** {@code T: any numeric type; r,x,y: T :: r = x - y} */
-    public static final int SUB = 15;
+  /** {@code T: any numeric type; r,x,y: T :: r = x - y} */
+  public static final int SUB = 15;
 
-    /** {@code T: any numeric type; r,x,y: T :: r = x * y} */
-    public static final int MUL = 16;
+  /** {@code T: any numeric type; r,x,y: T :: r = x * y} */
+  public static final int MUL = 16;
 
-    /** {@code T: any numeric type; r,x,y: T :: r = x / y} */
-    public static final int DIV = 17;
+  /** {@code T: any numeric type; r,x,y: T :: r = x / y} */
+  public static final int DIV = 17;
 
-    /**
-     * {@code T: any numeric type; r,x,y: T :: r = x % y}
-     * (Java-style remainder)
-     */
-    public static final int REM = 18;
+  /**
+   * {@code T: any numeric type; r,x,y: T :: r = x % y}
+   * (Java-style remainder)
+   */
+  public static final int REM = 18;
 
-    /** {@code T: any numeric type; r,x: T :: r = -x} */
-    public static final int NEG = 19;
+  /** {@code T: any numeric type; r,x: T :: r = -x} */
+  public static final int NEG = 19;
 
-    /** {@code T: any integral type; r,x,y: T :: r = x & y} */
-    public static final int AND = 20;
+  /** {@code T: any integral type; r,x,y: T :: r = x & y} */
+  public static final int AND = 20;
 
-    /** {@code T: any integral type; r,x,y: T :: r = x | y} */
-    public static final int OR = 21;
+  /** {@code T: any integral type; r,x,y: T :: r = x | y} */
+  public static final int OR = 21;
 
-    /** {@code T: any integral type; r,x,y: T :: r = x ^ y} */
-    public static final int XOR = 22;
+  /** {@code T: any integral type; r,x,y: T :: r = x ^ y} */
+  public static final int XOR = 22;
 
-    /**
-     * {@code T: any integral type; r,x: T; y: int :: r = x << y}
-     */
-    public static final int SHL = 23;
+  /**
+   * {@code T: any integral type; r,x: T; y: int :: r = x << y}
+   */
+  public static final int SHL = 23;
 
-    /**
-     * {@code T: any integral type; r,x: T; y: int :: r = x >> y}
-     * (signed right-shift)
-     */
-    public static final int SHR = 24;
+  /**
+   * {@code T: any integral type; r,x: T; y: int :: r = x >> y}
+   * (signed right-shift)
+   */
+  public static final int SHR = 24;
 
-    /**
-     * {@code T: any integral type; r,x: T; y: int :: r = x >>> y}
-     * (unsigned right-shift)
-     */
-    public static final int USHR = 25;
+  /**
+   * {@code T: any integral type; r,x: T; y: int :: r = x >>> y}
+   * (unsigned right-shift)
+   */
+  public static final int USHR = 25;
 
-    /** {@code T: any integral type; r,x: T :: r = ~x} */
-    public static final int NOT = 26;
+  /** {@code T: any integral type; r,x: T :: r = ~x} */
+  public static final int NOT = 26;
 
-    /**
-     * {@code T: any numeric type; r: int; x,y: T :: r = (x == y) ? 0
-     * : (x > y) ? 1 : -1} (Java-style "cmpl" where a NaN is
-     * considered "less than" all other values; also used for integral
-     * comparisons)
-     */
-    public static final int CMPL = 27;
+  /**
+   * {@code T: any numeric type; r: int; x,y: T :: r = (x == y) ? 0
+   * : (x > y) ? 1 : -1} (Java-style "cmpl" where a NaN is
+   * considered "less than" all other values; also used for integral
+   * comparisons)
+   */
+  public static final int CMPL = 27;
 
-    /**
-     * {@code T: any floating point type; r: int; x,y: T :: r = (x == y) ? 0
-     * : (x < y) ? -1 : 1} (Java-style "cmpg" where a NaN is
-     * considered "greater than" all other values)
-     */
-    public static final int CMPG = 28;
+  /**
+   * {@code T: any floating point type; r: int; x,y: T :: r = (x == y) ? 0
+   * : (x < y) ? -1 : 1} (Java-style "cmpg" where a NaN is
+   * considered "greater than" all other values)
+   */
+  public static final int CMPG = 28;
 
-    /**
-     * {@code T: any numeric type; U: any numeric type; r: T; x: U ::
-     * r = (T) x} (numeric type conversion between the four
-     * "real" numeric types)
-     */
-    public static final int CONV = 29;
+  /**
+   * {@code T: any numeric type; U: any numeric type; r: T; x: U ::
+   * r = (T) x} (numeric type conversion between the four
+   * "real" numeric types)
+   */
+  public static final int CONV = 29;
 
-    /**
-     * {@code r,x: int :: r = (x << 24) >> 24} (Java-style
-     * convert int to byte)
-     */
-    public static final int TO_BYTE = 30;
+  /**
+   * {@code r,x: int :: r = (x << 24) >> 24} (Java-style
+   * convert int to byte)
+   */
+  public static final int TO_BYTE = 30;
 
-    /**
-     * {@code r,x: int :: r = x & 0xffff} (Java-style convert int to char)
-     */
-    public static final int TO_CHAR = 31;
+  /**
+   * {@code r,x: int :: r = x & 0xffff} (Java-style convert int to char)
+   */
+  public static final int TO_CHAR = 31;
 
-    /**
-     * {@code r,x: int :: r = (x << 16) >> 16} (Java-style
-     * convert int to short)
-     */
-    public static final int TO_SHORT = 32;
+  /**
+   * {@code r,x: int :: r = (x << 16) >> 16} (Java-style
+   * convert int to short)
+   */
+  public static final int TO_SHORT = 32;
 
-    /** {@code T: return type for the method; x: T; return x} */
-    public static final int RETURN = 33;
+  /** {@code T: return type for the method; x: T; return x} */
+  public static final int RETURN = 33;
 
-    /** {@code T: any type; r: int; x: T[]; :: r = x.length} */
-    public static final int ARRAY_LENGTH = 34;
+  /** {@code T: any type; r: int; x: T[]; :: r = x.length} */
+  public static final int ARRAY_LENGTH = 34;
 
-    /** {@code x: Throwable :: throw(x)} */
-    public static final int THROW = 35;
+  /** {@code x: Throwable :: throw(x)} */
+  public static final int THROW = 35;
 
-    /** {@code x: Object :: monitorenter(x)} */
-    public static final int MONITOR_ENTER = 36;
+  /** {@code x: Object :: monitorenter(x)} */
+  public static final int MONITOR_ENTER = 36;
 
-    /** {@code x: Object :: monitorexit(x)} */
-    public static final int MONITOR_EXIT = 37;
+  /** {@code x: Object :: monitorexit(x)} */
+  public static final int MONITOR_EXIT = 37;
 
-    /** {@code T: any type; r: T; x: T[]; y: int :: r = x[y]} */
-    public static final int AGET = 38;
+  /** {@code T: any type; r: T; x: T[]; y: int :: r = x[y]} */
+  public static final int AGET = 38;
 
-    /** {@code T: any type; x: T; y: T[]; z: int :: x[y] = z} */
-    public static final int APUT = 39;
+  /** {@code T: any type; x: T; y: T[]; z: int :: x[y] = z} */
+  public static final int APUT = 39;
 
-    /**
-     * {@code T: any non-array object type :: r =
-     * alloc(T)} (allocate heap space for an object)
-     */
-    public static final int NEW_INSTANCE = 40;
+  /**
+   * {@code T: any non-array object type :: r =
+   * alloc(T)} (allocate heap space for an object)
+   */
+  public static final int NEW_INSTANCE = 40;
 
-    /** {@code T: any array type; r: T; x: int :: r = new T[x]} */
-    public static final int NEW_ARRAY = 41;
+  /** {@code T: any array type; r: T; x: int :: r = new T[x]} */
+  public static final int NEW_ARRAY = 41;
 
-    /**
-     * {@code T: any array type; r: T; x: int; v0..vx: T :: r = new T[x]
-     * {v0, ..., vx}}
-     */
-    public static final int FILLED_NEW_ARRAY = 42;
+  /**
+   * {@code T: any array type; r: T; x: int; v0..vx: T :: r = new T[x]
+   * {v0, ..., vx}}
+   */
+  public static final int FILLED_NEW_ARRAY = 42;
 
-    /**
-     * {@code T: any object type; x: Object :: (T) x} (can
-     * throw {@code ClassCastException})
-     */
-    public static final int CHECK_CAST = 43;
+  /**
+   * {@code T: any object type; x: Object :: (T) x} (can
+   * throw {@code ClassCastException})
+   */
+  public static final int CHECK_CAST = 43;
 
-    /**
-     * {@code T: any object type; x: Object :: x instanceof T}
-     */
-    public static final int INSTANCE_OF = 44;
+  /**
+   * {@code T: any object type; x: Object :: x instanceof T}
+   */
+  public static final int INSTANCE_OF = 44;
 
-    /**
-     * {@code T: any type; r: T; x: Object; f: instance field spec of
-     * type T :: r = x.f}
-     */
-    public static final int GET_FIELD = 45;
+  /**
+   * {@code T: any type; r: T; x: Object; f: instance field spec of
+   * type T :: r = x.f}
+   */
+  public static final int GET_FIELD = 45;
 
-    /**
-     * {@code T: any type; r: T; f: static field spec of type T :: r =
-     * f}
-     */
-    public static final int GET_STATIC = 46;
+  /**
+   * {@code T: any type; r: T; f: static field spec of type T :: r =
+   * f}
+   */
+  public static final int GET_STATIC = 46;
 
-    /**
-     * {@code T: any type; x: T; y: Object; f: instance field spec of type
-     * T :: y.f = x}
-     */
-    public static final int PUT_FIELD = 47;
+  /**
+   * {@code T: any type; x: T; y: Object; f: instance field spec of type
+   * T :: y.f = x}
+   */
+  public static final int PUT_FIELD = 47;
 
-    /**
-     * {@code T: any type; f: static field spec of type T; x: T :: f = x}
-     */
-    public static final int PUT_STATIC = 48;
+  /**
+   * {@code T: any type; f: static field spec of type T; x: T :: f = x}
+   */
+  public static final int PUT_STATIC = 48;
 
-    /**
-     * {@code Tr, T0, T1...: any types; r: Tr; m: static method spec;
-     * y0: T0; y1: T1 ... :: r = m(y0, y1, ...)} (call static
-     * method)
-     */
-    public static final int INVOKE_STATIC = 49;
+  /**
+   * {@code Tr, T0, T1...: any types; r: Tr; m: static method spec;
+   * y0: T0; y1: T1 ... :: r = m(y0, y1, ...)} (call static
+   * method)
+   */
+  public static final int INVOKE_STATIC = 49;
 
-    /**
-     * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
-     * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call normal
-     * virtual method)
-     */
-    public static final int INVOKE_VIRTUAL = 50;
+  /**
+   * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
+   * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call normal
+   * virtual method)
+   */
+  public static final int INVOKE_VIRTUAL = 50;
 
-    /**
-     * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
-     * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call
-     * superclass virtual method)
-     */
-    public static final int INVOKE_SUPER = 51;
+  /**
+   * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
+   * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call
+   * superclass virtual method)
+   */
+  public static final int INVOKE_SUPER = 51;
 
-    /**
-     * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
-     * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call
-     * direct/special method)
-     */
-    public static final int INVOKE_DIRECT = 52;
+  /**
+   * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: instance method
+   * spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1, ...)} (call
+   * direct/special method)
+   */
+  public static final int INVOKE_DIRECT = 52;
 
-    /**
-     * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: interface
-     * (instance) method spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1,
-     * ...)} (call interface method)
-     */
-    public static final int INVOKE_INTERFACE = 53;
+  /**
+   * {@code Tr, T0, T1...: any types; r: Tr; x: Object; m: interface
+   * (instance) method spec; y0: T0; y1: T1 ... :: r = x.m(y0, y1,
+   * ...)} (call interface method)
+   */
+  public static final int INVOKE_INTERFACE = 53;
 
-    /**
-     * {@code T0: any type; name: local variable name  :: mark(name,T0)}
-     * (mark beginning or end of local variable name)
-     */
-    public static final int MARK_LOCAL = 54;
+  /**
+   * {@code T0: any type; name: local variable name  :: mark(name,T0)}
+   * (mark beginning or end of local variable name)
+   */
+  public static final int MARK_LOCAL = 54;
 
-    /**
-     * {@code T: Any type; r: T :: r = return_type}.
-     * <b>Note:</b> This opcode should only ever be used in the
-     * first instruction of a block following an invoke-*.
-     */
-    public static final int MOVE_RESULT = 55;
+  /**
+   * {@code T: Any type; r: T :: r = return_type}.
+   * <b>Note:</b> This opcode should only ever be used in the
+   * first instruction of a block following an invoke-*.
+   */
+  public static final int MOVE_RESULT = 55;
 
-    /**
-     * {@code T: Any type; r: T :: r = return_type}.
-     * <b>Note:</b> This opcode should only ever be used in the
-     * first instruction of a block following a non-invoke throwing insn
-     */
-    public static final int MOVE_RESULT_PSEUDO = 56;
+  /**
+   * {@code T: Any type; r: T :: r = return_type}.
+   * <b>Note:</b> This opcode should only ever be used in the
+   * first instruction of a block following a non-invoke throwing insn
+   */
+  public static final int MOVE_RESULT_PSEUDO = 56;
 
-    /** {@code T: Any primitive type; v0..vx: T :: {v0, ..., vx}} */
-    public static final int FILL_ARRAY_DATA = 57;
+  /** {@code T: Any primitive type; v0..vx: T :: {v0, ..., vx}} */
+  public static final int FILL_ARRAY_DATA = 57;
 
-    /**
-     * This class is uninstantiable.
-     */
-    private RegOps() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private RegOps() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Gets the name of the given opcode.
+   *
+   * @param opcode the opcode
+   * @return {@code non-null;} its name
+   */
+  public static String opName(int opcode) {
+    switch (opcode) {
+      case NOP:
+        return "nop";
+      case MOVE:
+        return "move";
+      case MOVE_PARAM:
+        return "move-param";
+      case MOVE_EXCEPTION:
+        return "move-exception";
+      case CONST:
+        return "const";
+      case GOTO:
+        return "goto";
+      case IF_EQ:
+        return "if-eq";
+      case IF_NE:
+        return "if-ne";
+      case IF_LT:
+        return "if-lt";
+      case IF_GE:
+        return "if-ge";
+      case IF_LE:
+        return "if-le";
+      case IF_GT:
+        return "if-gt";
+      case SWITCH:
+        return "switch";
+      case ADD:
+        return "add";
+      case SUB:
+        return "sub";
+      case MUL:
+        return "mul";
+      case DIV:
+        return "div";
+      case REM:
+        return "rem";
+      case NEG:
+        return "neg";
+      case AND:
+        return "and";
+      case OR:
+        return "or";
+      case XOR:
+        return "xor";
+      case SHL:
+        return "shl";
+      case SHR:
+        return "shr";
+      case USHR:
+        return "ushr";
+      case NOT:
+        return "not";
+      case CMPL:
+        return "cmpl";
+      case CMPG:
+        return "cmpg";
+      case CONV:
+        return "conv";
+      case TO_BYTE:
+        return "to-byte";
+      case TO_CHAR:
+        return "to-char";
+      case TO_SHORT:
+        return "to-short";
+      case RETURN:
+        return "return";
+      case ARRAY_LENGTH:
+        return "array-length";
+      case THROW:
+        return "throw";
+      case MONITOR_ENTER:
+        return "monitor-enter";
+      case MONITOR_EXIT:
+        return "monitor-exit";
+      case AGET:
+        return "aget";
+      case APUT:
+        return "aput";
+      case NEW_INSTANCE:
+        return "new-instance";
+      case NEW_ARRAY:
+        return "new-array";
+      case FILLED_NEW_ARRAY:
+        return "filled-new-array";
+      case CHECK_CAST:
+        return "check-cast";
+      case INSTANCE_OF:
+        return "instance-of";
+      case GET_FIELD:
+        return "get-field";
+      case GET_STATIC:
+        return "get-static";
+      case PUT_FIELD:
+        return "put-field";
+      case PUT_STATIC:
+        return "put-static";
+      case INVOKE_STATIC:
+        return "invoke-static";
+      case INVOKE_VIRTUAL:
+        return "invoke-virtual";
+      case INVOKE_SUPER:
+        return "invoke-super";
+      case INVOKE_DIRECT:
+        return "invoke-direct";
+      case INVOKE_INTERFACE:
+        return "invoke-interface";
+      case MOVE_RESULT:
+        return "move-result";
+      case MOVE_RESULT_PSEUDO:
+        return "move-result-pseudo";
+      case FILL_ARRAY_DATA:
+        return "fill-array-data";
     }
 
-    /**
-     * Gets the name of the given opcode.
-     *
-     * @param opcode the opcode
-     * @return {@code non-null;} its name
-     */
-    public static String opName(int opcode) {
-        switch (opcode) {
-            case NOP: return "nop";
-            case MOVE: return "move";
-            case MOVE_PARAM: return "move-param";
-            case MOVE_EXCEPTION: return "move-exception";
-            case CONST: return "const";
-            case GOTO: return "goto";
-            case IF_EQ: return "if-eq";
-            case IF_NE: return "if-ne";
-            case IF_LT: return "if-lt";
-            case IF_GE: return "if-ge";
-            case IF_LE: return "if-le";
-            case IF_GT: return "if-gt";
-            case SWITCH: return "switch";
-            case ADD: return "add";
-            case SUB: return "sub";
-            case MUL: return "mul";
-            case DIV: return "div";
-            case REM: return "rem";
-            case NEG: return "neg";
-            case AND: return "and";
-            case OR: return "or";
-            case XOR: return "xor";
-            case SHL: return "shl";
-            case SHR: return "shr";
-            case USHR: return "ushr";
-            case NOT: return "not";
-            case CMPL: return "cmpl";
-            case CMPG: return "cmpg";
-            case CONV: return "conv";
-            case TO_BYTE: return "to-byte";
-            case TO_CHAR: return "to-char";
-            case TO_SHORT: return "to-short";
-            case RETURN: return "return";
-            case ARRAY_LENGTH: return "array-length";
-            case THROW: return "throw";
-            case MONITOR_ENTER: return "monitor-enter";
-            case MONITOR_EXIT: return "monitor-exit";
-            case AGET: return "aget";
-            case APUT: return "aput";
-            case NEW_INSTANCE: return "new-instance";
-            case NEW_ARRAY: return "new-array";
-            case FILLED_NEW_ARRAY: return "filled-new-array";
-            case CHECK_CAST: return "check-cast";
-            case INSTANCE_OF: return "instance-of";
-            case GET_FIELD: return "get-field";
-            case GET_STATIC: return "get-static";
-            case PUT_FIELD: return "put-field";
-            case PUT_STATIC: return "put-static";
-            case INVOKE_STATIC: return "invoke-static";
-            case INVOKE_VIRTUAL: return "invoke-virtual";
-            case INVOKE_SUPER: return "invoke-super";
-            case INVOKE_DIRECT: return "invoke-direct";
-            case INVOKE_INTERFACE: return "invoke-interface";
-            case MOVE_RESULT: return "move-result";
-            case MOVE_RESULT_PSEUDO: return "move-result-pseudo";
-            case FILL_ARRAY_DATA: return "fill-array-data";
-        }
+    return "unknown-" + Hex.u1(opcode);
+  }
 
-        return "unknown-" + Hex.u1(opcode);
+  /**
+   * Given an IF_* RegOp, returns the right-to-left flipped version. For
+   * example, IF_GT becomes IF_LT.
+   *
+   * @param opcode An IF_* RegOp
+   * @return flipped IF Regop
+   */
+  public static int flippedIfOpcode(final int opcode) {
+    switch (opcode) {
+      case RegOps.IF_EQ:
+      case RegOps.IF_NE:
+        return opcode;
+      case RegOps.IF_LT:
+        return RegOps.IF_GT;
+      case RegOps.IF_GE:
+        return RegOps.IF_LE;
+      case RegOps.IF_LE:
+        return RegOps.IF_GE;
+      case RegOps.IF_GT:
+        return RegOps.IF_LT;
+      default:
+        throw new RuntimeException("Unrecognized IF regop: " + opcode);
     }
-
-    /**
-     * Given an IF_* RegOp, returns the right-to-left flipped version. For
-     * example, IF_GT becomes IF_LT.
-     *
-     * @param opcode An IF_* RegOp
-     * @return flipped IF Regop
-     */
-    public static int flippedIfOpcode(final int opcode) {
-        switch (opcode) {
-            case RegOps.IF_EQ:
-            case RegOps.IF_NE:
-                return opcode;
-            case RegOps.IF_LT:
-                return RegOps.IF_GT;
-            case RegOps.IF_GE:
-                return RegOps.IF_LE;
-            case RegOps.IF_LE:
-                return RegOps.IF_GE;
-            case RegOps.IF_GT:
-                return RegOps.IF_LT;
-            default:
-                throw new RuntimeException("Unrecognized IF regop: " + opcode);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/RegisterSpec.java b/dx/src/com/android/jack/dx/rop/code/RegisterSpec.java
index 2460041..e9f1474 100644
--- a/dx/src/com/android/jack/dx/rop/code/RegisterSpec.java
+++ b/dx/src/com/android/jack/dx/rop/code/RegisterSpec.java
@@ -28,630 +28,626 @@
  * Combination of a register number and a type, used as the sources and
  * destinations of register-based operations.
  */
-public final class RegisterSpec
-        implements TypeBearer, ToHuman, Comparable<RegisterSpec> {
-    /** {@code non-null;} string to prefix register numbers with */
-    public static final String PREFIX = "v";
+public final class RegisterSpec implements TypeBearer, ToHuman, Comparable<RegisterSpec> {
+  /** {@code non-null;} string to prefix register numbers with */
+  public static final String PREFIX = "v";
 
-    /** {@code non-null;} intern table for instances */
-    private static final HashMap<Object, RegisterSpec> theInterns =
-        new HashMap<Object, RegisterSpec>(1000);
+  /** {@code non-null;} intern table for instances */
+  private static final HashMap<Object, RegisterSpec> theInterns =
+      new HashMap<Object, RegisterSpec>(1000);
 
-    /** {@code non-null;} common comparison instance used while interning */
-    private static final ForComparison theInterningItem = new ForComparison();
+  /** {@code non-null;} common comparison instance used while interning */
+  private static final ForComparison theInterningItem = new ForComparison();
 
+  /** {@code >= 0;} register number */
+  private final int reg;
+
+  /** {@code non-null;} type loaded or stored */
+  private final TypeBearer type;
+
+  /**
+   * {@code null-ok;} local variable info associated with this register,
+   * if any
+   */
+  private final LocalItem local;
+
+  /**
+   * Intern the given triple as an instance of this class.
+   *
+   * @param reg {@code >= 0;} the register number
+   * @param type {@code non-null;} the type (or possibly actual value) which
+   * is loaded from or stored to the indicated register
+   * @param local {@code null-ok;} the associated local variable, if any
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  private static RegisterSpec intern(int reg, TypeBearer type, LocalItem local) {
+    synchronized (theInterns) {
+      theInterningItem.set(reg, type, local);
+      RegisterSpec found = theInterns.get(theInterningItem);
+
+      if (found != null) {
+        return found;
+      }
+
+      found = theInterningItem.toRegisterSpec();
+      theInterns.put(found, found);
+      return found;
+    }
+  }
+
+  /**
+   * Returns an instance for the given register number and type, with
+   * no variable info. This method is allowed to return shared
+   * instances (but doesn't necessarily do so).
+   *
+   * @param reg {@code >= 0;} the register number
+   * @param type {@code non-null;} the type (or possibly actual value) which
+   * is loaded from or stored to the indicated register
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpec make(int reg, TypeBearer type) {
+    return intern(reg, type, null);
+  }
+
+  /**
+   * Returns an instance for the given register number, type, and
+   * variable info. This method is allowed to return shared
+   * instances (but doesn't necessarily do so).
+   *
+   * @param reg {@code >= 0;} the register number
+   * @param type {@code non-null;} the type (or possibly actual value) which
+   * is loaded from or stored to the indicated register
+   * @param local {@code non-null;} the associated local variable
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpec make(int reg, TypeBearer type, LocalItem local) {
+    if (local == null) {
+      throw new NullPointerException("local  == null");
+    }
+
+    return intern(reg, type, local);
+  }
+
+  /**
+   * Returns an instance for the given register number, type, and
+   * variable info. This method is allowed to return shared
+   * instances (but doesn't necessarily do so).
+   *
+   * @param reg {@code >= 0;} the register number
+   * @param type {@code non-null;} the type (or possibly actual value) which
+   * is loaded from or stored to the indicated register
+   * @param local {@code null-ok;} the associated variable info or null for
+   * none
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpec makeLocalOptional(int reg, TypeBearer type, LocalItem local) {
+
+    return intern(reg, type, local);
+  }
+
+  /**
+   * Gets the string form for the given register number.
+   *
+   * @param reg {@code >= 0;} the register number
+   * @return {@code non-null;} the string form
+   */
+  public static String regString(int reg) {
+    return PREFIX + reg;
+  }
+
+  /**
+   * Constructs an instance. This constructor is private. Use
+   * {@link #make}.
+   *
+   * @param reg {@code >= 0;} the register number
+   * @param type {@code non-null;} the type (or possibly actual value) which
+   * is loaded from or stored to the indicated register
+   * @param local {@code null-ok;} the associated local variable, if any
+   */
+  private RegisterSpec(int reg, TypeBearer type, LocalItem local) {
+    if (reg < 0) {
+      throw new IllegalArgumentException("reg < 0");
+    }
+
+    if (type == null) {
+      throw new NullPointerException("type == null");
+    }
+
+    this.reg = reg;
+    this.type = type;
+    this.local = local;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof RegisterSpec)) {
+      if (other instanceof ForComparison) {
+        ForComparison fc = (ForComparison) other;
+        return equals(fc.reg, fc.type, fc.local);
+      }
+      return false;
+    }
+
+    RegisterSpec spec = (RegisterSpec) other;
+    return equals(spec.reg, spec.type, spec.local);
+  }
+
+  /**
+   * Like {@code equals}, but only consider the simple types of the
+   * registers. That is, this compares {@code getType()} on the types
+   * to ignore whatever arbitrary extra stuff might be carried around
+   * by an outer {@link TypeBearer}.
+   *
+   * @param other {@code null-ok;} spec to compare to
+   * @return {@code true} iff {@code this} and {@code other} are equal
+   * in the stated way
+   */
+  public boolean equalsUsingSimpleType(RegisterSpec other) {
+    if (!matchesVariable(other)) {
+      return false;
+    }
+
+    return (reg == other.reg);
+  }
+
+  /**
+   * Like {@link #equalsUsingSimpleType} but ignoring the register number.
+   * This is useful to determine if two instances refer to the "same"
+   * local variable.
+   *
+   * @param other {@code null-ok;} spec to compare to
+   * @return {@code true} iff {@code this} and {@code other} are equal
+   * in the stated way
+   */
+  public boolean matchesVariable(RegisterSpec other) {
+    if (other == null) {
+      return false;
+    }
+
+    return type.getType().equals(other.type.getType())
+        && ((local == other.local) || ((local != null) && local.equals(other.local)));
+  }
+
+  /**
+   * Helper for {@link #equals} and {@link #ForComparison.equals},
+   * which actually does the test.
+   *
+   * @param reg value of the instance variable, for another instance
+   * @param type value of the instance variable, for another instance
+   * @param local value of the instance variable, for another instance
+   * @return whether this instance is equal to one with the given
+   * values
+   */
+  private boolean equals(int reg, TypeBearer type, LocalItem local) {
+    return (this.reg == reg) && this.type.equals(type)
+        && ((this.local == local) || ((this.local != null) && this.local.equals(local)));
+  }
+
+  /**
+   * Compares by (in priority order) register number, unwrapped type
+   * (that is types not {@link TypeBearer}s, and local info.
+   *
+   * @param other {@code non-null;} spec to compare to
+   * @return {@code -1..1;} standard result of comparison
+   */
+  @Override
+  public int compareTo(RegisterSpec other) {
+    if (this.reg < other.reg) {
+      return -1;
+    } else if (this.reg > other.reg) {
+      return 1;
+    }
+
+    int compare = type.getType().compareTo(other.type.getType());
+
+    if (compare != 0) {
+      return compare;
+    }
+
+    if (this.local == null) {
+      return (other.local == null) ? 0 : -1;
+    } else if (other.local == null) {
+      return 1;
+    }
+
+    return this.local.compareTo(other.local);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return hashCodeOf(reg, type, local);
+  }
+
+  /**
+   * Helper for {@link #hashCode} and {@link #ForComparison.hashCode},
+   * which actually does the calculation.
+   *
+   * @param reg value of the instance variable
+   * @param type value of the instance variable
+   * @param local value of the instance variable
+   * @return the hash code
+   */
+  private static int hashCodeOf(int reg, TypeBearer type, LocalItem local) {
+    int hash = (local != null) ? local.hashCode() : 0;
+
+    hash = (hash * 31 + type.hashCode()) * 31 + reg;
+    return hash;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return toString0(false);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return toString0(true);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return type.getType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public TypeBearer getFrameType() {
+    return type.getFrameType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int getBasicType() {
+    return type.getBasicType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int getBasicFrameType() {
+    return type.getBasicFrameType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final boolean isConstant() {
+    return false;
+  }
+
+  /**
+   * Gets the register number.
+   *
+   * @return {@code >= 0;} the register number
+   */
+  public int getReg() {
+    return reg;
+  }
+
+  /**
+   * Gets the type (or actual value) which is loaded from or stored
+   * to the register associated with this instance.
+   *
+   * @return {@code non-null;} the type
+   */
+  public TypeBearer getTypeBearer() {
+    return type;
+  }
+
+  /**
+   * Gets the variable info associated with this instance, if any.
+   *
+   * @return {@code null-ok;} the variable info, or {@code null} if this
+   * instance has none
+   */
+  public LocalItem getLocalItem() {
+    return local;
+  }
+
+  /**
+   * Gets the next available register number after the one in this
+   * instance. This is equal to the register number plus the width
+   * (category) of the type used. Among other things, this may also
+   * be used to determine the minimum required register count
+   * implied by this instance.
+   *
+   * @return {@code >= 0;} the required registers size
+   */
+  public int getNextReg() {
+    return reg + getCategory();
+  }
+
+  /**
+   * Gets the category of this instance's type. This is just a convenient
+   * shorthand for {@code getType().getCategory()}.
+   *
+   * @see #isCategory1
+   * @see #isCategory2
+   * @return {@code 1..2;} the category of this instance's type
+   */
+  public int getCategory() {
+    return type.getType().getCategory();
+  }
+
+  /**
+   * Gets whether this instance's type is category 1. This is just a
+   * convenient shorthand for {@code getType().isCategory1()}.
+   *
+   * @see #getCategory
+   * @see #isCategory2
+   * @return whether or not this instance's type is of category 1
+   */
+  public boolean isCategory1() {
+    return type.getType().isCategory1();
+  }
+
+  /**
+   * Gets whether this instance's type is category 2. This is just a
+   * convenient shorthand for {@code getType().isCategory2()}.
+   *
+   * @see #getCategory
+   * @see #isCategory1
+   * @return whether or not this instance's type is of category 2
+   */
+  public boolean isCategory2() {
+    return type.getType().isCategory2();
+  }
+
+  /**
+   * Gets the string form for just the register number of this instance.
+   *
+   * @return {@code non-null;} the register string form
+   */
+  public String regString() {
+    return regString(reg);
+  }
+
+  /**
+   * Returns an instance that is the intersection between this instance
+   * and the given one, if any. The intersection is defined as follows:
+   *
+   * <ul>
+   *   <li>If {@code other} is {@code null}, then the result
+   *     is {@code null}.
+   *   <li>If the register numbers don't match, then the intersection
+   *     is {@code null}. Otherwise, the register number of the
+   *     intersection is the same as the one in the two instances.</li>
+   *   <li>If the types returned by {@code getType()} are not
+   *     {@code equals()}, then the intersection is null.</li>
+   *   <li>If the type bearers returned by {@code getTypeBearer()}
+   *     are {@code equals()}, then the intersection's type bearer
+   *     is the one from this instance. Otherwise, the intersection's
+   *     type bearer is the {@code getType()} of this instance.</li>
+   *   <li>If the locals are {@code equals()}, then the local info
+   *     of the intersection is the local info of this instance. Otherwise,
+   *     the local info of the intersection is {@code null}.</li>
+   * </ul>
+   *
+   * @param other {@code null-ok;} instance to intersect with (or {@code null})
+   * @param localPrimary whether local variables are primary to the
+   * intersection; if {@code true}, then the only non-null
+   * results occur when registers being intersected have equal local
+   * infos (or both have {@code null} local infos)
+   * @return {@code null-ok;} the intersection
+   */
+  public RegisterSpec intersect(RegisterSpec other, boolean localPrimary) {
+    if (this == other) {
+      // Easy out.
+      return this;
+    }
+
+    if ((other == null) || (reg != other.getReg())) {
+      return null;
+    }
+
+    LocalItem resultLocal = ((local == null) || !local.equals(other.getLocalItem())) ? null : local;
+    boolean sameName = (resultLocal == local);
+
+    if (localPrimary && !sameName) {
+      return null;
+    }
+
+    Type thisType = getType();
+    Type otherType = other.getType();
+
+    // Note: Types are always interned.
+    if (thisType != otherType) {
+      return null;
+    }
+
+    TypeBearer resultTypeBearer = type.equals(other.getTypeBearer()) ? type : thisType;
+
+    if ((resultTypeBearer == type) && sameName) {
+      // It turns out that the intersection is "this" after all.
+      return this;
+    }
+
+    return (resultLocal == null) ? make(reg, resultTypeBearer)
+        : make(reg, resultTypeBearer, resultLocal);
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that the
+   * register number is replaced by the given one.
+   *
+   * @param newReg {@code >= 0;} the new register number
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpec withReg(int newReg) {
+    if (reg == newReg) {
+      return this;
+    }
+
+    return makeLocalOptional(newReg, type, local);
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the type is replaced by the given one.
+   *
+   * @param newType {@code non-null;} the new type
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpec withType(TypeBearer newType) {
+    return makeLocalOptional(reg, newType, local);
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that the
+   * register number is offset by the given amount.
+   *
+   * @param delta the amount to offset the register number by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpec withOffset(int delta) {
+    if (delta == 0) {
+      return this;
+    }
+
+    return withReg(reg + delta);
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the type bearer is replaced by the actual underlying type
+   * (thereby stripping off non-type information) with any
+   * initialization information stripped away as well.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpec withSimpleType() {
+    TypeBearer orig = type;
+    Type newType;
+
+    if (orig instanceof Type) {
+      newType = (Type) orig;
+    } else {
+      newType = orig.getType();
+    }
+
+    if (newType.isUninitialized()) {
+      newType = newType.getInitializedType();
+    }
+
+    if (newType == orig) {
+      return this;
+    }
+
+    return makeLocalOptional(reg, newType, local);
+  }
+
+  /**
+   * Returns an instance that is identical to this one except that the
+   * local variable is as specified in the parameter.
+   *
+   * @param local {@code null-ok;} the local item or null for none
+   * @return an appropriate instance
+   */
+  public RegisterSpec withLocalItem(LocalItem local) {
+    if ((this.local == local) || ((this.local != null) && this.local.equals(local))) {
+
+      return this;
+    }
+
+    return makeLocalOptional(reg, type, local);
+  }
+
+
+  /**
+   * Helper for {@link #toString} and {@link #toHuman}.
+   *
+   * @param human whether to be human-oriented
+   * @return {@code non-null;} the string form
+   */
+  private String toString0(boolean human) {
+    StringBuffer sb = new StringBuffer(40);
+
+    sb.append(regString());
+    sb.append(":");
+
+    if (local != null) {
+      sb.append(local.toString());
+    }
+
+    Type justType = type.getType();
+    sb.append(justType);
+
+    if (justType != type) {
+      sb.append("=");
+      if (human && (type instanceof CstString)) {
+        sb.append(((CstString) type).toQuoted());
+      } else if (human && (type instanceof Constant)) {
+        sb.append(type.toHuman());
+      } else {
+        sb.append(type);
+      }
+    }
+
+    return sb.toString();
+  }
+
+  /**
+   * Holder of register spec data for the purposes of comparison (so that
+   * {@code RegisterSpec} itself can still keep {@code final}
+   * instance variables.
+   */
+  private static class ForComparison {
     /** {@code >= 0;} register number */
-    private final int reg;
+    private int reg;
 
     /** {@code non-null;} type loaded or stored */
-    private final TypeBearer type;
+    private TypeBearer type;
 
     /**
-     * {@code null-ok;} local variable info associated with this register,
-     * if any
+     * {@code null-ok;} local variable associated with this
+     * register, if any
      */
-    private final LocalItem local;
+    private LocalItem local;
 
     /**
-     * Intern the given triple as an instance of this class.
+     * Set all the instance variables.
      *
      * @param reg {@code >= 0;} the register number
-     * @param type {@code non-null;} the type (or possibly actual value) which
-     * is loaded from or stored to the indicated register
+     * @param type {@code non-null;} the type (or possibly actual
+     * value) which is loaded from or stored to the indicated
+     * register
      * @param local {@code null-ok;} the associated local variable, if any
      * @return {@code non-null;} an appropriately-constructed instance
      */
-    private static RegisterSpec intern(int reg, TypeBearer type,
-            LocalItem local) {
-        synchronized (theInterns) {
-            theInterningItem.set(reg, type, local);
-            RegisterSpec found = theInterns.get(theInterningItem);
-
-            if (found != null) {
-                return found;
-            }
-
-            found = theInterningItem.toRegisterSpec();
-            theInterns.put(found, found);
-            return found;
-        }
+    public void set(int reg, TypeBearer type, LocalItem local) {
+      this.reg = reg;
+      this.type = type;
+      this.local = local;
     }
 
     /**
-     * Returns an instance for the given register number and type, with
-     * no variable info. This method is allowed to return shared
-     * instances (but doesn't necessarily do so).
+     * Construct a {@code RegisterSpec} of this instance's
+     * contents.
      *
-     * @param reg {@code >= 0;} the register number
-     * @param type {@code non-null;} the type (or possibly actual value) which
-     * is loaded from or stored to the indicated register
      * @return {@code non-null;} an appropriately-constructed instance
      */
-    public static RegisterSpec make(int reg, TypeBearer type) {
-        return intern(reg, type, null);
-    }
-
-    /**
-     * Returns an instance for the given register number, type, and
-     * variable info. This method is allowed to return shared
-     * instances (but doesn't necessarily do so).
-     *
-     * @param reg {@code >= 0;} the register number
-     * @param type {@code non-null;} the type (or possibly actual value) which
-     * is loaded from or stored to the indicated register
-     * @param local {@code non-null;} the associated local variable
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpec make(int reg, TypeBearer type,
-            LocalItem local) {
-        if (local == null) {
-            throw new NullPointerException("local  == null");
-        }
-
-        return intern(reg, type, local);
-    }
-
-    /**
-     * Returns an instance for the given register number, type, and
-     * variable info. This method is allowed to return shared
-     * instances (but doesn't necessarily do so).
-     *
-     * @param reg {@code >= 0;} the register number
-     * @param type {@code non-null;} the type (or possibly actual value) which
-     * is loaded from or stored to the indicated register
-     * @param local {@code null-ok;} the associated variable info or null for
-     * none
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpec makeLocalOptional(
-            int reg, TypeBearer type, LocalItem local) {
-
-        return intern(reg, type, local);
-    }
-
-    /**
-     * Gets the string form for the given register number.
-     *
-     * @param reg {@code >= 0;} the register number
-     * @return {@code non-null;} the string form
-     */
-    public static String regString(int reg) {
-        return PREFIX + reg;
-    }
-
-    /**
-     * Constructs an instance. This constructor is private. Use
-     * {@link #make}.
-     *
-     * @param reg {@code >= 0;} the register number
-     * @param type {@code non-null;} the type (or possibly actual value) which
-     * is loaded from or stored to the indicated register
-     * @param local {@code null-ok;} the associated local variable, if any
-     */
-    private RegisterSpec(int reg, TypeBearer type, LocalItem local) {
-        if (reg < 0) {
-            throw new IllegalArgumentException("reg < 0");
-        }
-
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
-
-        this.reg = reg;
-        this.type = type;
-        this.local = local;
+    public RegisterSpec toRegisterSpec() {
+      return new RegisterSpec(reg, type, local);
     }
 
     /** {@inheritDoc} */
     @Override
     public boolean equals(Object other) {
-        if (!(other instanceof RegisterSpec)) {
-            if (other instanceof ForComparison) {
-                ForComparison fc = (ForComparison) other;
-                return equals(fc.reg, fc.type, fc.local);
-            }
-            return false;
-        }
+      if (!(other instanceof RegisterSpec)) {
+        return false;
+      }
 
-        RegisterSpec spec = (RegisterSpec) other;
-        return equals(spec.reg, spec.type, spec.local);
-    }
-
-    /**
-     * Like {@code equals}, but only consider the simple types of the
-     * registers. That is, this compares {@code getType()} on the types
-     * to ignore whatever arbitrary extra stuff might be carried around
-     * by an outer {@link TypeBearer}.
-     *
-     * @param other {@code null-ok;} spec to compare to
-     * @return {@code true} iff {@code this} and {@code other} are equal
-     * in the stated way
-     */
-    public boolean equalsUsingSimpleType(RegisterSpec other) {
-        if (!matchesVariable(other)) {
-            return false;
-        }
-
-        return (reg == other.reg);
-    }
-
-    /**
-     * Like {@link #equalsUsingSimpleType} but ignoring the register number.
-     * This is useful to determine if two instances refer to the "same"
-     * local variable.
-     *
-     * @param other {@code null-ok;} spec to compare to
-     * @return {@code true} iff {@code this} and {@code other} are equal
-     * in the stated way
-     */
-    public boolean matchesVariable(RegisterSpec other) {
-        if (other == null) {
-            return false;
-        }
-
-        return type.getType().equals(other.type.getType())
-            && ((local == other.local)
-                    || ((local != null) && local.equals(other.local)));
-    }
-
-    /**
-     * Helper for {@link #equals} and {@link #ForComparison.equals},
-     * which actually does the test.
-     *
-     * @param reg value of the instance variable, for another instance
-     * @param type value of the instance variable, for another instance
-     * @param local value of the instance variable, for another instance
-     * @return whether this instance is equal to one with the given
-     * values
-     */
-    private boolean equals(int reg, TypeBearer type, LocalItem local) {
-        return (this.reg == reg)
-            && this.type.equals(type)
-            && ((this.local == local)
-                    || ((this.local != null) && this.local.equals(local)));
-    }
-
-    /**
-     * Compares by (in priority order) register number, unwrapped type
-     * (that is types not {@link TypeBearer}s, and local info.
-     *
-     * @param other {@code non-null;} spec to compare to
-     * @return {@code -1..1;} standard result of comparison
-     */
-    public int compareTo(RegisterSpec other) {
-        if (this.reg < other.reg) {
-            return -1;
-        } else if (this.reg > other.reg) {
-            return 1;
-        }
-
-        int compare = type.getType().compareTo(other.type.getType());
-
-        if (compare != 0) {
-            return compare;
-        }
-
-        if (this.local == null) {
-            return (other.local == null) ? 0 : -1;
-        } else if (other.local == null) {
-            return 1;
-        }
-
-        return this.local.compareTo(other.local);
+      RegisterSpec spec = (RegisterSpec) other;
+      return spec.equals(reg, type, local);
     }
 
     /** {@inheritDoc} */
     @Override
     public int hashCode() {
-        return hashCodeOf(reg, type, local);
+      return hashCodeOf(reg, type, local);
     }
-
-    /**
-     * Helper for {@link #hashCode} and {@link #ForComparison.hashCode},
-     * which actually does the calculation.
-     *
-     * @param reg value of the instance variable
-     * @param type value of the instance variable
-     * @param local value of the instance variable
-     * @return the hash code
-     */
-    private static int hashCodeOf(int reg, TypeBearer type, LocalItem local) {
-        int hash = (local != null) ? local.hashCode() : 0;
-
-        hash = (hash * 31 + type.hashCode()) * 31 + reg;
-        return hash;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return toString0(false);
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return toString0(true);
-    }
-
-    /** {@inheritDoc} */
-    public Type getType() {
-        return type.getType();
-    }
-
-    /** {@inheritDoc} */
-    public TypeBearer getFrameType() {
-        return type.getFrameType();
-    }
-
-    /** {@inheritDoc} */
-    public final int getBasicType() {
-        return type.getBasicType();
-    }
-
-    /** {@inheritDoc} */
-    public final int getBasicFrameType() {
-        return type.getBasicFrameType();
-    }
-
-    /** {@inheritDoc} */
-    public final boolean isConstant() {
-        return false;
-    }
-
-    /**
-     * Gets the register number.
-     *
-     * @return {@code >= 0;} the register number
-     */
-    public int getReg() {
-        return reg;
-    }
-
-    /**
-     * Gets the type (or actual value) which is loaded from or stored
-     * to the register associated with this instance.
-     *
-     * @return {@code non-null;} the type
-     */
-    public TypeBearer getTypeBearer() {
-        return type;
-    }
-
-    /**
-     * Gets the variable info associated with this instance, if any.
-     *
-     * @return {@code null-ok;} the variable info, or {@code null} if this
-     * instance has none
-     */
-    public LocalItem getLocalItem() {
-        return local;
-    }
-
-    /**
-     * Gets the next available register number after the one in this
-     * instance. This is equal to the register number plus the width
-     * (category) of the type used. Among other things, this may also
-     * be used to determine the minimum required register count
-     * implied by this instance.
-     *
-     * @return {@code >= 0;} the required registers size
-     */
-    public int getNextReg() {
-        return reg + getCategory();
-    }
-
-    /**
-     * Gets the category of this instance's type. This is just a convenient
-     * shorthand for {@code getType().getCategory()}.
-     *
-     * @see #isCategory1
-     * @see #isCategory2
-     * @return {@code 1..2;} the category of this instance's type
-     */
-    public int getCategory() {
-        return type.getType().getCategory();
-    }
-
-    /**
-     * Gets whether this instance's type is category 1. This is just a
-     * convenient shorthand for {@code getType().isCategory1()}.
-     *
-     * @see #getCategory
-     * @see #isCategory2
-     * @return whether or not this instance's type is of category 1
-     */
-    public boolean isCategory1() {
-        return type.getType().isCategory1();
-    }
-
-    /**
-     * Gets whether this instance's type is category 2. This is just a
-     * convenient shorthand for {@code getType().isCategory2()}.
-     *
-     * @see #getCategory
-     * @see #isCategory1
-     * @return whether or not this instance's type is of category 2
-     */
-    public boolean isCategory2() {
-        return type.getType().isCategory2();
-    }
-
-    /**
-     * Gets the string form for just the register number of this instance.
-     *
-     * @return {@code non-null;} the register string form
-     */
-    public String regString() {
-        return regString(reg);
-    }
-
-    /**
-     * Returns an instance that is the intersection between this instance
-     * and the given one, if any. The intersection is defined as follows:
-     *
-     * <ul>
-     *   <li>If {@code other} is {@code null}, then the result
-     *     is {@code null}.
-     *   <li>If the register numbers don't match, then the intersection
-     *     is {@code null}. Otherwise, the register number of the
-     *     intersection is the same as the one in the two instances.</li>
-     *   <li>If the types returned by {@code getType()} are not
-     *     {@code equals()}, then the intersection is null.</li>
-     *   <li>If the type bearers returned by {@code getTypeBearer()}
-     *     are {@code equals()}, then the intersection's type bearer
-     *     is the one from this instance. Otherwise, the intersection's
-     *     type bearer is the {@code getType()} of this instance.</li>
-     *   <li>If the locals are {@code equals()}, then the local info
-     *     of the intersection is the local info of this instance. Otherwise,
-     *     the local info of the intersection is {@code null}.</li>
-     * </ul>
-     *
-     * @param other {@code null-ok;} instance to intersect with (or {@code null})
-     * @param localPrimary whether local variables are primary to the
-     * intersection; if {@code true}, then the only non-null
-     * results occur when registers being intersected have equal local
-     * infos (or both have {@code null} local infos)
-     * @return {@code null-ok;} the intersection
-     */
-    public RegisterSpec intersect(RegisterSpec other, boolean localPrimary) {
-        if (this == other) {
-            // Easy out.
-            return this;
-        }
-
-        if ((other == null) || (reg != other.getReg())) {
-            return null;
-        }
-
-        LocalItem resultLocal =
-            ((local == null) || !local.equals(other.getLocalItem()))
-            ? null : local;
-        boolean sameName = (resultLocal == local);
-
-        if (localPrimary && !sameName) {
-            return null;
-        }
-
-        Type thisType = getType();
-        Type otherType = other.getType();
-
-        // Note: Types are always interned.
-        if (thisType != otherType) {
-            return null;
-        }
-
-        TypeBearer resultTypeBearer =
-            type.equals(other.getTypeBearer()) ? type : thisType;
-
-        if ((resultTypeBearer == type) && sameName) {
-            // It turns out that the intersection is "this" after all.
-            return this;
-        }
-
-        return (resultLocal == null) ? make(reg, resultTypeBearer) :
-            make(reg, resultTypeBearer, resultLocal);
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that the
-     * register number is replaced by the given one.
-     *
-     * @param newReg {@code >= 0;} the new register number
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpec withReg(int newReg) {
-        if (reg == newReg) {
-            return this;
-        }
-
-        return makeLocalOptional(newReg, type, local);
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the type is replaced by the given one.
-     *
-     * @param newType {@code non-null;} the new type
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpec withType(TypeBearer newType) {
-        return makeLocalOptional(reg, newType, local);
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that the
-     * register number is offset by the given amount.
-     *
-     * @param delta the amount to offset the register number by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpec withOffset(int delta) {
-        if (delta == 0) {
-            return this;
-        }
-
-        return withReg(reg + delta);
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the type bearer is replaced by the actual underlying type
-     * (thereby stripping off non-type information) with any
-     * initialization information stripped away as well.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpec withSimpleType() {
-        TypeBearer orig = type;
-        Type newType;
-
-        if (orig instanceof Type) {
-            newType = (Type) orig;
-        } else {
-            newType = orig.getType();
-        }
-
-        if (newType.isUninitialized()) {
-            newType = newType.getInitializedType();
-        }
-
-        if (newType == orig) {
-            return this;
-        }
-
-        return makeLocalOptional(reg, newType, local);
-    }
-
-    /**
-     * Returns an instance that is identical to this one except that the
-     * local variable is as specified in the parameter.
-     *
-     * @param local {@code null-ok;} the local item or null for none
-     * @return an appropriate instance
-     */
-    public RegisterSpec withLocalItem(LocalItem local) {
-        if ((this.local== local)
-                    || ((this.local != null) && this.local.equals(local))) {
-
-            return this;
-        }
-
-        return makeLocalOptional(reg, type, local);
-    }
-
-
-    /**
-     * Helper for {@link #toString} and {@link #toHuman}.
-     *
-     * @param human whether to be human-oriented
-     * @return {@code non-null;} the string form
-     */
-    private String toString0(boolean human) {
-        StringBuffer sb = new StringBuffer(40);
-
-        sb.append(regString());
-        sb.append(":");
-
-        if (local != null) {
-            sb.append(local.toString());
-        }
-
-        Type justType = type.getType();
-        sb.append(justType);
-
-        if (justType != type) {
-            sb.append("=");
-            if (human && (type instanceof CstString)) {
-                sb.append(((CstString) type).toQuoted());
-            } else if (human && (type instanceof Constant)) {
-                sb.append(type.toHuman());
-            } else {
-                sb.append(type);
-            }
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * Holder of register spec data for the purposes of comparison (so that
-     * {@code RegisterSpec} itself can still keep {@code final}
-     * instance variables.
-     */
-    private static class ForComparison {
-        /** {@code >= 0;} register number */
-        private int reg;
-
-        /** {@code non-null;} type loaded or stored */
-        private TypeBearer type;
-
-        /**
-         * {@code null-ok;} local variable associated with this
-         * register, if any
-         */
-        private LocalItem local;
-
-        /**
-         * Set all the instance variables.
-         *
-         * @param reg {@code >= 0;} the register number
-         * @param type {@code non-null;} the type (or possibly actual
-         * value) which is loaded from or stored to the indicated
-         * register
-         * @param local {@code null-ok;} the associated local variable, if any
-         * @return {@code non-null;} an appropriately-constructed instance
-         */
-        public void set(int reg, TypeBearer type, LocalItem local) {
-            this.reg = reg;
-            this.type = type;
-            this.local = local;
-        }
-
-        /**
-         * Construct a {@code RegisterSpec} of this instance's
-         * contents.
-         *
-         * @return {@code non-null;} an appropriately-constructed instance
-         */
-        public RegisterSpec toRegisterSpec() {
-            return new RegisterSpec(reg, type, local);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public boolean equals(Object other) {
-            if (!(other instanceof RegisterSpec)) {
-                return false;
-            }
-
-            RegisterSpec spec = (RegisterSpec) other;
-            return spec.equals(reg, type, local);
-        }
-
-        /** {@inheritDoc} */
-        @Override
-        public int hashCode() {
-            return hashCodeOf(reg, type, local);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/RegisterSpecList.java b/dx/src/com/android/jack/dx/rop/code/RegisterSpecList.java
index 50649fe..9f270ba 100644
--- a/dx/src/com/android/jack/dx/rop/code/RegisterSpecList.java
+++ b/dx/src/com/android/jack/dx/rop/code/RegisterSpecList.java
@@ -25,385 +25,383 @@
 /**
  * List of {@link RegisterSpec} instances.
  */
-public final class RegisterSpecList
-        extends FixedSizeList implements TypeList {
-    /** {@code non-null;} no-element instance */
-    public static final RegisterSpecList EMPTY = new RegisterSpecList(0);
+public final class RegisterSpecList extends FixedSizeList implements TypeList {
+  /** {@code non-null;} no-element instance */
+  public static final RegisterSpecList EMPTY = new RegisterSpecList(0);
 
-    /**
-     * Makes a single-element instance.
-     *
-     * @param spec {@code non-null;} the element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpecList make(RegisterSpec spec) {
-        RegisterSpecList result = new RegisterSpecList(1);
-        result.set(0, spec);
-        return result;
+  /**
+   * Makes a single-element instance.
+   *
+   * @param spec {@code non-null;} the element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpecList make(RegisterSpec spec) {
+    RegisterSpecList result = new RegisterSpecList(1);
+    result.set(0, spec);
+    return result;
+  }
+
+  /**
+   * Makes a two-element instance.
+   *
+   * @param spec0 {@code non-null;} the first element
+   * @param spec1 {@code non-null;} the second element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpecList make(RegisterSpec spec0, RegisterSpec spec1) {
+    RegisterSpecList result = new RegisterSpecList(2);
+    result.set(0, spec0);
+    result.set(1, spec1);
+    return result;
+  }
+
+  /**
+   * Makes a three-element instance.
+   *
+   * @param spec0 {@code non-null;} the first element
+   * @param spec1 {@code non-null;} the second element
+   * @param spec2 {@code non-null;} the third element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpecList make(RegisterSpec spec0, RegisterSpec spec1, RegisterSpec spec2) {
+    RegisterSpecList result = new RegisterSpecList(3);
+    result.set(0, spec0);
+    result.set(1, spec1);
+    result.set(2, spec2);
+    return result;
+  }
+
+  /**
+   * Makes a four-element instance.
+   *
+   * @param spec0 {@code non-null;} the first element
+   * @param spec1 {@code non-null;} the second element
+   * @param spec2 {@code non-null;} the third element
+   * @param spec3 {@code non-null;} the fourth element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static RegisterSpecList make(RegisterSpec spec0, RegisterSpec spec1, RegisterSpec spec2,
+      RegisterSpec spec3) {
+    RegisterSpecList result = new RegisterSpecList(4);
+    result.set(0, spec0);
+    result.set(1, spec1);
+    result.set(2, spec2);
+    result.set(3, spec3);
+    return result;
+  }
+
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public RegisterSpecList(int size) {
+    super(size);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Type getType(int n) {
+    return get(n).getType().getType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getWordCount() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      result += getType(i).getCategory();
     }
 
-    /**
-     * Makes a two-element instance.
-     *
-     * @param spec0 {@code non-null;} the first element
-     * @param spec1 {@code non-null;} the second element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpecList make(RegisterSpec spec0,
-                                        RegisterSpec spec1) {
-        RegisterSpecList result = new RegisterSpecList(2);
-        result.set(0, spec0);
-        result.set(1, spec1);
-        return result;
+    return result;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public TypeList withAddedType(Type type) {
+    throw new UnsupportedOperationException("unsupported");
+  }
+
+  /**
+   * Gets the indicated element. It is an error to call this with the
+   * index for an element which was never set; if you do that, this
+   * will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return {@code non-null;} the indicated element
+   */
+  public RegisterSpec get(int n) {
+    return (RegisterSpec) get0(n);
+  }
+
+  /**
+   * Returns a RegisterSpec in this list that uses the specified register,
+   * or null if there is none in this list.
+   * @param reg Register to find
+   * @return RegisterSpec that uses argument or null.
+   */
+  public RegisterSpec specForRegister(int reg) {
+    int sz = size();
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec rs;
+
+      rs = get(i);
+
+      if (rs.getReg() == reg) {
+        return rs;
+      }
     }
 
-    /**
-     * Makes a three-element instance.
-     *
-     * @param spec0 {@code non-null;} the first element
-     * @param spec1 {@code non-null;} the second element
-     * @param spec2 {@code non-null;} the third element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpecList make(RegisterSpec spec0, RegisterSpec spec1,
-                                        RegisterSpec spec2) {
-        RegisterSpecList result = new RegisterSpecList(3);
-        result.set(0, spec0);
-        result.set(1, spec1);
-        result.set(2, spec2);
-        return result;
+    return null;
+  }
+
+  /**
+   * Returns the index of a RegisterSpec in this list that uses the specified
+   * register, or -1 if none in this list uses the register.
+   * @param reg Register to find
+   * @return index of RegisterSpec or -1
+   */
+  public int indexOfRegister(int reg) {
+    int sz = size();
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec rs;
+
+      rs = get(i);
+
+      if (rs.getReg() == reg) {
+        return i;
+      }
     }
 
-    /**
-     * Makes a four-element instance.
-     *
-     * @param spec0 {@code non-null;} the first element
-     * @param spec1 {@code non-null;} the second element
-     * @param spec2 {@code non-null;} the third element
-     * @param spec3 {@code non-null;} the fourth element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static RegisterSpecList make(RegisterSpec spec0, RegisterSpec spec1,
-                                        RegisterSpec spec2,
-                                        RegisterSpec spec3) {
-        RegisterSpecList result = new RegisterSpecList(4);
-        result.set(0, spec0);
-        result.set(1, spec1);
-        result.set(2, spec2);
-        result.set(3, spec3);
-        return result;
+    return -1;
+  }
+
+  /**
+   * Sets the element at the given index.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @param spec {@code non-null;} the value to store
+   */
+  public void set(int n, RegisterSpec spec) {
+    set0(n, spec);
+  }
+
+  /**
+   * Gets the minimum required register count implied by this
+   * instance. This is equal to the highest register number referred
+   * to plus the widest width (largest category) of the type used in
+   * that register.
+   *
+   * @return {@code >= 0;} the required registers size
+   */
+  public int getRegistersSize() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec spec = (RegisterSpec) get0(i);
+      if (spec != null) {
+        int min = spec.getNextReg();
+        if (min > result) {
+          result = min;
+        }
+      }
     }
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public RegisterSpecList(int size) {
-        super(size);
+    return result;
+  }
+
+  /**
+   * Returns a new instance, which is the same as this instance,
+   * except that it has an additional element prepended to the original.
+   * Mutability of the result is inherited from the original.
+   *
+   * @param spec {@code non-null;} the new first spec (to prepend)
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList withFirst(RegisterSpec spec) {
+    int sz = size();
+    RegisterSpecList result = new RegisterSpecList(sz + 1);
+
+    for (int i = 0; i < sz; i++) {
+      result.set0(i + 1, get0(i));
     }
 
-    /** {@inheritDoc} */
-    public Type getType(int n) {
-        return get(n).getType().getType();
+    result.set0(0, spec);
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /** {@inheritDoc} */
-    public int getWordCount() {
-        int sz = size();
-        int result = 0;
+    return result;
+  }
 
-        for (int i = 0; i < sz; i++) {
-            result += getType(i).getCategory();
-        }
+  /**
+   * Returns a new instance, which is the same as this instance,
+   * except that its first element is removed. Mutability of the
+   * result is inherited from the original.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList withoutFirst() {
+    int newSize = size() - 1;
 
-        return result;
+    if (newSize == 0) {
+      return EMPTY;
     }
 
-    /** {@inheritDoc} */
-    public TypeList withAddedType(Type type) {
-        throw new UnsupportedOperationException("unsupported");
+    RegisterSpecList result = new RegisterSpecList(newSize);
+
+    for (int i = 0; i < newSize; i++) {
+      result.set0(i, get0(i + 1));
     }
 
-    /**
-     * Gets the indicated element. It is an error to call this with the
-     * index for an element which was never set; if you do that, this
-     * will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return {@code non-null;} the indicated element
-     */
-    public RegisterSpec get(int n) {
-        return (RegisterSpec) get0(n);
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Returns a RegisterSpec in this list that uses the specified register,
-     * or null if there is none in this list.
-     * @param reg Register to find
-     * @return RegisterSpec that uses argument or null.
-     */
-    public RegisterSpec specForRegister(int reg) {
-        int sz = size();
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec rs;
+    return result;
+  }
 
-            rs = get(i);
+  /**
+   * Returns a new instance, which is the same as this instance,
+   * except that its last element is removed. Mutability of the
+   * result is inherited from the original.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList withoutLast() {
+    int newSize = size() - 1;
 
-            if (rs.getReg() == reg) {
-                return rs;
-            }
-        }
-
-        return null;
+    if (newSize == 0) {
+      return EMPTY;
     }
 
-    /**
-     * Returns the index of a RegisterSpec in this list that uses the specified
-     * register, or -1 if none in this list uses the register.
-     * @param reg Register to find
-     * @return index of RegisterSpec or -1
-     */
-    public int indexOfRegister(int reg) {
-        int sz = size();
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec rs;
+    RegisterSpecList result = new RegisterSpecList(newSize);
 
-            rs = get(i);
-
-            if (rs.getReg() == reg) {
-                return i;
-            }
-        }
-
-        return -1;
+    for (int i = 0; i < newSize; i++) {
+      result.set0(i, get0(i));
     }
 
-    /**
-     * Sets the element at the given index.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @param spec {@code non-null;} the value to store
-     */
-    public void set(int n, RegisterSpec spec) {
-        set0(n, spec);
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Gets the minimum required register count implied by this
-     * instance. This is equal to the highest register number referred
-     * to plus the widest width (largest category) of the type used in
-     * that register.
-     *
-     * @return {@code >= 0;} the required registers size
-     */
-    public int getRegistersSize() {
-        int sz = size();
-        int result = 0;
+    return result;
+  }
 
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec spec = (RegisterSpec) get0(i);
-            if (spec != null) {
-                int min = spec.getNextReg();
-                if (min > result) {
-                    result = min;
-                }
-            }
-        }
+  /**
+   * Returns a new instance, which contains a subset of the elements
+   * specified by the given BitSet. Indexes in the BitSet with a zero
+   * are included, while indexes with a one are excluded. Mutability
+   * of the result is inherited from the original.
+   *
+   * @param exclusionSet {@code non-null;} set of registers to exclude
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList subset(BitSet exclusionSet) {
+    int newSize = size() - exclusionSet.cardinality();
 
-        return result;
+    if (newSize == 0) {
+      return EMPTY;
     }
 
-    /**
-     * Returns a new instance, which is the same as this instance,
-     * except that it has an additional element prepended to the original.
-     * Mutability of the result is inherited from the original.
-     *
-     * @param spec {@code non-null;} the new first spec (to prepend)
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList withFirst(RegisterSpec spec) {
-        int sz = size();
-        RegisterSpecList result = new RegisterSpecList(sz + 1);
+    RegisterSpecList result = new RegisterSpecList(newSize);
 
-        for (int i = 0; i < sz; i++) {
-            result.set0(i + 1, get0(i));
-        }
-
-        result.set0(0, spec);
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    int newIndex = 0;
+    for (int oldIndex = 0; oldIndex < size(); oldIndex++) {
+      if (!exclusionSet.get(oldIndex)) {
+        result.set0(newIndex, get0(oldIndex));
+        newIndex++;
+      }
     }
 
-    /**
-     * Returns a new instance, which is the same as this instance,
-     * except that its first element is removed. Mutability of the
-     * result is inherited from the original.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList withoutFirst() {
-        int newSize = size() - 1;
-
-        if (newSize == 0) {
-            return EMPTY;
-        }
-
-        RegisterSpecList result = new RegisterSpecList(newSize);
-
-        for (int i = 0; i < newSize; i++) {
-            result.set0(i, get0(i + 1));
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Returns a new instance, which is the same as this instance,
-     * except that its last element is removed. Mutability of the
-     * result is inherited from the original.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList withoutLast() {
-        int newSize = size() - 1;
+    return result;
+  }
 
-        if (newSize == 0) {
-            return EMPTY;
-        }
+  /**
+   * Returns an instance that is identical to this one, except that
+   * all register numbers are offset by the given amount. Mutability
+   * of the result is inherited from the original.
+   *
+   * @param delta the amount to offset the register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList withOffset(int delta) {
+    int sz = size();
 
-        RegisterSpecList result = new RegisterSpecList(newSize);
-
-        for (int i = 0; i < newSize; i++) {
-            result.set0(i, get0(i));
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    if (sz == 0) {
+      // Don't bother making a new zero-element instance.
+      return this;
     }
 
-    /**
-     * Returns a new instance, which contains a subset of the elements
-     * specified by the given BitSet. Indexes in the BitSet with a zero
-     * are included, while indexes with a one are excluded. Mutability
-     * of the result is inherited from the original.
-     *
-     * @param exclusionSet {@code non-null;} set of registers to exclude
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList subset(BitSet exclusionSet) {
-        int newSize = size() - exclusionSet.cardinality();
+    RegisterSpecList result = new RegisterSpecList(sz);
 
-        if (newSize == 0) {
-            return EMPTY;
-        }
-
-        RegisterSpecList result = new RegisterSpecList(newSize);
-
-        int newIndex = 0;
-        for (int oldIndex = 0; oldIndex < size(); oldIndex++) {
-            if (!exclusionSet.get(oldIndex)) {
-                result.set0(newIndex, get0(oldIndex));
-                newIndex++;
-            }
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec one = (RegisterSpec) get0(i);
+      if (one != null) {
+        result.set0(i, one.withOffset(delta));
+      }
     }
 
-    /**
-     * Returns an instance that is identical to this one, except that
-     * all register numbers are offset by the given amount. Mutability
-     * of the result is inherited from the original.
-     *
-     * @param delta the amount to offset the register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList withOffset(int delta) {
-        int sz = size();
-
-        if (sz == 0) {
-            // Don't bother making a new zero-element instance.
-            return this;
-        }
-
-        RegisterSpecList result = new RegisterSpecList(sz);
-
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec one = (RegisterSpec) get0(i);
-            if (one != null) {
-                result.set0(i, one.withOffset(delta));
-            }
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Returns an instance that is identical to this one, except that
-     * all incompatible register numbers are renumbered sequentially from
-     * the given base, with the first number duplicated if indicated. If
-     * a null BitSet is given, it indicates all registers are compatible.
-     *
-     * @param base the base register number
-     * @param duplicateFirst whether to duplicate the first number
-     * @param compatRegs {@code null-ok;} either a {@code non-null} set of
-     * compatible registers, or {@code null} to indicate all registers are
-     * compatible
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecList withExpandedRegisters(int base,
-                                                  boolean duplicateFirst,
-                                                  BitSet compatRegs) {
-        int sz = size();
+    return result;
+  }
 
-        if (sz == 0) {
-            // Don't bother making a new zero-element instance.
-            return this;
-        }
+  /**
+   * Returns an instance that is identical to this one, except that
+   * all incompatible register numbers are renumbered sequentially from
+   * the given base, with the first number duplicated if indicated. If
+   * a null BitSet is given, it indicates all registers are compatible.
+   *
+   * @param base the base register number
+   * @param duplicateFirst whether to duplicate the first number
+   * @param compatRegs {@code null-ok;} either a {@code non-null} set of
+   * compatible registers, or {@code null} to indicate all registers are
+   * compatible
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecList withExpandedRegisters(int base, boolean duplicateFirst,
+      BitSet compatRegs) {
+    int sz = size();
 
-        RegisterSpecList result = new RegisterSpecList(sz);
-
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec one = (RegisterSpec) get0(i);
-            boolean replace = (compatRegs == null) ? true : !compatRegs.get(i);
-
-            if (replace) {
-                result.set0(i, one.withReg(base));
-                if (!duplicateFirst) {
-                    base += one.getCategory();
-                }
-            } else {
-                result.set0(i, one);
-            }
-
-            if (duplicateFirst) {
-                duplicateFirst = false;
-            }
-        }
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
+    if (sz == 0) {
+      // Don't bother making a new zero-element instance.
+      return this;
     }
+
+    RegisterSpecList result = new RegisterSpecList(sz);
+
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec one = (RegisterSpec) get0(i);
+      boolean replace = (compatRegs == null) ? true : !compatRegs.get(i);
+
+      if (replace) {
+        result.set0(i, one.withReg(base));
+        if (!duplicateFirst) {
+          base += one.getCategory();
+        }
+      } else {
+        result.set0(i, one);
+      }
+
+      if (duplicateFirst) {
+        duplicateFirst = false;
+      }
+    }
+
+    if (isImmutable()) {
+      result.setImmutable();
+    }
+
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/RegisterSpecSet.java b/dx/src/com/android/jack/dx/rop/code/RegisterSpecSet.java
index 4116155..7538027 100644
--- a/dx/src/com/android/jack/dx/rop/code/RegisterSpecSet.java
+++ b/dx/src/com/android/jack/dx/rop/code/RegisterSpecSet.java
@@ -22,375 +22,373 @@
  * Set of {@link RegisterSpec} instances, where a given register number
  * may appear only once in the set.
  */
-public final class RegisterSpecSet
-        extends MutabilityControl {
-    /** {@code non-null;} no-element instance */
-    public static final RegisterSpecSet EMPTY = new RegisterSpecSet(0);
+public final class RegisterSpecSet extends MutabilityControl {
+  /** {@code non-null;} no-element instance */
+  public static final RegisterSpecSet EMPTY = new RegisterSpecSet(0);
 
-    /**
-     * {@code non-null;} array of register specs, where each element is
-     * {@code null} or is an instance whose {@code reg}
-     * matches the array index
-     */
-    private final RegisterSpec[] specs;
+  /**
+   * {@code non-null;} array of register specs, where each element is
+   * {@code null} or is an instance whose {@code reg}
+   * matches the array index
+   */
+  private final RegisterSpec[] specs;
 
-    /** {@code >= -1;} size of the set or {@code -1} if not yet calculated */
-    private int size;
+  /** {@code >= -1;} size of the set or {@code -1} if not yet calculated */
+  private int size;
 
-    /**
-     * Constructs an instance. The instance is initially empty.
-     *
-     * @param maxSize {@code >= 0;} the maximum register number (exclusive) that
-     * may be represented in this instance
-     */
-    public RegisterSpecSet(int maxSize) {
-        super(maxSize != 0);
+  /**
+   * Constructs an instance. The instance is initially empty.
+   *
+   * @param maxSize {@code >= 0;} the maximum register number (exclusive) that
+   * may be represented in this instance
+   */
+  public RegisterSpecSet(int maxSize) {
+    super(maxSize != 0);
 
-        this.specs = new RegisterSpec[maxSize];
-        this.size = 0;
+    this.specs = new RegisterSpec[maxSize];
+    this.size = 0;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof RegisterSpecSet)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof RegisterSpecSet)) {
-            return false;
-        }
+    RegisterSpecSet otherSet = (RegisterSpecSet) other;
+    RegisterSpec[] otherSpecs = otherSet.specs;
+    int len = specs.length;
 
-        RegisterSpecSet otherSet = (RegisterSpecSet) other;
-        RegisterSpec[] otherSpecs = otherSet.specs;
-        int len = specs.length;
-
-        if ((len != otherSpecs.length) || (size() != otherSet.size())) {
-            return false;
-        }
-
-        for (int i = 0; i < len; i++) {
-            RegisterSpec s1 = specs[i];
-            RegisterSpec s2 = otherSpecs[i];
-
-            if (s1 == s2) {
-                continue;
-            }
-
-            if ((s1 == null) || !s1.equals(s2)) {
-                return false;
-            }
-        }
-
-        return true;
+    if ((len != otherSpecs.length) || (size() != otherSet.size())) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        int len = specs.length;
-        int hash = 0;
+    for (int i = 0; i < len; i++) {
+      RegisterSpec s1 = specs[i];
+      RegisterSpec s2 = otherSpecs[i];
 
-        for (int i = 0; i < len; i++) {
-            RegisterSpec spec = specs[i];
-            int oneHash = (spec == null) ? 0 : spec.hashCode();
-            hash = (hash * 31) + oneHash;
-        }
+      if (s1 == s2) {
+        continue;
+      }
 
-        return hash;
+      if ((s1 == null) || !s1.equals(s2)) {
+        return false;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int len = specs.length;
-        StringBuffer sb = new StringBuffer(len * 25);
+    return true;
+  }
 
-        sb.append('{');
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    int len = specs.length;
+    int hash = 0;
 
-        boolean any = false;
-        for (int i = 0; i < len; i++) {
-            RegisterSpec spec = specs[i];
-            if (spec != null) {
-                if (any) {
-                    sb.append(", ");
-                } else {
-                    any = true;
-                }
-                sb.append(spec);
-            }
-        }
-
-        sb.append('}');
-        return sb.toString();
+    for (int i = 0; i < len; i++) {
+      RegisterSpec spec = specs[i];
+      int oneHash = (spec == null) ? 0 : spec.hashCode();
+      hash = (hash * 31) + oneHash;
     }
 
-    /**
-     * Gets the maximum number of registers that may be in this instance, which
-     * is also the maximum-plus-one of register numbers that may be
-     * represented.
-     *
-     * @return {@code >= 0;} the maximum size
-     */
-    public int getMaxSize() {
-        return specs.length;
+    return hash;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int len = specs.length;
+    StringBuffer sb = new StringBuffer(len * 25);
+
+    sb.append('{');
+
+    boolean any = false;
+    for (int i = 0; i < len; i++) {
+      RegisterSpec spec = specs[i];
+      if (spec != null) {
+        if (any) {
+          sb.append(", ");
+        } else {
+          any = true;
+        }
+        sb.append(spec);
+      }
     }
 
-    /**
-     * Gets the current size of this instance.
-     *
-     * @return {@code >= 0;} the size
-     */
-    public int size() {
-        int result = size;
+    sb.append('}');
+    return sb.toString();
+  }
 
-        if (result < 0) {
-            int len = specs.length;
+  /**
+   * Gets the maximum number of registers that may be in this instance, which
+   * is also the maximum-plus-one of register numbers that may be
+   * represented.
+   *
+   * @return {@code >= 0;} the maximum size
+   */
+  public int getMaxSize() {
+    return specs.length;
+  }
 
-            result = 0;
-            for (int i = 0; i < len; i++) {
-                if (specs[i] != null) {
-                    result++;
-                }
-            }
+  /**
+   * Gets the current size of this instance.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int size() {
+    int result = size;
 
-            size = result;
+    if (result < 0) {
+      int len = specs.length;
+
+      result = 0;
+      for (int i = 0; i < len; i++) {
+        if (specs[i] != null) {
+          result++;
         }
+      }
 
-        return result;
+      size = result;
     }
 
-    /**
-     * Gets the element with the given register number, if any.
-     *
-     * @param reg {@code >= 0;} the desired register number
-     * @return {@code null-ok;} the element with the given register number or
-     * {@code null} if there is none
-     */
-    public RegisterSpec get(int reg) {
-        try {
-            return specs[reg];
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus reg");
-        }
+    return result;
+  }
+
+  /**
+   * Gets the element with the given register number, if any.
+   *
+   * @param reg {@code >= 0;} the desired register number
+   * @return {@code null-ok;} the element with the given register number or
+   * {@code null} if there is none
+   */
+  public RegisterSpec get(int reg) {
+    try {
+      return specs[reg];
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus reg");
+    }
+  }
+
+  /**
+   * Gets the element with the same register number as the given
+   * spec, if any. This is just a convenient shorthand for
+   * {@code get(spec.getReg())}.
+   *
+   * @param spec {@code non-null;} spec with the desired register number
+   * @return {@code null-ok;} the element with the matching register number or
+   * {@code null} if there is none
+   */
+  public RegisterSpec get(RegisterSpec spec) {
+    return get(spec.getReg());
+  }
+
+  /**
+   * Returns the spec in this set that's currently associated with a
+   * given local (type, name, and signature), or {@code null} if there is
+   * none. This ignores the register number of the given spec but
+   * matches on everything else.
+   *
+   * @param spec {@code non-null;} local to look for
+   * @return {@code null-ok;} first register found that matches, if any
+   */
+  public RegisterSpec findMatchingLocal(RegisterSpec spec) {
+    int length = specs.length;
+
+    for (int reg = 0; reg < length; reg++) {
+      RegisterSpec s = specs[reg];
+
+      if (s == null) {
+        continue;
+      }
+
+      if (spec.matchesVariable(s)) {
+        return s;
+      }
     }
 
-    /**
-     * Gets the element with the same register number as the given
-     * spec, if any. This is just a convenient shorthand for
-     * {@code get(spec.getReg())}.
-     *
-     * @param spec {@code non-null;} spec with the desired register number
-     * @return {@code null-ok;} the element with the matching register number or
-     * {@code null} if there is none
-     */
-    public RegisterSpec get(RegisterSpec spec) {
-        return get(spec.getReg());
+    return null;
+  }
+
+  /**
+   * Returns the spec in this set that's currently associated with a given
+   * local (name and signature), or {@code null} if there is none.
+   *
+   * @param local {@code non-null;} local item to search for
+   * @return {@code null-ok;} first register found with matching name and signature
+   */
+  public RegisterSpec localItemToSpec(LocalItem local) {
+    int length = specs.length;
+
+    for (int reg = 0; reg < length; reg++) {
+      RegisterSpec spec = specs[reg];
+
+      if ((spec != null) && local.equals(spec.getLocalItem())) {
+        return spec;
+      }
     }
 
-    /**
-     * Returns the spec in this set that's currently associated with a
-     * given local (type, name, and signature), or {@code null} if there is
-     * none. This ignores the register number of the given spec but
-     * matches on everything else.
-     *
-     * @param spec {@code non-null;} local to look for
-     * @return {@code null-ok;} first register found that matches, if any
-     */
-    public RegisterSpec findMatchingLocal(RegisterSpec spec) {
-        int length = specs.length;
+    return null;
+  }
 
-        for (int reg = 0; reg < length; reg++) {
-            RegisterSpec s = specs[reg];
+  /**
+   * Removes a spec from the set. Only the register number
+   * of the parameter is significant.
+   *
+   * @param toRemove {@code non-null;} register to remove.
+   */
+  public void remove(RegisterSpec toRemove) {
+    try {
+      specs[toRemove.getReg()] = null;
+      size = -1;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus reg");
+    }
+  }
 
-            if (s == null) {
-                continue;
-            }
+  /**
+   * Puts the given spec into the set. If there is already an element in
+   * the set with the same register number, it is replaced. Additionally,
+   * if the previous element is for a category-2 register, then that
+   * previous element is nullified. Finally, if the given spec is for
+   * a category-2 register, then the immediately subsequent element
+   * is nullified.
+   *
+   * @param spec {@code non-null;} the register spec to put in the instance
+   */
+  public void put(RegisterSpec spec) {
+    throwIfImmutable();
 
-            if (spec.matchesVariable(s)) {
-                return s;
-            }
-        }
-
-        return null;
+    if (spec == null) {
+      throw new NullPointerException("spec == null");
     }
 
-    /**
-     * Returns the spec in this set that's currently associated with a given
-     * local (name and signature), or {@code null} if there is none.
-     *
-     * @param local {@code non-null;} local item to search for
-     * @return {@code null-ok;} first register found with matching name and signature
-     */
-    public RegisterSpec localItemToSpec(LocalItem local) {
-        int length = specs.length;
+    size = -1;
 
-        for (int reg = 0; reg < length; reg++) {
-            RegisterSpec spec = specs[reg];
+    try {
+      int reg = spec.getReg();
+      specs[reg] = spec;
 
-            if ((spec != null) && local.equals(spec.getLocalItem())) {
-                return spec;
-            }
+      if (reg > 0) {
+        int prevReg = reg - 1;
+        RegisterSpec prevSpec = specs[prevReg];
+        if ((prevSpec != null) && (prevSpec.getCategory() == 2)) {
+          specs[prevReg] = null;
         }
+      }
 
-        return null;
+      if (spec.getCategory() == 2) {
+        specs[reg + 1] = null;
+      }
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("spec.getReg() out of range");
+    }
+  }
+
+  /**
+   * Put the entire contents of the given set into this one.
+   *
+   * @param set {@code non-null;} the set to put into this instance
+   */
+  public void putAll(RegisterSpecSet set) {
+    int max = set.getMaxSize();
+
+    for (int i = 0; i < max; i++) {
+      RegisterSpec spec = set.get(i);
+      if (spec != null) {
+        put(spec);
+      }
+    }
+  }
+
+  /**
+   * Intersects this instance with the given one, modifying this
+   * instance. The intersection consists of the pairwise
+   * {@link RegisterSpec#intersect} of corresponding elements from
+   * this instance and the given one where both are non-null.
+   *
+   * @param other {@code non-null;} set to intersect with
+   * @param localPrimary whether local variables are primary to
+   * the intersection; if {@code true}, then the only non-null
+   * result elements occur when registers being intersected have
+   * equal names (or both have {@code null} names)
+   */
+  public void intersect(RegisterSpecSet other, boolean localPrimary) {
+    throwIfImmutable();
+
+    RegisterSpec[] otherSpecs = other.specs;
+    int thisLen = specs.length;
+    int len = Math.min(thisLen, otherSpecs.length);
+
+    size = -1;
+
+    for (int i = 0; i < len; i++) {
+      RegisterSpec spec = specs[i];
+
+      if (spec == null) {
+        continue;
+      }
+
+      RegisterSpec intersection = spec.intersect(otherSpecs[i], localPrimary);
+      if (intersection != spec) {
+        specs[i] = intersection;
+      }
     }
 
-    /**
-     * Removes a spec from the set. Only the register number
-     * of the parameter is significant.
-     *
-     * @param toRemove {@code non-null;} register to remove.
-     */
-    public void remove(RegisterSpec toRemove) {
-        try {
-            specs[toRemove.getReg()] = null;
-            size = -1;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus reg");
-        }
+    for (int i = len; i < thisLen; i++) {
+      specs[i] = null;
+    }
+  }
+
+  /**
+   * Returns an instance that is identical to this one, except that
+   * all register numbers are offset by the given amount. Mutability
+   * of the result is inherited from the original.
+   *
+   * @param delta the amount to offset the register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RegisterSpecSet withOffset(int delta) {
+    int len = specs.length;
+    RegisterSpecSet result = new RegisterSpecSet(len + delta);
+
+    for (int i = 0; i < len; i++) {
+      RegisterSpec spec = specs[i];
+      if (spec != null) {
+        result.put(spec.withOffset(delta));
+      }
     }
 
-    /**
-     * Puts the given spec into the set. If there is already an element in
-     * the set with the same register number, it is replaced. Additionally,
-     * if the previous element is for a category-2 register, then that
-     * previous element is nullified. Finally, if the given spec is for
-     * a category-2 register, then the immediately subsequent element
-     * is nullified.
-     *
-     * @param spec {@code non-null;} the register spec to put in the instance
-     */
-    public void put(RegisterSpec spec) {
-        throwIfImmutable();
+    result.size = size;
 
-        if (spec == null) {
-            throw new NullPointerException("spec == null");
-        }
-
-        size = -1;
-
-        try {
-            int reg = spec.getReg();
-            specs[reg] = spec;
-
-            if (reg > 0) {
-                int prevReg = reg - 1;
-                RegisterSpec prevSpec = specs[prevReg];
-                if ((prevSpec != null) && (prevSpec.getCategory() == 2)) {
-                    specs[prevReg] = null;
-                }
-            }
-
-            if (spec.getCategory() == 2) {
-                specs[reg + 1] = null;
-            }
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("spec.getReg() out of range");
-        }
+    if (isImmutable()) {
+      result.setImmutable();
     }
 
-    /**
-     * Put the entire contents of the given set into this one.
-     *
-     * @param set {@code non-null;} the set to put into this instance
-     */
-    public void putAll(RegisterSpecSet set) {
-        int max = set.getMaxSize();
+    return result;
+  }
 
-        for (int i = 0; i < max; i++) {
-            RegisterSpec spec = set.get(i);
-            if (spec != null) {
-                put(spec);
-            }
-        }
+  /**
+   * Makes and return a mutable copy of this instance.
+   *
+   * @return {@code non-null;} the mutable copy
+   */
+  public RegisterSpecSet mutableCopy() {
+    int len = specs.length;
+    RegisterSpecSet copy = new RegisterSpecSet(len);
+
+    for (int i = 0; i < len; i++) {
+      RegisterSpec spec = specs[i];
+      if (spec != null) {
+        copy.put(spec);
+      }
     }
 
-    /**
-     * Intersects this instance with the given one, modifying this
-     * instance. The intersection consists of the pairwise
-     * {@link RegisterSpec#intersect} of corresponding elements from
-     * this instance and the given one where both are non-null.
-     *
-     * @param other {@code non-null;} set to intersect with
-     * @param localPrimary whether local variables are primary to
-     * the intersection; if {@code true}, then the only non-null
-     * result elements occur when registers being intersected have
-     * equal names (or both have {@code null} names)
-     */
-    public void intersect(RegisterSpecSet other, boolean localPrimary) {
-        throwIfImmutable();
+    copy.size = size;
 
-        RegisterSpec[] otherSpecs = other.specs;
-        int thisLen = specs.length;
-        int len = Math.min(thisLen, otherSpecs.length);
-
-        size = -1;
-
-        for (int i = 0; i < len; i++) {
-            RegisterSpec spec = specs[i];
-
-            if (spec == null) {
-                continue;
-            }
-
-            RegisterSpec intersection =
-                spec.intersect(otherSpecs[i], localPrimary);
-            if (intersection != spec) {
-                specs[i] = intersection;
-            }
-        }
-
-        for (int i = len; i < thisLen; i++) {
-            specs[i] = null;
-        }
-    }
-
-    /**
-     * Returns an instance that is identical to this one, except that
-     * all register numbers are offset by the given amount. Mutability
-     * of the result is inherited from the original.
-     *
-     * @param delta the amount to offset the register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RegisterSpecSet withOffset(int delta) {
-        int len = specs.length;
-        RegisterSpecSet result = new RegisterSpecSet(len + delta);
-
-        for (int i = 0; i < len; i++) {
-            RegisterSpec spec = specs[i];
-            if (spec != null) {
-                result.put(spec.withOffset(delta));
-            }
-        }
-
-        result.size = size;
-
-        if (isImmutable()) {
-            result.setImmutable();
-        }
-
-        return result;
-    }
-
-    /**
-     * Makes and return a mutable copy of this instance.
-     *
-     * @return {@code non-null;} the mutable copy
-     */
-    public RegisterSpecSet mutableCopy() {
-        int len = specs.length;
-        RegisterSpecSet copy = new RegisterSpecSet(len);
-
-        for (int i = 0; i < len; i++) {
-            RegisterSpec spec = specs[i];
-            if (spec != null) {
-                copy.put(spec);
-            }
-        }
-
-        copy.size = size;
-
-        return copy;
-    }
+    return copy;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/Rop.java b/dx/src/com/android/jack/dx/rop/code/Rop.java
index 161a0ee..3ae002b 100644
--- a/dx/src/com/android/jack/dx/rop/code/Rop.java
+++ b/dx/src/com/android/jack/dx/rop/code/Rop.java
@@ -25,383 +25,392 @@
  * Class that describes all the immutable parts of register-based operations.
  */
 public final class Rop {
-    /** minimum {@code BRANCH_*} value */
-    public static final int BRANCH_MIN = 1;
+  /** minimum {@code BRANCH_*} value */
+  public static final int BRANCH_MIN = 1;
 
-    /** indicates a non-branching op */
-    public static final int BRANCH_NONE = 1;
+  /** indicates a non-branching op */
+  public static final int BRANCH_NONE = 1;
 
-    /** indicates a function/method return */
-    public static final int BRANCH_RETURN = 2;
+  /** indicates a function/method return */
+  public static final int BRANCH_RETURN = 2;
 
-    /** indicates an unconditional goto */
-    public static final int BRANCH_GOTO = 3;
+  /** indicates an unconditional goto */
+  public static final int BRANCH_GOTO = 3;
 
-    /** indicates a two-way branch */
-    public static final int BRANCH_IF = 4;
+  /** indicates a two-way branch */
+  public static final int BRANCH_IF = 4;
 
-    /** indicates a switch-style branch */
-    public static final int BRANCH_SWITCH = 5;
+  /** indicates a switch-style branch */
+  public static final int BRANCH_SWITCH = 5;
 
-    /** indicates a throw-style branch (both always-throws and may-throw) */
-    public static final int BRANCH_THROW = 6;
+  /** indicates a throw-style branch (both always-throws and may-throw) */
+  public static final int BRANCH_THROW = 6;
 
-    /** maximum {@code BRANCH_*} value */
-    public static final int BRANCH_MAX = 6;
+  /** maximum {@code BRANCH_*} value */
+  public static final int BRANCH_MAX = 6;
 
-    /** the opcode; one of the constants in {@link RegOps} */
-    private final int opcode;
+  /** the opcode; one of the constants in {@link RegOps} */
+  private final int opcode;
 
-    /**
-     * {@code non-null;} result type of this operation; {@link Type#VOID} for
-     * no-result operations
-     */
-    private final Type result;
+  /**
+   * {@code non-null;} result type of this operation; {@link Type#VOID} for
+   * no-result operations
+   */
+  private final Type result;
 
-    /** {@code non-null;} types of all the sources of this operation */
-    private final TypeList sources;
+  /** {@code non-null;} types of all the sources of this operation */
+  private final TypeList sources;
 
-    /** {@code non-null;} list of possible types thrown by this operation */
-    private final TypeList exceptions;
+  /** {@code non-null;} list of possible types thrown by this operation */
+  private final TypeList exceptions;
 
-    /**
-     * the branchingness of this op; one of the {@code BRANCH_*}
-     * constants in this class
-     */
-    private final int branchingness;
+  /**
+   * the branchingness of this op; one of the {@code BRANCH_*}
+   * constants in this class
+   */
+  private final int branchingness;
 
-    /** whether this is a function/method call op or similar */
-    private final boolean isCallLike;
+  /** whether this is a function/method call op or similar */
+  private final boolean isCallLike;
 
-    /** {@code null-ok;} nickname, if specified (used for debugging) */
-    private final String nickname;
+  /** {@code null-ok;} nickname, if specified (used for debugging) */
+  private final String nickname;
 
-    /**
-     * Constructs an instance. This method is private. Use one of the
-     * public constructors.
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param result {@code non-null;} result type of this operation; {@link
-     * Type#VOID} for no-result operations
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param exceptions {@code non-null;} list of possible types thrown by this
-     * operation
-     * @param branchingness the branchingness of this op; one of the
-     * {@code BRANCH_*} constants
-     * @param isCallLike whether the op is a function/method call or similar
-     * @param nickname {@code null-ok;} optional nickname (used for debugging)
-     */
-    public Rop(int opcode, Type result, TypeList sources,
-               TypeList exceptions, int branchingness, boolean isCallLike,
-               String nickname) {
-        if (result == null) {
-            throw new NullPointerException("result == null");
-        }
-
-        if (sources == null) {
-            throw new NullPointerException("sources == null");
-        }
-
-        if (exceptions == null) {
-            throw new NullPointerException("exceptions == null");
-        }
-
-        if ((branchingness < BRANCH_MIN) || (branchingness > BRANCH_MAX)) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
-
-        if ((exceptions.size() != 0) && (branchingness != BRANCH_THROW)) {
-            throw new IllegalArgumentException("exceptions / branchingness " +
-                                               "mismatch");
-        }
-
-        this.opcode = opcode;
-        this.result = result;
-        this.sources = sources;
-        this.exceptions = exceptions;
-        this.branchingness = branchingness;
-        this.isCallLike = isCallLike;
-        this.nickname = nickname;
+  /**
+   * Constructs an instance. This method is private. Use one of the
+   * public constructors.
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param result {@code non-null;} result type of this operation; {@link
+   * Type#VOID} for no-result operations
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param exceptions {@code non-null;} list of possible types thrown by this
+   * operation
+   * @param branchingness the branchingness of this op; one of the
+   * {@code BRANCH_*} constants
+   * @param isCallLike whether the op is a function/method call or similar
+   * @param nickname {@code null-ok;} optional nickname (used for debugging)
+   */
+  public Rop(int opcode,
+      Type result,
+      TypeList sources,
+      TypeList exceptions,
+      int branchingness,
+      boolean isCallLike,
+      String nickname) {
+    if (result == null) {
+      throw new NullPointerException("result == null");
     }
 
-    /**
-     * Constructs an instance. The constructed instance is never a
-     * call-like op (see {@link #isCallLike}).
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param result {@code non-null;} result type of this operation; {@link
-     * Type#VOID} for no-result operations
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param exceptions {@code non-null;} list of possible types thrown by this
-     * operation
-     * @param branchingness the branchingness of this op; one of the
-     * {@code BRANCH_*} constants
-     * @param nickname {@code null-ok;} optional nickname (used for debugging)
-     */
-    public Rop(int opcode, Type result, TypeList sources,
-               TypeList exceptions, int branchingness, String nickname) {
-        this(opcode, result, sources, exceptions, branchingness, false,
-             nickname);
+    if (sources == null) {
+      throw new NullPointerException("sources == null");
     }
 
-    /**
-     * Constructs a no-exception instance. The constructed instance is never a
-     * call-like op (see {@link #isCallLike}).
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param result {@code non-null;} result type of this operation; {@link
-     * Type#VOID} for no-result operations
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param branchingness the branchingness of this op; one of the
-     * {@code BRANCH_*} constants
-     * @param nickname {@code null-ok;} optional nickname (used for debugging)
-     */
-    public Rop(int opcode, Type result, TypeList sources, int branchingness,
-               String nickname) {
-        this(opcode, result, sources, StdTypeList.EMPTY, branchingness, false,
-             nickname);
+    if (exceptions == null) {
+      throw new NullPointerException("exceptions == null");
     }
 
-    /**
-     * Constructs a non-branching no-exception instance. The
-     * {@code branchingness} is always {@code BRANCH_NONE},
-     * and it is never a call-like op (see {@link #isCallLike}).
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param result {@code non-null;} result type of this operation; {@link
-     * Type#VOID} for no-result operations
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param nickname {@code null-ok;} optional nickname (used for debugging)
-     */
-    public Rop(int opcode, Type result, TypeList sources, String nickname) {
-        this(opcode, result, sources, StdTypeList.EMPTY, Rop.BRANCH_NONE,
-             false, nickname);
+    if ((branchingness < BRANCH_MIN) || (branchingness > BRANCH_MAX)) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
 
-    /**
-     * Constructs a non-empty exceptions instance. Its
-     * {@code branchingness} is always {@code BRANCH_THROW},
-     * but it is never a call-like op (see {@link #isCallLike}).
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param result {@code non-null;} result type of this operation; {@link
-     * Type#VOID} for no-result operations
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param exceptions {@code non-null;} list of possible types thrown by this
-     * operation
-     * @param nickname {@code null-ok;} optional nickname (used for debugging)
-     */
-    public Rop(int opcode, Type result, TypeList sources, TypeList exceptions,
-               String nickname) {
-        this(opcode, result, sources, exceptions, Rop.BRANCH_THROW, false,
-             nickname);
+    if ((exceptions.size() != 0) && (branchingness != BRANCH_THROW)) {
+      throw new IllegalArgumentException("exceptions / branchingness " + "mismatch");
     }
 
-    /**
-     * Constructs a non-nicknamed instance with non-empty exceptions, which
-     * is always a call-like op (see {@link #isCallLike}). Its
-     * {@code branchingness} is always {@code BRANCH_THROW}.
-     *
-     * @param opcode the opcode; one of the constants in {@link RegOps}
-     * @param sources {@code non-null;} types of all the sources of this operation
-     * @param exceptions {@code non-null;} list of possible types thrown by this
-     * operation
-     */
-    public Rop(int opcode, TypeList sources, TypeList exceptions) {
-        this(opcode, Type.VOID, sources, exceptions, Rop.BRANCH_THROW, true,
-             null);
+    this.opcode = opcode;
+    this.result = result;
+    this.sources = sources;
+    this.exceptions = exceptions;
+    this.branchingness = branchingness;
+    this.isCallLike = isCallLike;
+    this.nickname = nickname;
+  }
+
+  /**
+   * Constructs an instance. The constructed instance is never a
+   * call-like op (see {@link #isCallLike}).
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param result {@code non-null;} result type of this operation; {@link
+   * Type#VOID} for no-result operations
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param exceptions {@code non-null;} list of possible types thrown by this
+   * operation
+   * @param branchingness the branchingness of this op; one of the
+   * {@code BRANCH_*} constants
+   * @param nickname {@code null-ok;} optional nickname (used for debugging)
+   */
+  public Rop(int opcode,
+      Type result,
+      TypeList sources,
+      TypeList exceptions,
+      int branchingness,
+      String nickname) {
+    this(opcode, result, sources, exceptions, branchingness, false, nickname);
+  }
+
+  /**
+   * Constructs a no-exception instance. The constructed instance is never a
+   * call-like op (see {@link #isCallLike}).
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param result {@code non-null;} result type of this operation; {@link
+   * Type#VOID} for no-result operations
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param branchingness the branchingness of this op; one of the
+   * {@code BRANCH_*} constants
+   * @param nickname {@code null-ok;} optional nickname (used for debugging)
+   */
+  public Rop(int opcode, Type result, TypeList sources, int branchingness, String nickname) {
+    this(opcode, result, sources, StdTypeList.EMPTY, branchingness, false, nickname);
+  }
+
+  /**
+   * Constructs a non-branching no-exception instance. The
+   * {@code branchingness} is always {@code BRANCH_NONE},
+   * and it is never a call-like op (see {@link #isCallLike}).
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param result {@code non-null;} result type of this operation; {@link
+   * Type#VOID} for no-result operations
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param nickname {@code null-ok;} optional nickname (used for debugging)
+   */
+  public Rop(int opcode, Type result, TypeList sources, String nickname) {
+    this(opcode, result, sources, StdTypeList.EMPTY, Rop.BRANCH_NONE, false, nickname);
+  }
+
+  /**
+   * Constructs a non-empty exceptions instance. Its
+   * {@code branchingness} is always {@code BRANCH_THROW},
+   * but it is never a call-like op (see {@link #isCallLike}).
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param result {@code non-null;} result type of this operation; {@link
+   * Type#VOID} for no-result operations
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param exceptions {@code non-null;} list of possible types thrown by this
+   * operation
+   * @param nickname {@code null-ok;} optional nickname (used for debugging)
+   */
+  public Rop(int opcode, Type result, TypeList sources, TypeList exceptions, String nickname) {
+    this(opcode, result, sources, exceptions, Rop.BRANCH_THROW, false, nickname);
+  }
+
+  /**
+   * Constructs a non-nicknamed instance with non-empty exceptions, which
+   * is always a call-like op (see {@link #isCallLike}). Its
+   * {@code branchingness} is always {@code BRANCH_THROW}.
+   *
+   * @param opcode the opcode; one of the constants in {@link RegOps}
+   * @param sources {@code non-null;} types of all the sources of this operation
+   * @param exceptions {@code non-null;} list of possible types thrown by this
+   * operation
+   */
+  public Rop(int opcode, TypeList sources, TypeList exceptions) {
+    this(opcode, Type.VOID, sources, exceptions, Rop.BRANCH_THROW, true, null);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (this == other) {
+      // Easy out.
+      return true;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (this == other) {
-            // Easy out.
-            return true;
-        }
-
-        if (!(other instanceof Rop)) {
-            return false;
-        }
-
-        Rop rop = (Rop) other;
-
-        return (opcode == rop.opcode) &&
-            (branchingness == rop.branchingness) &&
-            (result == rop.result) &&
-            sources.equals(rop.sources) &&
-            exceptions.equals(rop.exceptions);
+    if (!(other instanceof Rop)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        int h = (opcode * 31) + branchingness;
-        h = (h * 31) + result.hashCode();
-        h = (h * 31) + sources.hashCode();
-        h = (h * 31) + exceptions.hashCode();
+    Rop rop = (Rop) other;
 
-        return h;
+    return (opcode == rop.opcode) && (branchingness == rop.branchingness) && (result == rop.result)
+        && sources.equals(rop.sources) && exceptions.equals(rop.exceptions);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    int h = (opcode * 31) + branchingness;
+    h = (h * 31) + result.hashCode();
+    h = (h * 31) + sources.hashCode();
+    h = (h * 31) + exceptions.hashCode();
+
+    return h;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(40);
+
+    sb.append("Rop{");
+
+    sb.append(RegOps.opName(opcode));
+
+    if (result != Type.VOID) {
+      sb.append(" ");
+      sb.append(result);
+    } else {
+      sb.append(" .");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(40);
+    sb.append(" <-");
 
-        sb.append("Rop{");
+    int sz = sources.size();
+    if (sz == 0) {
+      sb.append(" .");
+    } else {
+      for (int i = 0; i < sz; i++) {
+        sb.append(' ');
+        sb.append(sources.getType(i));
+      }
+    }
 
-        sb.append(RegOps.opName(opcode));
+    if (isCallLike) {
+      sb.append(" call");
+    }
 
-        if (result != Type.VOID) {
-            sb.append(" ");
-            sb.append(result);
+    sz = exceptions.size();
+    if (sz != 0) {
+      sb.append(" throws");
+      for (int i = 0; i < sz; i++) {
+        sb.append(' ');
+        Type one = exceptions.getType(i);
+        if (one == Type.THROWABLE) {
+          sb.append("<any>");
         } else {
-            sb.append(" .");
+          sb.append(exceptions.getType(i));
         }
-
-        sb.append(" <-");
-
-        int sz = sources.size();
-        if (sz == 0) {
-            sb.append(" .");
-        } else {
-            for (int i = 0; i < sz; i++) {
-                sb.append(' ');
-                sb.append(sources.getType(i));
-            }
-        }
-
-        if (isCallLike) {
-            sb.append(" call");
-        }
-
-        sz = exceptions.size();
-        if (sz != 0) {
-            sb.append(" throws");
-            for (int i = 0; i < sz; i++) {
-                sb.append(' ');
-                Type one = exceptions.getType(i);
-                if (one == Type.THROWABLE) {
-                    sb.append("<any>");
-                } else {
-                    sb.append(exceptions.getType(i));
-                }
-            }
-        } else {
-            switch (branchingness) {
-                case BRANCH_NONE:   sb.append(" flows"); break;
-                case BRANCH_RETURN: sb.append(" returns"); break;
-                case BRANCH_GOTO:   sb.append(" gotos"); break;
-                case BRANCH_IF:     sb.append(" ifs"); break;
-                case BRANCH_SWITCH: sb.append(" switches"); break;
-                default: sb.append(" " + Hex.u1(branchingness)); break;
-            }
-        }
-
-        sb.append('}');
-
-        return sb.toString();
+      }
+    } else {
+      switch (branchingness) {
+        case BRANCH_NONE:
+          sb.append(" flows");
+          break;
+        case BRANCH_RETURN:
+          sb.append(" returns");
+          break;
+        case BRANCH_GOTO:
+          sb.append(" gotos");
+          break;
+        case BRANCH_IF:
+          sb.append(" ifs");
+          break;
+        case BRANCH_SWITCH:
+          sb.append(" switches");
+          break;
+        default:
+          sb.append(" " + Hex.u1(branchingness));
+          break;
+      }
     }
 
-    /**
-     * Gets the opcode.
-     *
-     * @return the opcode
-     */
-    public int getOpcode() {
-        return opcode;
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /**
+   * Gets the opcode.
+   *
+   * @return the opcode
+   */
+  public int getOpcode() {
+    return opcode;
+  }
+
+  /**
+   * Gets the result type. A return value of {@link Type#VOID}
+   * means this operation returns nothing.
+   *
+   * @return {@code null-ok;} the result spec
+   */
+  public Type getResult() {
+    return result;
+  }
+
+  /**
+   * Gets the source types.
+   *
+   * @return {@code non-null;} the source types
+   */
+  public TypeList getSources() {
+    return sources;
+  }
+
+  /**
+   * Gets the list of exception types that might be thrown.
+   *
+   * @return {@code non-null;} the list of exception types
+   */
+  public TypeList getExceptions() {
+    return exceptions;
+  }
+
+  /**
+   * Gets the branchingness of this instance.
+   *
+   * @return the branchingness
+   */
+  public int getBranchingness() {
+    return branchingness;
+  }
+
+  /**
+   * Gets whether this opcode is a function/method call or similar.
+   *
+   * @return {@code true} iff this opcode is call-like
+   */
+  public boolean isCallLike() {
+    return isCallLike;
+  }
+
+
+  /**
+   * Gets whether this opcode is commutative (the order of its sources are
+   * unimportant) or not. All commutative Rops have exactly two sources and
+   * have no branchiness.
+   *
+   * @return true if rop is commutative
+   */
+  public boolean isCommutative() {
+    switch (opcode) {
+      case RegOps.AND:
+      case RegOps.OR:
+      case RegOps.XOR:
+      case RegOps.ADD:
+      case RegOps.MUL:
+        return true;
+      default:
+        return false;
+    }
+  }
+
+  /**
+   * Gets the nickname. If this instance has no nickname, this returns
+   * the result of calling {@link #toString}.
+   *
+   * @return {@code non-null;} the nickname
+   */
+  public String getNickname() {
+    if (nickname != null) {
+      return nickname;
     }
 
-    /**
-     * Gets the result type. A return value of {@link Type#VOID}
-     * means this operation returns nothing.
-     *
-     * @return {@code null-ok;} the result spec
-     */
-    public Type getResult() {
-        return result;
-    }
+    return toString();
+  }
 
-    /**
-     * Gets the source types.
-     *
-     * @return {@code non-null;} the source types
-     */
-    public TypeList getSources() {
-        return sources;
-    }
-
-    /**
-     * Gets the list of exception types that might be thrown.
-     *
-     * @return {@code non-null;} the list of exception types
-     */
-    public TypeList getExceptions() {
-        return exceptions;
-    }
-
-    /**
-     * Gets the branchingness of this instance.
-     *
-     * @return the branchingness
-     */
-    public int getBranchingness() {
-        return branchingness;
-    }
-
-    /**
-     * Gets whether this opcode is a function/method call or similar.
-     *
-     * @return {@code true} iff this opcode is call-like
-     */
-    public boolean isCallLike() {
-        return isCallLike;
-    }
-
-
-    /**
-     * Gets whether this opcode is commutative (the order of its sources are
-     * unimportant) or not. All commutative Rops have exactly two sources and
-     * have no branchiness.
-     *
-     * @return true if rop is commutative
-     */
-    public boolean isCommutative() {
-        switch (opcode) {
-            case RegOps.AND:
-            case RegOps.OR:
-            case RegOps.XOR:
-            case RegOps.ADD:
-            case RegOps.MUL:
-                return true;
-            default:
-                return false;
-        }
-    }
-
-    /**
-     * Gets the nickname. If this instance has no nickname, this returns
-     * the result of calling {@link #toString}.
-     *
-     * @return {@code non-null;} the nickname
-     */
-    public String getNickname() {
-        if (nickname != null) {
-            return nickname;
-        }
-
-        return toString();
-    }
-
-    /**
-     * Gets whether this operation can possibly throw an exception. This
-     * is just a convenient wrapper for
-     * {@code getExceptions().size() != 0}.
-     *
-     * @return {@code true} iff this operation can possibly throw
-     */
-    public final boolean canThrow() {
-        return (exceptions.size() != 0);
-    }
+  /**
+   * Gets whether this operation can possibly throw an exception. This
+   * is just a convenient wrapper for
+   * {@code getExceptions().size() != 0}.
+   *
+   * @return {@code true} iff this operation can possibly throw
+   */
+  public final boolean canThrow() {
+    return (exceptions.size() != 0);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/RopMethod.java b/dx/src/com/android/jack/dx/rop/code/RopMethod.java
index 412dc0d..3133652 100644
--- a/dx/src/com/android/jack/dx/rop/code/RopMethod.java
+++ b/dx/src/com/android/jack/dx/rop/code/RopMethod.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.dx.rop.code;
 
-import com.android.jack.dx.util.Bits;
 import com.android.jack.dx.util.Hex;
 import com.android.jack.dx.util.IntList;
 
@@ -24,184 +23,183 @@
  * All of the parts that make up a method at the rop layer.
  */
 public final class RopMethod {
-    /** {@code non-null;} basic block list of the method */
-    private final BasicBlockList blocks;
+  /** {@code non-null;} basic block list of the method */
+  private final BasicBlockList blocks;
 
-    /** {@code >= 0;} label for the block which starts the method */
-    private final int firstLabel;
+  /** {@code >= 0;} label for the block which starts the method */
+  private final int firstLabel;
 
-    /**
-     * {@code null-ok;} array of predecessors for each block, indexed by block
-     * label
-     */
-    private IntList[] predecessors;
+  /**
+   * {@code null-ok;} array of predecessors for each block, indexed by block
+   * label
+   */
+  private IntList[] predecessors;
 
-    /**
-     * {@code null-ok;} the predecessors for the implicit "exit" block, that is
-     * the labels for the blocks that return, if calculated
-     */
-    private IntList exitPredecessors;
+  /**
+   * {@code null-ok;} the predecessors for the implicit "exit" block, that is
+   * the labels for the blocks that return, if calculated
+   */
+  private IntList exitPredecessors;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param blocks {@code non-null;} basic block list of the method
-     * @param firstLabel {@code >= 0;} the label of the first block to execute
-     */
-    public RopMethod(BasicBlockList blocks, int firstLabel) {
-        if (blocks == null) {
-            throw new NullPointerException("blocks == null");
-        }
-
-        if (firstLabel < 0) {
-            throw new IllegalArgumentException("firstLabel < 0");
-        }
-
-        this.blocks = blocks;
-        this.firstLabel = firstLabel;
-
-        this.predecessors = null;
-        this.exitPredecessors = null;
+  /**
+   * Constructs an instance.
+   *
+   * @param blocks {@code non-null;} basic block list of the method
+   * @param firstLabel {@code >= 0;} the label of the first block to execute
+   */
+  public RopMethod(BasicBlockList blocks, int firstLabel) {
+    if (blocks == null) {
+      throw new NullPointerException("blocks == null");
     }
 
-    /**
-     * Gets the basic block list for this method.
-     *
-     * @return {@code non-null;} the list
-     */
-    public BasicBlockList getBlocks() {
-        return blocks;
+    if (firstLabel < 0) {
+      throw new IllegalArgumentException("firstLabel < 0");
     }
 
-    /**
-     * Gets the label for the first block in the method that this list
-     * represents.
-     *
-     * @return {@code >= 0;} the first-block label
-     */
-    public int getFirstLabel() {
-        return firstLabel;
+    this.blocks = blocks;
+    this.firstLabel = firstLabel;
+
+    this.predecessors = null;
+    this.exitPredecessors = null;
+  }
+
+  /**
+   * Gets the basic block list for this method.
+   *
+   * @return {@code non-null;} the list
+   */
+  public BasicBlockList getBlocks() {
+    return blocks;
+  }
+
+  /**
+   * Gets the label for the first block in the method that this list
+   * represents.
+   *
+   * @return {@code >= 0;} the first-block label
+   */
+  public int getFirstLabel() {
+    return firstLabel;
+  }
+
+  /**
+   * Gets the predecessors associated with the given block. This throws
+   * an exception if there is no block with the given label.
+   *
+   * @param label {@code >= 0;} the label of the block in question
+   * @return {@code non-null;} the predecessors of that block
+   */
+  public IntList labelToPredecessors(int label) {
+    if (exitPredecessors == null) {
+      calcPredecessors();
     }
 
-    /**
-     * Gets the predecessors associated with the given block. This throws
-     * an exception if there is no block with the given label.
-     *
-     * @param label {@code >= 0;} the label of the block in question
-     * @return {@code non-null;} the predecessors of that block
-     */
-    public IntList labelToPredecessors(int label) {
-        if (exitPredecessors == null) {
-            calcPredecessors();
-        }
+    IntList result = predecessors[label];
 
-        IntList result = predecessors[label];
-
-        if (result == null) {
-            throw new RuntimeException("no such block: " + Hex.u2(label));
-        }
-
-        return result;
+    if (result == null) {
+      throw new RuntimeException("no such block: " + Hex.u2(label));
     }
 
-    /**
-     * Gets the exit predecessors for this instance.
-     *
-     * @return {@code non-null;} the exit predecessors
-     */
-    public IntList getExitPredecessors() {
-        if (exitPredecessors == null) {
-            calcPredecessors();
-        }
+    return result;
+  }
 
-        return exitPredecessors;
+  /**
+   * Gets the exit predecessors for this instance.
+   *
+   * @return {@code non-null;} the exit predecessors
+   */
+  public IntList getExitPredecessors() {
+    if (exitPredecessors == null) {
+      calcPredecessors();
     }
 
+    return exitPredecessors;
+  }
 
-    /**
-     * Returns an instance that is identical to this one, except that
-     * the registers in each instruction are offset by the given
-     * amount.
-     *
-     * @param delta the amount to offset register numbers by
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public RopMethod withRegisterOffset(int delta) {
-        RopMethod result = new RopMethod(blocks.withRegisterOffset(delta),
-                                         firstLabel);
 
-        if (exitPredecessors != null) {
-            /*
-             * The predecessors have been calculated. It's safe to
-             * inject these into the new instance, since the
-             * transformation being applied doesn't affect the
-             * predecessors.
-             */
-            result.exitPredecessors = exitPredecessors;
-            result.predecessors = predecessors;
-        }
+  /**
+   * Returns an instance that is identical to this one, except that
+   * the registers in each instruction are offset by the given
+   * amount.
+   *
+   * @param delta the amount to offset register numbers by
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public RopMethod withRegisterOffset(int delta) {
+    RopMethod result = new RopMethod(blocks.withRegisterOffset(delta), firstLabel);
 
-        return result;
+    if (exitPredecessors != null) {
+      /*
+       * The predecessors have been calculated. It's safe to
+       * inject these into the new instance, since the
+       * transformation being applied doesn't affect the
+       * predecessors.
+       */
+      result.exitPredecessors = exitPredecessors;
+      result.predecessors = predecessors;
     }
 
-    /**
-     * Calculates the predecessor sets for each block as well as for the
-     * exit.
+    return result;
+  }
+
+  /**
+   * Calculates the predecessor sets for each block as well as for the
+   * exit.
+   */
+  private void calcPredecessors() {
+    int maxLabel = blocks.getMaxLabel();
+    IntList[] predecessors = new IntList[maxLabel];
+    IntList exitPredecessors = new IntList(10);
+    int sz = blocks.size();
+
+    /*
+     * For each block, find its successors, and add the block's label to
+     * the successor's predecessors.
      */
-    private void calcPredecessors() {
-        int maxLabel = blocks.getMaxLabel();
-        IntList[] predecessors = new IntList[maxLabel];
-        IntList exitPredecessors = new IntList(10);
-        int sz = blocks.size();
-
-        /*
-         * For each block, find its successors, and add the block's label to
-         * the successor's predecessors.
-         */
-        for (int i = 0; i < sz; i++) {
-            BasicBlock one = blocks.get(i);
-            int label = one.getLabel();
-            IntList successors = one.getSuccessors();
-            int ssz = successors.size();
-            if (ssz == 0) {
-                // This block exits.
-                exitPredecessors.add(label);
-            } else {
-                for (int j = 0; j < ssz; j++) {
-                    int succLabel = successors.get(j);
-                    IntList succPreds = predecessors[succLabel];
-                    if (succPreds == null) {
-                        succPreds = new IntList(10);
-                        predecessors[succLabel] = succPreds;
-                    }
-                    succPreds.add(label);
-                }
-            }
+    for (int i = 0; i < sz; i++) {
+      BasicBlock one = blocks.get(i);
+      int label = one.getLabel();
+      IntList successors = one.getSuccessors();
+      int ssz = successors.size();
+      if (ssz == 0) {
+        // This block exits.
+        exitPredecessors.add(label);
+      } else {
+        for (int j = 0; j < ssz; j++) {
+          int succLabel = successors.get(j);
+          IntList succPreds = predecessors[succLabel];
+          if (succPreds == null) {
+            succPreds = new IntList(10);
+            predecessors[succLabel] = succPreds;
+          }
+          succPreds.add(label);
         }
-
-        // Sort and immutablize all the predecessor lists.
-        for (int i = 0; i < maxLabel; i++) {
-            IntList preds = predecessors[i];
-            if (preds != null) {
-                preds.sort();
-                preds.setImmutable();
-            }
-        }
-
-        exitPredecessors.sort();
-        exitPredecessors.setImmutable();
-
-        /*
-         * The start label might not ever have had any predecessors
-         * added to it (probably doesn't, because of how Java gets
-         * translated into rop form). So, check for this and rectify
-         * the situation if required.
-         */
-        if (predecessors[firstLabel] == null) {
-            predecessors[firstLabel] = IntList.EMPTY;
-        }
-
-        this.predecessors = predecessors;
-        this.exitPredecessors = exitPredecessors;
+      }
     }
+
+    // Sort and immutablize all the predecessor lists.
+    for (int i = 0; i < maxLabel; i++) {
+      IntList preds = predecessors[i];
+      if (preds != null) {
+        preds.sort();
+        preds.setImmutable();
+      }
+    }
+
+    exitPredecessors.sort();
+    exitPredecessors.setImmutable();
+
+    /*
+     * The start label might not ever have had any predecessors
+     * added to it (probably doesn't, because of how Java gets
+     * translated into rop form). So, check for this and rectify
+     * the situation if required.
+     */
+    if (predecessors[firstLabel] == null) {
+      predecessors[firstLabel] = IntList.EMPTY;
+    }
+
+    this.predecessors = predecessors;
+    this.exitPredecessors = exitPredecessors;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/Rops.java b/dx/src/com/android/jack/dx/rop/code/Rops.java
index 23deb8d..22ba56e 100644
--- a/dx/src/com/android/jack/dx/rop/code/Rops.java
+++ b/dx/src/com/android/jack/dx/rop/code/Rops.java
@@ -30,2061 +30,2110 @@
  * Standard instances of {@link Rop}.
  */
 public final class Rops {
-    /** {@code nop()} */
-    public static final Rop NOP =
-        new Rop(RegOps.NOP, Type.VOID, StdTypeList.EMPTY, "nop");
+  /** {@code nop()} */
+  public static final Rop NOP = new Rop(RegOps.NOP, Type.VOID, StdTypeList.EMPTY, "nop");
 
-    /** {@code r,x: int :: r = x;} */
-    public static final Rop MOVE_INT =
-        new Rop(RegOps.MOVE, Type.INT, StdTypeList.INT, "move-int");
+  /** {@code r,x: int :: r = x;} */
+  public static final Rop MOVE_INT = new Rop(RegOps.MOVE, Type.INT, StdTypeList.INT, "move-int");
 
-    /** {@code r,x: long :: r = x;} */
-    public static final Rop MOVE_LONG =
-        new Rop(RegOps.MOVE, Type.LONG, StdTypeList.LONG, "move-long");
+  /** {@code r,x: long :: r = x;} */
+  public static final Rop MOVE_LONG =
+      new Rop(RegOps.MOVE, Type.LONG, StdTypeList.LONG, "move-long");
 
-    /** {@code r,x: float :: r = x;} */
-    public static final Rop MOVE_FLOAT =
-        new Rop(RegOps.MOVE, Type.FLOAT, StdTypeList.FLOAT, "move-float");
+  /** {@code r,x: float :: r = x;} */
+  public static final Rop MOVE_FLOAT =
+      new Rop(RegOps.MOVE, Type.FLOAT, StdTypeList.FLOAT, "move-float");
 
-    /** {@code r,x: double :: r = x;} */
-    public static final Rop MOVE_DOUBLE =
-        new Rop(RegOps.MOVE, Type.DOUBLE, StdTypeList.DOUBLE, "move-double");
+  /** {@code r,x: double :: r = x;} */
+  public static final Rop MOVE_DOUBLE =
+      new Rop(RegOps.MOVE, Type.DOUBLE, StdTypeList.DOUBLE, "move-double");
 
-    /** {@code r,x: Object :: r = x;} */
-    public static final Rop MOVE_OBJECT =
-        new Rop(RegOps.MOVE, Type.OBJECT, StdTypeList.OBJECT, "move-object");
+  /** {@code r,x: Object :: r = x;} */
+  public static final Rop MOVE_OBJECT =
+      new Rop(RegOps.MOVE, Type.OBJECT, StdTypeList.OBJECT, "move-object");
 
-    /**
-     * {@code r,x: ReturnAddress :: r = x;}
-     *
-     * Note that this rop-form instruction has no dex-form equivilent and
-     * must be removed before the dex conversion.
-     */
-    public static final Rop MOVE_RETURN_ADDRESS =
-        new Rop(RegOps.MOVE, Type.RETURN_ADDRESS,
-                StdTypeList.RETURN_ADDRESS, "move-return-address");
+  /**
+   * {@code r,x: ReturnAddress :: r = x;}
+   *
+   * Note that this rop-form instruction has no dex-form equivilent and
+   * must be removed before the dex conversion.
+   */
+  public static final Rop MOVE_RETURN_ADDRESS =
+      new Rop(RegOps.MOVE, Type.RETURN_ADDRESS, StdTypeList.RETURN_ADDRESS, "move-return-address");
 
-    /** {@code r,param(x): int :: r = param(x);} */
-    public static final Rop MOVE_PARAM_INT =
-        new Rop(RegOps.MOVE_PARAM, Type.INT, StdTypeList.EMPTY,
-                "move-param-int");
+  /** {@code r,param(x): int :: r = param(x);} */
+  public static final Rop MOVE_PARAM_INT =
+      new Rop(RegOps.MOVE_PARAM, Type.INT, StdTypeList.EMPTY, "move-param-int");
 
-    /** {@code r,param(x): long :: r = param(x);} */
-    public static final Rop MOVE_PARAM_LONG =
-        new Rop(RegOps.MOVE_PARAM, Type.LONG, StdTypeList.EMPTY,
-                "move-param-long");
+  /** {@code r,param(x): long :: r = param(x);} */
+  public static final Rop MOVE_PARAM_LONG =
+      new Rop(RegOps.MOVE_PARAM, Type.LONG, StdTypeList.EMPTY, "move-param-long");
 
-    /** {@code r,param(x): float :: r = param(x);} */
-    public static final Rop MOVE_PARAM_FLOAT =
-        new Rop(RegOps.MOVE_PARAM, Type.FLOAT, StdTypeList.EMPTY,
-                "move-param-float");
+  /** {@code r,param(x): float :: r = param(x);} */
+  public static final Rop MOVE_PARAM_FLOAT =
+      new Rop(RegOps.MOVE_PARAM, Type.FLOAT, StdTypeList.EMPTY, "move-param-float");
 
-    /** {@code r,param(x): double :: r = param(x);} */
-    public static final Rop MOVE_PARAM_DOUBLE =
-        new Rop(RegOps.MOVE_PARAM, Type.DOUBLE, StdTypeList.EMPTY,
-                "move-param-double");
+  /** {@code r,param(x): double :: r = param(x);} */
+  public static final Rop MOVE_PARAM_DOUBLE =
+      new Rop(RegOps.MOVE_PARAM, Type.DOUBLE, StdTypeList.EMPTY, "move-param-double");
 
-    /** {@code r,param(x): Object :: r = param(x);} */
-    public static final Rop MOVE_PARAM_OBJECT =
-        new Rop(RegOps.MOVE_PARAM, Type.OBJECT, StdTypeList.EMPTY,
-                "move-param-object");
+  /** {@code r,param(x): Object :: r = param(x);} */
+  public static final Rop MOVE_PARAM_OBJECT =
+      new Rop(RegOps.MOVE_PARAM, Type.OBJECT, StdTypeList.EMPTY, "move-param-object");
 
-    /** {@code r, literal: int :: r = literal;} */
-    public static final Rop CONST_INT =
-        new Rop(RegOps.CONST, Type.INT, StdTypeList.EMPTY, "const-int");
+  /** {@code r, literal: int :: r = literal;} */
+  public static final Rop CONST_INT =
+      new Rop(RegOps.CONST, Type.INT, StdTypeList.EMPTY, "const-int");
 
-    /** {@code r, literal: long :: r = literal;} */
-    public static final Rop CONST_LONG =
-        new Rop(RegOps.CONST, Type.LONG, StdTypeList.EMPTY, "const-long");
+  /** {@code r, literal: long :: r = literal;} */
+  public static final Rop CONST_LONG =
+      new Rop(RegOps.CONST, Type.LONG, StdTypeList.EMPTY, "const-long");
 
-    /** {@code r, literal: float :: r = literal;} */
-    public static final Rop CONST_FLOAT =
-        new Rop(RegOps.CONST, Type.FLOAT, StdTypeList.EMPTY, "const-float");
+  /** {@code r, literal: float :: r = literal;} */
+  public static final Rop CONST_FLOAT =
+      new Rop(RegOps.CONST, Type.FLOAT, StdTypeList.EMPTY, "const-float");
 
-    /** {@code r, literal: double :: r = literal;} */
-    public static final Rop CONST_DOUBLE =
-        new Rop(RegOps.CONST, Type.DOUBLE, StdTypeList.EMPTY, "const-double");
+  /** {@code r, literal: double :: r = literal;} */
+  public static final Rop CONST_DOUBLE =
+      new Rop(RegOps.CONST, Type.DOUBLE, StdTypeList.EMPTY, "const-double");
 
-    /** {@code r, literal: Object :: r = literal;} */
-    public static final Rop CONST_OBJECT =
-        new Rop(RegOps.CONST, Type.OBJECT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "const-object");
+  /** {@code r, literal: Object :: r = literal;} */
+  public static final Rop CONST_OBJECT =
+      new Rop(RegOps.CONST, Type.OBJECT, StdTypeList.EMPTY, Exceptions.LIST_Error, "const-object");
 
-    /** {@code r, literal: Object :: r = literal;} */
-    public static final Rop CONST_OBJECT_NOTHROW =
-        new Rop(RegOps.CONST, Type.OBJECT, StdTypeList.EMPTY,
-                "const-object-nothrow");
+  /** {@code r, literal: Object :: r = literal;} */
+  public static final Rop CONST_OBJECT_NOTHROW =
+      new Rop(RegOps.CONST, Type.OBJECT, StdTypeList.EMPTY, "const-object-nothrow");
 
-    /** {@code goto label} */
-    public static final Rop GOTO =
-        new Rop(RegOps.GOTO, Type.VOID, StdTypeList.EMPTY, Rop.BRANCH_GOTO,
-                "goto");
+  /** {@code goto label} */
+  public static final Rop GOTO =
+      new Rop(RegOps.GOTO, Type.VOID, StdTypeList.EMPTY, Rop.BRANCH_GOTO, "goto");
 
-    /** {@code x: int :: if (x == 0) goto label} */
-    public static final Rop IF_EQZ_INT =
-        new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-eqz-int");
+  /** {@code x: int :: if (x == 0) goto label} */
+  public static final Rop IF_EQZ_INT =
+      new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-eqz-int");
 
-    /** {@code x: int :: if (x != 0) goto label} */
-    public static final Rop IF_NEZ_INT =
-        new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-nez-int");
+  /** {@code x: int :: if (x != 0) goto label} */
+  public static final Rop IF_NEZ_INT =
+      new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-nez-int");
 
-    /** {@code x: int :: if (x < 0) goto label} */
-    public static final Rop IF_LTZ_INT =
-        new Rop(RegOps.IF_LT, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-ltz-int");
+  /** {@code x: int :: if (x < 0) goto label} */
+  public static final Rop IF_LTZ_INT =
+      new Rop(RegOps.IF_LT, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-ltz-int");
 
-    /** {@code x: int :: if (x >= 0) goto label} */
-    public static final Rop IF_GEZ_INT =
-        new Rop(RegOps.IF_GE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-gez-int");
+  /** {@code x: int :: if (x >= 0) goto label} */
+  public static final Rop IF_GEZ_INT =
+      new Rop(RegOps.IF_GE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-gez-int");
 
-    /** {@code x: int :: if (x <= 0) goto label} */
-    public static final Rop IF_LEZ_INT =
-        new Rop(RegOps.IF_LE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-lez-int");
+  /** {@code x: int :: if (x <= 0) goto label} */
+  public static final Rop IF_LEZ_INT =
+      new Rop(RegOps.IF_LE, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-lez-int");
 
-    /** {@code x: int :: if (x > 0) goto label} */
-    public static final Rop IF_GTZ_INT =
-        new Rop(RegOps.IF_GT, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF,
-                "if-gtz-int");
+  /** {@code x: int :: if (x > 0) goto label} */
+  public static final Rop IF_GTZ_INT =
+      new Rop(RegOps.IF_GT, Type.VOID, StdTypeList.INT, Rop.BRANCH_IF, "if-gtz-int");
 
-    /** {@code x: Object :: if (x == null) goto label} */
-    public static final Rop IF_EQZ_OBJECT =
-        new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.OBJECT, Rop.BRANCH_IF,
-                "if-eqz-object");
+  /** {@code x: Object :: if (x == null) goto label} */
+  public static final Rop IF_EQZ_OBJECT =
+      new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.OBJECT, Rop.BRANCH_IF, "if-eqz-object");
 
-    /** {@code x: Object :: if (x != null) goto label} */
-    public static final Rop IF_NEZ_OBJECT =
-        new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.OBJECT, Rop.BRANCH_IF,
-                "if-nez-object");
+  /** {@code x: Object :: if (x != null) goto label} */
+  public static final Rop IF_NEZ_OBJECT =
+      new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.OBJECT, Rop.BRANCH_IF, "if-nez-object");
 
-    /** {@code x,y: int :: if (x == y) goto label} */
-    public static final Rop IF_EQ_INT =
-        new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-eq-int");
+  /** {@code x,y: int :: if (x == y) goto label} */
+  public static final Rop IF_EQ_INT =
+      new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-eq-int");
 
-    /** {@code x,y: int :: if (x != y) goto label} */
-    public static final Rop IF_NE_INT =
-        new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-ne-int");
+  /** {@code x,y: int :: if (x != y) goto label} */
+  public static final Rop IF_NE_INT =
+      new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-ne-int");
 
-    /** {@code x,y: int :: if (x < y) goto label} */
-    public static final Rop IF_LT_INT =
-        new Rop(RegOps.IF_LT, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-lt-int");
+  /** {@code x,y: int :: if (x < y) goto label} */
+  public static final Rop IF_LT_INT =
+      new Rop(RegOps.IF_LT, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-lt-int");
 
-    /** {@code x,y: int :: if (x >= y) goto label} */
-    public static final Rop IF_GE_INT =
-        new Rop(RegOps.IF_GE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-ge-int");
+  /** {@code x,y: int :: if (x >= y) goto label} */
+  public static final Rop IF_GE_INT =
+      new Rop(RegOps.IF_GE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-ge-int");
 
-    /** {@code x,y: int :: if (x <= y) goto label} */
-    public static final Rop IF_LE_INT =
-        new Rop(RegOps.IF_LE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-le-int");
+  /** {@code x,y: int :: if (x <= y) goto label} */
+  public static final Rop IF_LE_INT =
+      new Rop(RegOps.IF_LE, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-le-int");
 
-    /** {@code x,y: int :: if (x > y) goto label} */
-    public static final Rop IF_GT_INT =
-        new Rop(RegOps.IF_GT, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF,
-                "if-gt-int");
+  /** {@code x,y: int :: if (x > y) goto label} */
+  public static final Rop IF_GT_INT =
+      new Rop(RegOps.IF_GT, Type.VOID, StdTypeList.INT_INT, Rop.BRANCH_IF, "if-gt-int");
 
-    /** {@code x,y: Object :: if (x == y) goto label} */
-    public static final Rop IF_EQ_OBJECT =
-        new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.OBJECT_OBJECT,
-                Rop.BRANCH_IF, "if-eq-object");
+  /** {@code x,y: Object :: if (x == y) goto label} */
+  public static final Rop IF_EQ_OBJECT =
+      new Rop(RegOps.IF_EQ, Type.VOID, StdTypeList.OBJECT_OBJECT, Rop.BRANCH_IF, "if-eq-object");
 
-    /** {@code x,y: Object :: if (x != y) goto label} */
-    public static final Rop IF_NE_OBJECT =
-        new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.OBJECT_OBJECT,
-                Rop.BRANCH_IF, "if-ne-object");
+  /** {@code x,y: Object :: if (x != y) goto label} */
+  public static final Rop IF_NE_OBJECT =
+      new Rop(RegOps.IF_NE, Type.VOID, StdTypeList.OBJECT_OBJECT, Rop.BRANCH_IF, "if-ne-object");
 
-    /** {@code x: int :: goto switchtable[x]} */
-    public static final Rop SWITCH =
-        new Rop(RegOps.SWITCH, Type.VOID, StdTypeList.INT, Rop.BRANCH_SWITCH,
-                "switch");
+  /** {@code x: int :: goto switchtable[x]} */
+  public static final Rop SWITCH =
+      new Rop(RegOps.SWITCH, Type.VOID, StdTypeList.INT, Rop.BRANCH_SWITCH, "switch");
 
-    /** {@code r,x,y: int :: r = x + y;} */
-    public static final Rop ADD_INT =
-        new Rop(RegOps.ADD, Type.INT, StdTypeList.INT_INT, "add-int");
+  /** {@code r,x,y: int :: r = x + y;} */
+  public static final Rop ADD_INT = new Rop(RegOps.ADD, Type.INT, StdTypeList.INT_INT, "add-int");
 
-    /** {@code r,x,y: long :: r = x + y;} */
-    public static final Rop ADD_LONG =
-        new Rop(RegOps.ADD, Type.LONG, StdTypeList.LONG_LONG, "add-long");
+  /** {@code r,x,y: long :: r = x + y;} */
+  public static final Rop ADD_LONG =
+      new Rop(RegOps.ADD, Type.LONG, StdTypeList.LONG_LONG, "add-long");
 
-    /** {@code r,x,y: float :: r = x + y;} */
-    public static final Rop ADD_FLOAT =
-        new Rop(RegOps.ADD, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "add-float");
+  /** {@code r,x,y: float :: r = x + y;} */
+  public static final Rop ADD_FLOAT =
+      new Rop(RegOps.ADD, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "add-float");
 
-    /** {@code r,x,y: double :: r = x + y;} */
-    public static final Rop ADD_DOUBLE =
-        new Rop(RegOps.ADD, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE,
-                Rop.BRANCH_NONE, "add-double");
+  /** {@code r,x,y: double :: r = x + y;} */
+  public static final Rop ADD_DOUBLE =
+      new Rop(RegOps.ADD, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE, Rop.BRANCH_NONE, "add-double");
 
-    /** {@code r,x,y: int :: r = x - y;} */
-    public static final Rop SUB_INT =
-        new Rop(RegOps.SUB, Type.INT, StdTypeList.INT_INT, "sub-int");
+  /** {@code r,x,y: int :: r = x - y;} */
+  public static final Rop SUB_INT = new Rop(RegOps.SUB, Type.INT, StdTypeList.INT_INT, "sub-int");
 
-    /** {@code r,x,y: long :: r = x - y;} */
-    public static final Rop SUB_LONG =
-        new Rop(RegOps.SUB, Type.LONG, StdTypeList.LONG_LONG, "sub-long");
+  /** {@code r,x,y: long :: r = x - y;} */
+  public static final Rop SUB_LONG =
+      new Rop(RegOps.SUB, Type.LONG, StdTypeList.LONG_LONG, "sub-long");
 
-    /** {@code r,x,y: float :: r = x - y;} */
-    public static final Rop SUB_FLOAT =
-        new Rop(RegOps.SUB, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "sub-float");
+  /** {@code r,x,y: float :: r = x - y;} */
+  public static final Rop SUB_FLOAT =
+      new Rop(RegOps.SUB, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "sub-float");
 
-    /** {@code r,x,y: double :: r = x - y;} */
-    public static final Rop SUB_DOUBLE =
-        new Rop(RegOps.SUB, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE,
-                Rop.BRANCH_NONE, "sub-double");
+  /** {@code r,x,y: double :: r = x - y;} */
+  public static final Rop SUB_DOUBLE =
+      new Rop(RegOps.SUB, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE, Rop.BRANCH_NONE, "sub-double");
 
-    /** {@code r,x,y: int :: r = x * y;} */
-    public static final Rop MUL_INT =
-        new Rop(RegOps.MUL, Type.INT, StdTypeList.INT_INT, "mul-int");
+  /** {@code r,x,y: int :: r = x * y;} */
+  public static final Rop MUL_INT = new Rop(RegOps.MUL, Type.INT, StdTypeList.INT_INT, "mul-int");
 
-    /** {@code r,x,y: long :: r = x * y;} */
-    public static final Rop MUL_LONG =
-        new Rop(RegOps.MUL, Type.LONG, StdTypeList.LONG_LONG, "mul-long");
+  /** {@code r,x,y: long :: r = x * y;} */
+  public static final Rop MUL_LONG =
+      new Rop(RegOps.MUL, Type.LONG, StdTypeList.LONG_LONG, "mul-long");
 
-    /** {@code r,x,y: float :: r = x * y;} */
-    public static final Rop MUL_FLOAT =
-        new Rop(RegOps.MUL, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "mul-float");
+  /** {@code r,x,y: float :: r = x * y;} */
+  public static final Rop MUL_FLOAT =
+      new Rop(RegOps.MUL, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "mul-float");
 
-    /** {@code r,x,y: double :: r = x * y;} */
-    public static final Rop MUL_DOUBLE =
-        new Rop(RegOps.MUL, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE,
-                Rop.BRANCH_NONE, "mul-double");
+  /** {@code r,x,y: double :: r = x * y;} */
+  public static final Rop MUL_DOUBLE =
+      new Rop(RegOps.MUL, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE, Rop.BRANCH_NONE, "mul-double");
 
-    /** {@code r,x,y: int :: r = x / y;} */
-    public static final Rop DIV_INT =
-        new Rop(RegOps.DIV, Type.INT, StdTypeList.INT_INT,
-                Exceptions.LIST_Error_ArithmeticException, "div-int");
+  /** {@code r,x,y: int :: r = x / y;} */
+  public static final Rop DIV_INT = new Rop(RegOps.DIV, Type.INT, StdTypeList.INT_INT,
+      Exceptions.LIST_Error_ArithmeticException, "div-int");
 
-    /** {@code r,x,y: long :: r = x / y;} */
-    public static final Rop DIV_LONG =
-        new Rop(RegOps.DIV, Type.LONG, StdTypeList.LONG_LONG,
-                Exceptions.LIST_Error_ArithmeticException, "div-long");
+  /** {@code r,x,y: long :: r = x / y;} */
+  public static final Rop DIV_LONG = new Rop(RegOps.DIV, Type.LONG, StdTypeList.LONG_LONG,
+      Exceptions.LIST_Error_ArithmeticException, "div-long");
 
-    /** {@code r,x,y: float :: r = x / y;} */
-    public static final Rop DIV_FLOAT =
-        new Rop(RegOps.DIV, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "div-float");
+  /** {@code r,x,y: float :: r = x / y;} */
+  public static final Rop DIV_FLOAT =
+      new Rop(RegOps.DIV, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "div-float");
 
-    /** {@code r,x,y: double :: r = x / y;} */
-    public static final Rop DIV_DOUBLE =
-        new Rop(RegOps.DIV, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE,
-                "div-double");
+  /** {@code r,x,y: double :: r = x / y;} */
+  public static final Rop DIV_DOUBLE =
+      new Rop(RegOps.DIV, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE, "div-double");
 
-    /** {@code r,x,y: int :: r = x % y;} */
-    public static final Rop REM_INT =
-        new Rop(RegOps.REM, Type.INT, StdTypeList.INT_INT,
-                Exceptions.LIST_Error_ArithmeticException, "rem-int");
+  /** {@code r,x,y: int :: r = x % y;} */
+  public static final Rop REM_INT = new Rop(RegOps.REM, Type.INT, StdTypeList.INT_INT,
+      Exceptions.LIST_Error_ArithmeticException, "rem-int");
 
-    /** {@code r,x,y: long :: r = x % y;} */
-    public static final Rop REM_LONG =
-        new Rop(RegOps.REM, Type.LONG, StdTypeList.LONG_LONG,
-                Exceptions.LIST_Error_ArithmeticException, "rem-long");
+  /** {@code r,x,y: long :: r = x % y;} */
+  public static final Rop REM_LONG = new Rop(RegOps.REM, Type.LONG, StdTypeList.LONG_LONG,
+      Exceptions.LIST_Error_ArithmeticException, "rem-long");
 
-    /** {@code r,x,y: float :: r = x % y;} */
-    public static final Rop REM_FLOAT =
-        new Rop(RegOps.REM, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "rem-float");
+  /** {@code r,x,y: float :: r = x % y;} */
+  public static final Rop REM_FLOAT =
+      new Rop(RegOps.REM, Type.FLOAT, StdTypeList.FLOAT_FLOAT, "rem-float");
 
-    /** {@code r,x,y: double :: r = x % y;} */
-    public static final Rop REM_DOUBLE =
-        new Rop(RegOps.REM, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE,
-                "rem-double");
+  /** {@code r,x,y: double :: r = x % y;} */
+  public static final Rop REM_DOUBLE =
+      new Rop(RegOps.REM, Type.DOUBLE, StdTypeList.DOUBLE_DOUBLE, "rem-double");
 
-    /** {@code r,x: int :: r = -x;} */
-    public static final Rop NEG_INT =
-        new Rop(RegOps.NEG, Type.INT, StdTypeList.INT, "neg-int");
+  /** {@code r,x: int :: r = -x;} */
+  public static final Rop NEG_INT = new Rop(RegOps.NEG, Type.INT, StdTypeList.INT, "neg-int");
 
-    /** {@code r,x: long :: r = -x;} */
-    public static final Rop NEG_LONG =
-        new Rop(RegOps.NEG, Type.LONG, StdTypeList.LONG, "neg-long");
+  /** {@code r,x: long :: r = -x;} */
+  public static final Rop NEG_LONG = new Rop(RegOps.NEG, Type.LONG, StdTypeList.LONG, "neg-long");
 
-    /** {@code r,x: float :: r = -x;} */
-    public static final Rop NEG_FLOAT =
-        new Rop(RegOps.NEG, Type.FLOAT, StdTypeList.FLOAT, "neg-float");
+  /** {@code r,x: float :: r = -x;} */
+  public static final Rop NEG_FLOAT =
+      new Rop(RegOps.NEG, Type.FLOAT, StdTypeList.FLOAT, "neg-float");
 
-    /** {@code r,x: double :: r = -x;} */
-    public static final Rop NEG_DOUBLE =
-        new Rop(RegOps.NEG, Type.DOUBLE, StdTypeList.DOUBLE, "neg-double");
+  /** {@code r,x: double :: r = -x;} */
+  public static final Rop NEG_DOUBLE =
+      new Rop(RegOps.NEG, Type.DOUBLE, StdTypeList.DOUBLE, "neg-double");
 
-    /** {@code r,x,y: int :: r = x & y;} */
-    public static final Rop AND_INT =
-        new Rop(RegOps.AND, Type.INT, StdTypeList.INT_INT, "and-int");
+  /** {@code r,x,y: int :: r = x & y;} */
+  public static final Rop AND_INT = new Rop(RegOps.AND, Type.INT, StdTypeList.INT_INT, "and-int");
 
-    /** {@code r,x,y: long :: r = x & y;} */
-    public static final Rop AND_LONG =
-        new Rop(RegOps.AND, Type.LONG, StdTypeList.LONG_LONG, "and-long");
+  /** {@code r,x,y: long :: r = x & y;} */
+  public static final Rop AND_LONG =
+      new Rop(RegOps.AND, Type.LONG, StdTypeList.LONG_LONG, "and-long");
 
-    /** {@code r,x,y: int :: r = x | y;} */
-    public static final Rop OR_INT =
-        new Rop(RegOps.OR, Type.INT, StdTypeList.INT_INT, "or-int");
+  /** {@code r,x,y: int :: r = x | y;} */
+  public static final Rop OR_INT = new Rop(RegOps.OR, Type.INT, StdTypeList.INT_INT, "or-int");
 
-    /** {@code r,x,y: long :: r = x | y;} */
-    public static final Rop OR_LONG =
-        new Rop(RegOps.OR, Type.LONG, StdTypeList.LONG_LONG, "or-long");
+  /** {@code r,x,y: long :: r = x | y;} */
+  public static final Rop OR_LONG = new Rop(RegOps.OR, Type.LONG, StdTypeList.LONG_LONG, "or-long");
 
-    /** {@code r,x,y: int :: r = x ^ y;} */
-    public static final Rop XOR_INT =
-        new Rop(RegOps.XOR, Type.INT, StdTypeList.INT_INT, "xor-int");
+  /** {@code r,x,y: int :: r = x ^ y;} */
+  public static final Rop XOR_INT = new Rop(RegOps.XOR, Type.INT, StdTypeList.INT_INT, "xor-int");
 
-    /** {@code r,x,y: long :: r = x ^ y;} */
-    public static final Rop XOR_LONG =
-        new Rop(RegOps.XOR, Type.LONG, StdTypeList.LONG_LONG, "xor-long");
+  /** {@code r,x,y: long :: r = x ^ y;} */
+  public static final Rop XOR_LONG =
+      new Rop(RegOps.XOR, Type.LONG, StdTypeList.LONG_LONG, "xor-long");
 
-    /** {@code r,x,y: int :: r = x << y;} */
-    public static final Rop SHL_INT =
-        new Rop(RegOps.SHL, Type.INT, StdTypeList.INT_INT, "shl-int");
+  /** {@code r,x,y: int :: r = x << y;} */
+  public static final Rop SHL_INT = new Rop(RegOps.SHL, Type.INT, StdTypeList.INT_INT, "shl-int");
 
-    /** {@code r,x: long; y: int :: r = x << y;} */
-    public static final Rop SHL_LONG =
-        new Rop(RegOps.SHL, Type.LONG, StdTypeList.LONG_INT, "shl-long");
+  /** {@code r,x: long; y: int :: r = x << y;} */
+  public static final Rop SHL_LONG =
+      new Rop(RegOps.SHL, Type.LONG, StdTypeList.LONG_INT, "shl-long");
 
-    /** {@code r,x,y: int :: r = x >> y;} */
-    public static final Rop SHR_INT =
-        new Rop(RegOps.SHR, Type.INT, StdTypeList.INT_INT, "shr-int");
+  /** {@code r,x,y: int :: r = x >> y;} */
+  public static final Rop SHR_INT = new Rop(RegOps.SHR, Type.INT, StdTypeList.INT_INT, "shr-int");
 
-    /** {@code r,x: long; y: int :: r = x >> y;} */
-    public static final Rop SHR_LONG =
-        new Rop(RegOps.SHR, Type.LONG, StdTypeList.LONG_INT, "shr-long");
+  /** {@code r,x: long; y: int :: r = x >> y;} */
+  public static final Rop SHR_LONG =
+      new Rop(RegOps.SHR, Type.LONG, StdTypeList.LONG_INT, "shr-long");
 
-    /** {@code r,x,y: int :: r = x >>> y;} */
-    public static final Rop USHR_INT =
-        new Rop(RegOps.USHR, Type.INT, StdTypeList.INT_INT, "ushr-int");
+  /** {@code r,x,y: int :: r = x >>> y;} */
+  public static final Rop USHR_INT =
+      new Rop(RegOps.USHR, Type.INT, StdTypeList.INT_INT, "ushr-int");
 
-    /** {@code r,x: long; y: int :: r = x >>> y;} */
-    public static final Rop USHR_LONG =
-        new Rop(RegOps.USHR, Type.LONG, StdTypeList.LONG_INT, "ushr-long");
+  /** {@code r,x: long; y: int :: r = x >>> y;} */
+  public static final Rop USHR_LONG =
+      new Rop(RegOps.USHR, Type.LONG, StdTypeList.LONG_INT, "ushr-long");
 
-    /** {@code r,x: int :: r = ~x;} */
-    public static final Rop NOT_INT =
-        new Rop(RegOps.NOT, Type.INT, StdTypeList.INT, "not-int");
+  /** {@code r,x: int :: r = ~x;} */
+  public static final Rop NOT_INT = new Rop(RegOps.NOT, Type.INT, StdTypeList.INT, "not-int");
 
-    /** {@code r,x: long :: r = ~x;} */
-    public static final Rop NOT_LONG =
-        new Rop(RegOps.NOT, Type.LONG, StdTypeList.LONG, "not-long");
+  /** {@code r,x: long :: r = ~x;} */
+  public static final Rop NOT_LONG = new Rop(RegOps.NOT, Type.LONG, StdTypeList.LONG, "not-long");
 
-    /** {@code r,x,c: int :: r = x + c;} */
-    public static final Rop ADD_CONST_INT =
-        new Rop(RegOps.ADD, Type.INT, StdTypeList.INT, "add-const-int");
+  /** {@code r,x,c: int :: r = x + c;} */
+  public static final Rop ADD_CONST_INT =
+      new Rop(RegOps.ADD, Type.INT, StdTypeList.INT, "add-const-int");
 
-    /** {@code r,x,c: long :: r = x + c;} */
-    public static final Rop ADD_CONST_LONG =
-        new Rop(RegOps.ADD, Type.LONG, StdTypeList.LONG, "add-const-long");
+  /** {@code r,x,c: long :: r = x + c;} */
+  public static final Rop ADD_CONST_LONG =
+      new Rop(RegOps.ADD, Type.LONG, StdTypeList.LONG, "add-const-long");
 
-    /** {@code r,x,c: float :: r = x + c;} */
-    public static final Rop ADD_CONST_FLOAT =
-        new Rop(RegOps.ADD, Type.FLOAT, StdTypeList.FLOAT, "add-const-float");
+  /** {@code r,x,c: float :: r = x + c;} */
+  public static final Rop ADD_CONST_FLOAT =
+      new Rop(RegOps.ADD, Type.FLOAT, StdTypeList.FLOAT, "add-const-float");
 
-    /** {@code r,x,c: double :: r = x + c;} */
-    public static final Rop ADD_CONST_DOUBLE =
-        new Rop(RegOps.ADD, Type.DOUBLE, StdTypeList.DOUBLE,
-                "add-const-double");
+  /** {@code r,x,c: double :: r = x + c;} */
+  public static final Rop ADD_CONST_DOUBLE =
+      new Rop(RegOps.ADD, Type.DOUBLE, StdTypeList.DOUBLE, "add-const-double");
 
-    /** {@code r,x,c: int :: r = x - c;} */
-    public static final Rop SUB_CONST_INT =
-        new Rop(RegOps.SUB, Type.INT, StdTypeList.INT, "sub-const-int");
+  /** {@code r,x,c: int :: r = x - c;} */
+  public static final Rop SUB_CONST_INT =
+      new Rop(RegOps.SUB, Type.INT, StdTypeList.INT, "sub-const-int");
 
-    /** {@code r,x,c: long :: r = x - c;} */
-    public static final Rop SUB_CONST_LONG =
-        new Rop(RegOps.SUB, Type.LONG, StdTypeList.LONG, "sub-const-long");
+  /** {@code r,x,c: long :: r = x - c;} */
+  public static final Rop SUB_CONST_LONG =
+      new Rop(RegOps.SUB, Type.LONG, StdTypeList.LONG, "sub-const-long");
 
-    /** {@code r,x,c: float :: r = x - c;} */
-    public static final Rop SUB_CONST_FLOAT =
-        new Rop(RegOps.SUB, Type.FLOAT, StdTypeList.FLOAT, "sub-const-float");
+  /** {@code r,x,c: float :: r = x - c;} */
+  public static final Rop SUB_CONST_FLOAT =
+      new Rop(RegOps.SUB, Type.FLOAT, StdTypeList.FLOAT, "sub-const-float");
 
-    /** {@code r,x,c: double :: r = x - c;} */
-    public static final Rop SUB_CONST_DOUBLE =
-        new Rop(RegOps.SUB, Type.DOUBLE, StdTypeList.DOUBLE,
-                "sub-const-double");
+  /** {@code r,x,c: double :: r = x - c;} */
+  public static final Rop SUB_CONST_DOUBLE =
+      new Rop(RegOps.SUB, Type.DOUBLE, StdTypeList.DOUBLE, "sub-const-double");
 
-    /** {@code r,x,c: int :: r = x * c;} */
-    public static final Rop MUL_CONST_INT =
-        new Rop(RegOps.MUL, Type.INT, StdTypeList.INT, "mul-const-int");
+  /** {@code r,x,c: int :: r = x * c;} */
+  public static final Rop MUL_CONST_INT =
+      new Rop(RegOps.MUL, Type.INT, StdTypeList.INT, "mul-const-int");
 
-    /** {@code r,x,c: long :: r = x * c;} */
-    public static final Rop MUL_CONST_LONG =
-        new Rop(RegOps.MUL, Type.LONG, StdTypeList.LONG, "mul-const-long");
+  /** {@code r,x,c: long :: r = x * c;} */
+  public static final Rop MUL_CONST_LONG =
+      new Rop(RegOps.MUL, Type.LONG, StdTypeList.LONG, "mul-const-long");
 
-    /** {@code r,x,c: float :: r = x * c;} */
-    public static final Rop MUL_CONST_FLOAT =
-        new Rop(RegOps.MUL, Type.FLOAT, StdTypeList.FLOAT, "mul-const-float");
+  /** {@code r,x,c: float :: r = x * c;} */
+  public static final Rop MUL_CONST_FLOAT =
+      new Rop(RegOps.MUL, Type.FLOAT, StdTypeList.FLOAT, "mul-const-float");
 
-    /** {@code r,x,c: double :: r = x * c;} */
-    public static final Rop MUL_CONST_DOUBLE =
-        new Rop(RegOps.MUL, Type.DOUBLE, StdTypeList.DOUBLE,
-                "mul-const-double");
+  /** {@code r,x,c: double :: r = x * c;} */
+  public static final Rop MUL_CONST_DOUBLE =
+      new Rop(RegOps.MUL, Type.DOUBLE, StdTypeList.DOUBLE, "mul-const-double");
 
-    /** {@code r,x,c: int :: r = x / c;} */
-    public static final Rop DIV_CONST_INT =
-        new Rop(RegOps.DIV, Type.INT, StdTypeList.INT,
-                Exceptions.LIST_Error_ArithmeticException, "div-const-int");
+  /** {@code r,x,c: int :: r = x / c;} */
+  public static final Rop DIV_CONST_INT = new Rop(RegOps.DIV, Type.INT, StdTypeList.INT,
+      Exceptions.LIST_Error_ArithmeticException, "div-const-int");
 
-    /** {@code r,x,c: long :: r = x / c;} */
-    public static final Rop DIV_CONST_LONG =
-        new Rop(RegOps.DIV, Type.LONG, StdTypeList.LONG,
-                Exceptions.LIST_Error_ArithmeticException, "div-const-long");
+  /** {@code r,x,c: long :: r = x / c;} */
+  public static final Rop DIV_CONST_LONG = new Rop(RegOps.DIV, Type.LONG, StdTypeList.LONG,
+      Exceptions.LIST_Error_ArithmeticException, "div-const-long");
 
-    /** {@code r,x,c: float :: r = x / c;} */
-    public static final Rop DIV_CONST_FLOAT =
-        new Rop(RegOps.DIV, Type.FLOAT, StdTypeList.FLOAT, "div-const-float");
+  /** {@code r,x,c: float :: r = x / c;} */
+  public static final Rop DIV_CONST_FLOAT =
+      new Rop(RegOps.DIV, Type.FLOAT, StdTypeList.FLOAT, "div-const-float");
 
-    /** {@code r,x,c: double :: r = x / c;} */
-    public static final Rop DIV_CONST_DOUBLE =
-        new Rop(RegOps.DIV, Type.DOUBLE, StdTypeList.DOUBLE,
-                "div-const-double");
+  /** {@code r,x,c: double :: r = x / c;} */
+  public static final Rop DIV_CONST_DOUBLE =
+      new Rop(RegOps.DIV, Type.DOUBLE, StdTypeList.DOUBLE, "div-const-double");
 
-    /** {@code r,x,c: int :: r = x % c;} */
-    public static final Rop REM_CONST_INT =
-        new Rop(RegOps.REM, Type.INT, StdTypeList.INT,
-                Exceptions.LIST_Error_ArithmeticException, "rem-const-int");
+  /** {@code r,x,c: int :: r = x % c;} */
+  public static final Rop REM_CONST_INT = new Rop(RegOps.REM, Type.INT, StdTypeList.INT,
+      Exceptions.LIST_Error_ArithmeticException, "rem-const-int");
 
-    /** {@code r,x,c: long :: r = x % c;} */
-    public static final Rop REM_CONST_LONG =
-        new Rop(RegOps.REM, Type.LONG, StdTypeList.LONG,
-                Exceptions.LIST_Error_ArithmeticException, "rem-const-long");
+  /** {@code r,x,c: long :: r = x % c;} */
+  public static final Rop REM_CONST_LONG = new Rop(RegOps.REM, Type.LONG, StdTypeList.LONG,
+      Exceptions.LIST_Error_ArithmeticException, "rem-const-long");
 
-    /** {@code r,x,c: float :: r = x % c;} */
-    public static final Rop REM_CONST_FLOAT =
-        new Rop(RegOps.REM, Type.FLOAT, StdTypeList.FLOAT, "rem-const-float");
+  /** {@code r,x,c: float :: r = x % c;} */
+  public static final Rop REM_CONST_FLOAT =
+      new Rop(RegOps.REM, Type.FLOAT, StdTypeList.FLOAT, "rem-const-float");
 
-    /** {@code r,x,c: double :: r = x % c;} */
-    public static final Rop REM_CONST_DOUBLE =
-        new Rop(RegOps.REM, Type.DOUBLE, StdTypeList.DOUBLE,
-                "rem-const-double");
+  /** {@code r,x,c: double :: r = x % c;} */
+  public static final Rop REM_CONST_DOUBLE =
+      new Rop(RegOps.REM, Type.DOUBLE, StdTypeList.DOUBLE, "rem-const-double");
 
-    /** {@code r,x,c: int :: r = x & c;} */
-    public static final Rop AND_CONST_INT =
-        new Rop(RegOps.AND, Type.INT, StdTypeList.INT, "and-const-int");
+  /** {@code r,x,c: int :: r = x & c;} */
+  public static final Rop AND_CONST_INT =
+      new Rop(RegOps.AND, Type.INT, StdTypeList.INT, "and-const-int");
 
-    /** {@code r,x,c: long :: r = x & c;} */
-    public static final Rop AND_CONST_LONG =
-        new Rop(RegOps.AND, Type.LONG, StdTypeList.LONG, "and-const-long");
+  /** {@code r,x,c: long :: r = x & c;} */
+  public static final Rop AND_CONST_LONG =
+      new Rop(RegOps.AND, Type.LONG, StdTypeList.LONG, "and-const-long");
 
-    /** {@code r,x,c: int :: r = x | c;} */
-    public static final Rop OR_CONST_INT =
-        new Rop(RegOps.OR, Type.INT, StdTypeList.INT, "or-const-int");
+  /** {@code r,x,c: int :: r = x | c;} */
+  public static final Rop OR_CONST_INT =
+      new Rop(RegOps.OR, Type.INT, StdTypeList.INT, "or-const-int");
 
-    /** {@code r,x,c: long :: r = x | c;} */
-    public static final Rop OR_CONST_LONG =
-        new Rop(RegOps.OR, Type.LONG, StdTypeList.LONG, "or-const-long");
+  /** {@code r,x,c: long :: r = x | c;} */
+  public static final Rop OR_CONST_LONG =
+      new Rop(RegOps.OR, Type.LONG, StdTypeList.LONG, "or-const-long");
 
-    /** {@code r,x,c: int :: r = x ^ c;} */
-    public static final Rop XOR_CONST_INT =
-        new Rop(RegOps.XOR, Type.INT, StdTypeList.INT, "xor-const-int");
+  /** {@code r,x,c: int :: r = x ^ c;} */
+  public static final Rop XOR_CONST_INT =
+      new Rop(RegOps.XOR, Type.INT, StdTypeList.INT, "xor-const-int");
 
-    /** {@code r,x,c: long :: r = x ^ c;} */
-    public static final Rop XOR_CONST_LONG =
-        new Rop(RegOps.XOR, Type.LONG, StdTypeList.LONG, "xor-const-long");
+  /** {@code r,x,c: long :: r = x ^ c;} */
+  public static final Rop XOR_CONST_LONG =
+      new Rop(RegOps.XOR, Type.LONG, StdTypeList.LONG, "xor-const-long");
 
-    /** {@code r,x,c: int :: r = x << c;} */
-    public static final Rop SHL_CONST_INT =
-        new Rop(RegOps.SHL, Type.INT, StdTypeList.INT, "shl-const-int");
+  /** {@code r,x,c: int :: r = x << c;} */
+  public static final Rop SHL_CONST_INT =
+      new Rop(RegOps.SHL, Type.INT, StdTypeList.INT, "shl-const-int");
 
-    /** {@code r,x: long; c: int :: r = x << c;} */
-    public static final Rop SHL_CONST_LONG =
-        new Rop(RegOps.SHL, Type.LONG, StdTypeList.INT, "shl-const-long");
+  /** {@code r,x: long; c: int :: r = x << c;} */
+  public static final Rop SHL_CONST_LONG =
+      new Rop(RegOps.SHL, Type.LONG, StdTypeList.INT, "shl-const-long");
 
-    /** {@code r,x,c: int :: r = x >> c;} */
-    public static final Rop SHR_CONST_INT =
-        new Rop(RegOps.SHR, Type.INT, StdTypeList.INT, "shr-const-int");
+  /** {@code r,x,c: int :: r = x >> c;} */
+  public static final Rop SHR_CONST_INT =
+      new Rop(RegOps.SHR, Type.INT, StdTypeList.INT, "shr-const-int");
 
-    /** {@code r,x: long; c: int :: r = x >> c;} */
-    public static final Rop SHR_CONST_LONG =
-        new Rop(RegOps.SHR, Type.LONG, StdTypeList.INT, "shr-const-long");
+  /** {@code r,x: long; c: int :: r = x >> c;} */
+  public static final Rop SHR_CONST_LONG =
+      new Rop(RegOps.SHR, Type.LONG, StdTypeList.INT, "shr-const-long");
 
-    /** {@code r,x,c: int :: r = x >>> c;} */
-    public static final Rop USHR_CONST_INT =
-        new Rop(RegOps.USHR, Type.INT, StdTypeList.INT, "ushr-const-int");
+  /** {@code r,x,c: int :: r = x >>> c;} */
+  public static final Rop USHR_CONST_INT =
+      new Rop(RegOps.USHR, Type.INT, StdTypeList.INT, "ushr-const-int");
 
-    /** {@code r,x: long; c: int :: r = x >>> c;} */
-    public static final Rop USHR_CONST_LONG =
-        new Rop(RegOps.USHR, Type.LONG, StdTypeList.INT, "ushr-const-long");
+  /** {@code r,x: long; c: int :: r = x >>> c;} */
+  public static final Rop USHR_CONST_LONG =
+      new Rop(RegOps.USHR, Type.LONG, StdTypeList.INT, "ushr-const-long");
 
-    /** {@code r: int; x,y: long :: r = cmp(x, y);} */
-    public static final Rop CMPL_LONG =
-        new Rop(RegOps.CMPL, Type.INT, StdTypeList.LONG_LONG, "cmpl-long");
+  /** {@code r: int; x,y: long :: r = cmp(x, y);} */
+  public static final Rop CMPL_LONG =
+      new Rop(RegOps.CMPL, Type.INT, StdTypeList.LONG_LONG, "cmpl-long");
 
-    /** {@code r: int; x,y: float :: r = cmpl(x, y);} */
-    public static final Rop CMPL_FLOAT =
-        new Rop(RegOps.CMPL, Type.INT, StdTypeList.FLOAT_FLOAT, "cmpl-float");
+  /** {@code r: int; x,y: float :: r = cmpl(x, y);} */
+  public static final Rop CMPL_FLOAT =
+      new Rop(RegOps.CMPL, Type.INT, StdTypeList.FLOAT_FLOAT, "cmpl-float");
 
-    /** {@code r: int; x,y: double :: r = cmpl(x, y);} */
-    public static final Rop CMPL_DOUBLE =
-        new Rop(RegOps.CMPL, Type.INT, StdTypeList.DOUBLE_DOUBLE,
-                "cmpl-double");
+  /** {@code r: int; x,y: double :: r = cmpl(x, y);} */
+  public static final Rop CMPL_DOUBLE =
+      new Rop(RegOps.CMPL, Type.INT, StdTypeList.DOUBLE_DOUBLE, "cmpl-double");
 
-    /** {@code r: int; x,y: float :: r = cmpg(x, y);} */
-    public static final Rop CMPG_FLOAT =
-        new Rop(RegOps.CMPG, Type.INT, StdTypeList.FLOAT_FLOAT, "cmpg-float");
+  /** {@code r: int; x,y: float :: r = cmpg(x, y);} */
+  public static final Rop CMPG_FLOAT =
+      new Rop(RegOps.CMPG, Type.INT, StdTypeList.FLOAT_FLOAT, "cmpg-float");
 
-    /** {@code r: int; x,y: double :: r = cmpg(x, y);} */
-    public static final Rop CMPG_DOUBLE =
-        new Rop(RegOps.CMPG, Type.INT, StdTypeList.DOUBLE_DOUBLE,
-                "cmpg-double");
+  /** {@code r: int; x,y: double :: r = cmpg(x, y);} */
+  public static final Rop CMPG_DOUBLE =
+      new Rop(RegOps.CMPG, Type.INT, StdTypeList.DOUBLE_DOUBLE, "cmpg-double");
 
-    /** {@code r: int; x: long :: r = (int) x} */
-    public static final Rop CONV_L2I =
-        new Rop(RegOps.CONV, Type.INT, StdTypeList.LONG, "conv-l2i");
+  /** {@code r: int; x: long :: r = (int) x} */
+  public static final Rop CONV_L2I = new Rop(RegOps.CONV, Type.INT, StdTypeList.LONG, "conv-l2i");
 
-    /** {@code r: int; x: float :: r = (int) x} */
-    public static final Rop CONV_F2I =
-        new Rop(RegOps.CONV, Type.INT, StdTypeList.FLOAT, "conv-f2i");
+  /** {@code r: int; x: float :: r = (int) x} */
+  public static final Rop CONV_F2I = new Rop(RegOps.CONV, Type.INT, StdTypeList.FLOAT, "conv-f2i");
 
-    /** {@code r: int; x: double :: r = (int) x} */
-    public static final Rop CONV_D2I =
-        new Rop(RegOps.CONV, Type.INT, StdTypeList.DOUBLE, "conv-d2i");
+  /** {@code r: int; x: double :: r = (int) x} */
+  public static final Rop CONV_D2I = new Rop(RegOps.CONV, Type.INT, StdTypeList.DOUBLE, "conv-d2i");
 
-    /** {@code r: long; x: int :: r = (long) x} */
-    public static final Rop CONV_I2L =
-        new Rop(RegOps.CONV, Type.LONG, StdTypeList.INT, "conv-i2l");
+  /** {@code r: long; x: int :: r = (long) x} */
+  public static final Rop CONV_I2L = new Rop(RegOps.CONV, Type.LONG, StdTypeList.INT, "conv-i2l");
 
-    /** {@code r: long; x: float :: r = (long) x} */
-    public static final Rop CONV_F2L =
-        new Rop(RegOps.CONV, Type.LONG, StdTypeList.FLOAT, "conv-f2l");
+  /** {@code r: long; x: float :: r = (long) x} */
+  public static final Rop CONV_F2L = new Rop(RegOps.CONV, Type.LONG, StdTypeList.FLOAT, "conv-f2l");
 
-    /** {@code r: long; x: double :: r = (long) x} */
-    public static final Rop CONV_D2L =
-        new Rop(RegOps.CONV, Type.LONG, StdTypeList.DOUBLE, "conv-d2l");
+  /** {@code r: long; x: double :: r = (long) x} */
+  public static final Rop CONV_D2L =
+      new Rop(RegOps.CONV, Type.LONG, StdTypeList.DOUBLE, "conv-d2l");
 
-    /** {@code r: float; x: int :: r = (float) x} */
-    public static final Rop CONV_I2F =
-        new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.INT, "conv-i2f");
+  /** {@code r: float; x: int :: r = (float) x} */
+  public static final Rop CONV_I2F = new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.INT, "conv-i2f");
 
-    /** {@code r: float; x: long :: r = (float) x} */
-    public static final Rop CONV_L2F =
-        new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.LONG, "conv-l2f");
+  /** {@code r: float; x: long :: r = (float) x} */
+  public static final Rop CONV_L2F = new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.LONG, "conv-l2f");
 
-    /** {@code r: float; x: double :: r = (float) x} */
-    public static final Rop CONV_D2F =
-        new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.DOUBLE, "conv-d2f");
+  /** {@code r: float; x: double :: r = (float) x} */
+  public static final Rop CONV_D2F =
+      new Rop(RegOps.CONV, Type.FLOAT, StdTypeList.DOUBLE, "conv-d2f");
 
-    /** {@code r: double; x: int :: r = (double) x} */
-    public static final Rop CONV_I2D =
-        new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.INT, "conv-i2d");
+  /** {@code r: double; x: int :: r = (double) x} */
+  public static final Rop CONV_I2D = new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.INT, "conv-i2d");
 
-    /** {@code r: double; x: long :: r = (double) x} */
-    public static final Rop CONV_L2D =
-        new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.LONG, "conv-l2d");
+  /** {@code r: double; x: long :: r = (double) x} */
+  public static final Rop CONV_L2D =
+      new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.LONG, "conv-l2d");
 
-    /** {@code r: double; x: float :: r = (double) x} */
-    public static final Rop CONV_F2D =
-        new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.FLOAT, "conv-f2d");
+  /** {@code r: double; x: float :: r = (double) x} */
+  public static final Rop CONV_F2D =
+      new Rop(RegOps.CONV, Type.DOUBLE, StdTypeList.FLOAT, "conv-f2d");
 
-    /**
-     * {@code r,x: int :: r = (x << 24) >> 24} (Java-style
-     * convert int to byte)
-     */
-    public static final Rop TO_BYTE =
-        new Rop(RegOps.TO_BYTE, Type.INT, StdTypeList.INT, "to-byte");
+  /**
+   * {@code r,x: int :: r = (x << 24) >> 24} (Java-style
+   * convert int to byte)
+   */
+  public static final Rop TO_BYTE = new Rop(RegOps.TO_BYTE, Type.INT, StdTypeList.INT, "to-byte");
 
-    /**
-     * {@code r,x: int :: r = x & 0xffff} (Java-style
-     * convert int to char)
-     */
-    public static final Rop TO_CHAR =
-        new Rop(RegOps.TO_CHAR, Type.INT, StdTypeList.INT, "to-char");
+  /**
+   * {@code r,x: int :: r = x & 0xffff} (Java-style
+   * convert int to char)
+   */
+  public static final Rop TO_CHAR = new Rop(RegOps.TO_CHAR, Type.INT, StdTypeList.INT, "to-char");
 
-    /**
-     * {@code r,x: int :: r = (x << 16) >> 16} (Java-style
-     * convert int to short)
-     */
-    public static final Rop TO_SHORT =
-        new Rop(RegOps.TO_SHORT, Type.INT, StdTypeList.INT, "to-short");
+  /**
+   * {@code r,x: int :: r = (x << 16) >> 16} (Java-style
+   * convert int to short)
+   */
+  public static final Rop TO_SHORT =
+      new Rop(RegOps.TO_SHORT, Type.INT, StdTypeList.INT, "to-short");
 
-    /** {@code return void} */
-    public static final Rop RETURN_VOID =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.EMPTY, Rop.BRANCH_RETURN,
-                "return-void");
+  /** {@code return void} */
+  public static final Rop RETURN_VOID =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.EMPTY, Rop.BRANCH_RETURN, "return-void");
 
-    /** {@code x: int; return x} */
-    public static final Rop RETURN_INT =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.INT, Rop.BRANCH_RETURN,
-                "return-int");
+  /** {@code x: int; return x} */
+  public static final Rop RETURN_INT =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.INT, Rop.BRANCH_RETURN, "return-int");
 
-    /** {@code x: long; return x} */
-    public static final Rop RETURN_LONG =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.LONG, Rop.BRANCH_RETURN,
-                "return-long");
+  /** {@code x: long; return x} */
+  public static final Rop RETURN_LONG =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.LONG, Rop.BRANCH_RETURN, "return-long");
 
-    /** {@code x: float; return x} */
-    public static final Rop RETURN_FLOAT =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.FLOAT, Rop.BRANCH_RETURN,
-                "return-float");
+  /** {@code x: float; return x} */
+  public static final Rop RETURN_FLOAT =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.FLOAT, Rop.BRANCH_RETURN, "return-float");
 
-    /** {@code x: double; return x} */
-    public static final Rop RETURN_DOUBLE =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.DOUBLE,
-                Rop.BRANCH_RETURN, "return-double");
+  /** {@code x: double; return x} */
+  public static final Rop RETURN_DOUBLE =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.DOUBLE, Rop.BRANCH_RETURN, "return-double");
 
-    /** {@code x: Object; return x} */
-    public static final Rop RETURN_OBJECT =
-        new Rop(RegOps.RETURN, Type.VOID, StdTypeList.OBJECT,
-                Rop.BRANCH_RETURN, "return-object");
+  /** {@code x: Object; return x} */
+  public static final Rop RETURN_OBJECT =
+      new Rop(RegOps.RETURN, Type.VOID, StdTypeList.OBJECT, Rop.BRANCH_RETURN, "return-object");
 
-    /** {@code T: any type; r: int; x: T[]; :: r = x.length} */
-    public static final Rop ARRAY_LENGTH =
-        new Rop(RegOps.ARRAY_LENGTH, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "array-length");
+  /** {@code T: any type; r: int; x: T[]; :: r = x.length} */
+  public static final Rop ARRAY_LENGTH = new Rop(RegOps.ARRAY_LENGTH, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "array-length");
 
-    /** {@code x: Throwable :: throw(x)} */
-    public static final Rop THROW =
-        new Rop(RegOps.THROW, Type.VOID, StdTypeList.THROWABLE,
-                StdTypeList.THROWABLE, "throw");
+  /** {@code x: Throwable :: throw(x)} */
+  public static final Rop THROW =
+      new Rop(RegOps.THROW, Type.VOID, StdTypeList.THROWABLE, StdTypeList.THROWABLE, "throw");
 
-    /** {@code x: Object :: monitorenter(x)} */
-    public static final Rop MONITOR_ENTER =
-        new Rop(RegOps.MONITOR_ENTER, Type.VOID, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "monitor-enter");
+  /** {@code x: Object :: monitorenter(x)} */
+  public static final Rop MONITOR_ENTER = new Rop(RegOps.MONITOR_ENTER, Type.VOID,
+      StdTypeList.OBJECT, Exceptions.LIST_Error_NullPointerException, "monitor-enter");
 
-    /** {@code x: Object :: monitorexit(x)} */
-    public static final Rop MONITOR_EXIT =
-        new Rop(RegOps.MONITOR_EXIT, Type.VOID, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_Null_IllegalMonitorStateException,
-                "monitor-exit");
+  /** {@code x: Object :: monitorexit(x)} */
+  public static final Rop MONITOR_EXIT = new Rop(RegOps.MONITOR_EXIT, Type.VOID, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_Null_IllegalMonitorStateException, "monitor-exit");
 
-    /** {@code r,y: int; x: int[] :: r = x[y]} */
-    public static final Rop AGET_INT =
-        new Rop(RegOps.AGET, Type.INT, StdTypeList.INTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-int");
+  /** {@code r,y: int; x: int[] :: r = x[y]} */
+  public static final Rop AGET_INT = new Rop(RegOps.AGET, Type.INT, StdTypeList.INTARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-int");
 
-    /** {@code r: long; x: long[]; y: int :: r = x[y]} */
-    public static final Rop AGET_LONG =
-        new Rop(RegOps.AGET, Type.LONG, StdTypeList.LONGARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-long");
+  /** {@code r: long; x: long[]; y: int :: r = x[y]} */
+  public static final Rop AGET_LONG = new Rop(RegOps.AGET, Type.LONG, StdTypeList.LONGARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-long");
 
-    /** {@code r: float; x: float[]; y: int :: r = x[y]} */
-    public static final Rop AGET_FLOAT =
-        new Rop(RegOps.AGET, Type.FLOAT, StdTypeList.FLOATARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-float");
+  /** {@code r: float; x: float[]; y: int :: r = x[y]} */
+  public static final Rop AGET_FLOAT = new Rop(RegOps.AGET, Type.FLOAT, StdTypeList.FLOATARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-float");
 
-    /** {@code r: double; x: double[]; y: int :: r = x[y]} */
-    public static final Rop AGET_DOUBLE =
-        new Rop(RegOps.AGET, Type.DOUBLE, StdTypeList.DOUBLEARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-double");
+  /** {@code r: double; x: double[]; y: int :: r = x[y]} */
+  public static final Rop AGET_DOUBLE = new Rop(RegOps.AGET, Type.DOUBLE, StdTypeList.DOUBLEARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-double");
 
-    /** {@code r: Object; x: Object[]; y: int :: r = x[y]} */
-    public static final Rop AGET_OBJECT =
-        new Rop(RegOps.AGET, Type.OBJECT, StdTypeList.OBJECTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-object");
+  /** {@code r: Object; x: Object[]; y: int :: r = x[y]} */
+  public static final Rop AGET_OBJECT = new Rop(RegOps.AGET, Type.OBJECT, StdTypeList.OBJECTARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-object");
 
-    /** {@code r: boolean; x: boolean[]; y: int :: r = x[y]} */
-    public static final Rop AGET_BOOLEAN =
-        new Rop(RegOps.AGET, Type.INT, StdTypeList.BOOLEANARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-boolean");
+  /** {@code r: boolean; x: boolean[]; y: int :: r = x[y]} */
+  public static final Rop AGET_BOOLEAN = new Rop(RegOps.AGET, Type.INT, StdTypeList.BOOLEANARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-boolean");
 
-    /** {@code r: byte; x: byte[]; y: int :: r = x[y]} */
-    public static final Rop AGET_BYTE =
-        new Rop(RegOps.AGET, Type.INT, StdTypeList.BYTEARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-byte");
+  /** {@code r: byte; x: byte[]; y: int :: r = x[y]} */
+  public static final Rop AGET_BYTE = new Rop(RegOps.AGET, Type.INT, StdTypeList.BYTEARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-byte");
 
-    /** {@code r: char; x: char[]; y: int :: r = x[y]} */
-    public static final Rop AGET_CHAR =
-        new Rop(RegOps.AGET, Type.INT, StdTypeList.CHARARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-char");
+  /** {@code r: char; x: char[]; y: int :: r = x[y]} */
+  public static final Rop AGET_CHAR = new Rop(RegOps.AGET, Type.INT, StdTypeList.CHARARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-char");
 
-    /** {@code r: short; x: short[]; y: int :: r = x[y]} */
-    public static final Rop AGET_SHORT =
-        new Rop(RegOps.AGET, Type.INT, StdTypeList.SHORTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aget-short");
+  /** {@code r: short; x: short[]; y: int :: r = x[y]} */
+  public static final Rop AGET_SHORT = new Rop(RegOps.AGET, Type.INT, StdTypeList.SHORTARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aget-short");
 
-    /** {@code x,z: int; y: int[] :: y[z] = x} */
-    public static final Rop APUT_INT =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_INTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aput-int");
+  /** {@code x,z: int; y: int[] :: y[z] = x} */
+  public static final Rop APUT_INT = new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_INTARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aput-int");
 
-    /** {@code x: long; y: long[]; z: int :: y[z] = x} */
-    public static final Rop APUT_LONG =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.LONG_LONGARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aput-long");
+  /** {@code x: long; y: long[]; z: int :: y[z] = x} */
+  public static final Rop APUT_LONG = new Rop(RegOps.APUT, Type.VOID, StdTypeList.LONG_LONGARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds, "aput-long");
 
-    /** {@code x: float; y: float[]; z: int :: y[z] = x} */
-    public static final Rop APUT_FLOAT =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.FLOAT_FLOATARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aput-float");
+  /** {@code x: float; y: float[]; z: int :: y[z] = x} */
+  public static final Rop APUT_FLOAT = new Rop(RegOps.APUT, Type.VOID,
+      StdTypeList.FLOAT_FLOATARR_INT, Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
+      "aput-float");
 
-    /** {@code x: double; y: double[]; z: int :: y[z] = x} */
-    public static final Rop APUT_DOUBLE =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.DOUBLE_DOUBLEARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
-                "aput-double");
+  /** {@code x: double; y: double[]; z: int :: y[z] = x} */
+  public static final Rop APUT_DOUBLE = new Rop(RegOps.APUT, Type.VOID,
+      StdTypeList.DOUBLE_DOUBLEARR_INT, Exceptions.LIST_Error_Null_ArrayIndexOutOfBounds,
+      "aput-double");
 
-    /** {@code x: Object; y: Object[]; z: int :: y[z] = x} */
-    public static final Rop APUT_OBJECT =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.OBJECT_OBJECTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore,
-                "aput-object");
+  /** {@code x: Object; y: Object[]; z: int :: y[z] = x} */
+  public static final Rop APUT_OBJECT = new Rop(RegOps.APUT, Type.VOID,
+      StdTypeList.OBJECT_OBJECTARR_INT, Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore,
+      "aput-object");
 
-    /** {@code x: boolean; y: boolean[]; z: int :: y[z] = x} */
-    public static final Rop APUT_BOOLEAN =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_BOOLEANARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore,
-                "aput-boolean");
+  /** {@code x: boolean; y: boolean[]; z: int :: y[z] = x} */
+  public static final Rop APUT_BOOLEAN = new Rop(RegOps.APUT, Type.VOID,
+      StdTypeList.INT_BOOLEANARR_INT, Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore,
+      "aput-boolean");
 
-    /** {@code x: byte; y: byte[]; z: int :: y[z] = x} */
-    public static final Rop APUT_BYTE =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_BYTEARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore, "aput-byte");
+  /** {@code x: byte; y: byte[]; z: int :: y[z] = x} */
+  public static final Rop APUT_BYTE = new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_BYTEARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore, "aput-byte");
 
-    /** {@code x: char; y: char[]; z: int :: y[z] = x} */
-    public static final Rop APUT_CHAR =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_CHARARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore, "aput-char");
+  /** {@code x: char; y: char[]; z: int :: y[z] = x} */
+  public static final Rop APUT_CHAR = new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_CHARARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore, "aput-char");
 
-    /** {@code x: short; y: short[]; z: int :: y[z] = x} */
-    public static final Rop APUT_SHORT =
-        new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_SHORTARR_INT,
-                Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore,
-                "aput-short");
+  /** {@code x: short; y: short[]; z: int :: y[z] = x} */
+  public static final Rop APUT_SHORT = new Rop(RegOps.APUT, Type.VOID, StdTypeList.INT_SHORTARR_INT,
+      Exceptions.LIST_Error_Null_ArrayIndex_ArrayStore, "aput-short");
 
-    /**
-     * {@code T: any non-array object type :: r =
-     * alloc(T)} (allocate heap space for an object)
-     */
-    public static final Rop NEW_INSTANCE =
-        new Rop(RegOps.NEW_INSTANCE, Type.OBJECT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "new-instance");
+  /**
+   * {@code T: any non-array object type :: r =
+   * alloc(T)} (allocate heap space for an object)
+   */
+  public static final Rop NEW_INSTANCE = new Rop(RegOps.NEW_INSTANCE, Type.OBJECT,
+      StdTypeList.EMPTY, Exceptions.LIST_Error, "new-instance");
 
-    /** {@code r: int[]; x: int :: r = new int[x]} */
-    public static final Rop NEW_ARRAY_INT =
-        new Rop(RegOps.NEW_ARRAY, Type.INT_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-int");
+  /** {@code r: int[]; x: int :: r = new int[x]} */
+  public static final Rop NEW_ARRAY_INT = new Rop(RegOps.NEW_ARRAY, Type.INT_ARRAY, StdTypeList.INT,
+      Exceptions.LIST_Error_NegativeArraySizeException, "new-array-int");
 
-    /** {@code r: long[]; x: int :: r = new long[x]} */
-    public static final Rop NEW_ARRAY_LONG =
-        new Rop(RegOps.NEW_ARRAY, Type.LONG_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-long");
+  /** {@code r: long[]; x: int :: r = new long[x]} */
+  public static final Rop NEW_ARRAY_LONG = new Rop(RegOps.NEW_ARRAY, Type.LONG_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-long");
 
-    /** {@code r: float[]; x: int :: r = new float[x]} */
-    public static final Rop NEW_ARRAY_FLOAT =
-        new Rop(RegOps.NEW_ARRAY, Type.FLOAT_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-float");
+  /** {@code r: float[]; x: int :: r = new float[x]} */
+  public static final Rop NEW_ARRAY_FLOAT = new Rop(RegOps.NEW_ARRAY, Type.FLOAT_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-float");
 
-    /** {@code r: double[]; x: int :: r = new double[x]} */
-    public static final Rop NEW_ARRAY_DOUBLE =
-        new Rop(RegOps.NEW_ARRAY, Type.DOUBLE_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-double");
+  /** {@code r: double[]; x: int :: r = new double[x]} */
+  public static final Rop NEW_ARRAY_DOUBLE = new Rop(RegOps.NEW_ARRAY, Type.DOUBLE_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-double");
 
-    /** {@code r: boolean[]; x: int :: r = new boolean[x]} */
-    public static final Rop NEW_ARRAY_BOOLEAN =
-        new Rop(RegOps.NEW_ARRAY, Type.BOOLEAN_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-boolean");
+  /** {@code r: boolean[]; x: int :: r = new boolean[x]} */
+  public static final Rop NEW_ARRAY_BOOLEAN = new Rop(RegOps.NEW_ARRAY, Type.BOOLEAN_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-boolean");
 
-    /** {@code r: byte[]; x: int :: r = new byte[x]} */
-    public static final Rop NEW_ARRAY_BYTE =
-        new Rop(RegOps.NEW_ARRAY, Type.BYTE_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-byte");
+  /** {@code r: byte[]; x: int :: r = new byte[x]} */
+  public static final Rop NEW_ARRAY_BYTE = new Rop(RegOps.NEW_ARRAY, Type.BYTE_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-byte");
 
-    /** {@code r: char[]; x: int :: r = new char[x]} */
-    public static final Rop NEW_ARRAY_CHAR =
-        new Rop(RegOps.NEW_ARRAY, Type.CHAR_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-char");
+  /** {@code r: char[]; x: int :: r = new char[x]} */
+  public static final Rop NEW_ARRAY_CHAR = new Rop(RegOps.NEW_ARRAY, Type.CHAR_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-char");
 
-    /** {@code r: short[]; x: int :: r = new short[x]} */
-    public static final Rop NEW_ARRAY_SHORT =
-        new Rop(RegOps.NEW_ARRAY, Type.SHORT_ARRAY, StdTypeList.INT,
-                Exceptions.LIST_Error_NegativeArraySizeException,
-                "new-array-short");
+  /** {@code r: short[]; x: int :: r = new short[x]} */
+  public static final Rop NEW_ARRAY_SHORT = new Rop(RegOps.NEW_ARRAY, Type.SHORT_ARRAY,
+      StdTypeList.INT, Exceptions.LIST_Error_NegativeArraySizeException, "new-array-short");
 
-    /**
-     * {@code T: any non-array object type; x: Object :: (T) x} (can
-     * throw {@code ClassCastException})
-     */
-    public static final Rop CHECK_CAST =
-        new Rop(RegOps.CHECK_CAST, Type.VOID, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_ClassCastException, "check-cast");
+  /**
+   * {@code T: any non-array object type; x: Object :: (T) x} (can
+   * throw {@code ClassCastException})
+   */
+  public static final Rop CHECK_CAST = new Rop(RegOps.CHECK_CAST, Type.VOID, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_ClassCastException, "check-cast");
 
-    /**
-     * {@code T: any non-array object type; x: Object :: x instanceof
-     * T}. Note: This is listed as throwing {@code Error}
-     * explicitly because the op <i>can</i> throw, but there are no
-     * other predefined exceptions for it.
-     */
-    public static final Rop INSTANCE_OF =
-        new Rop(RegOps.INSTANCE_OF, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error, "instance-of");
+  /**
+   * {@code T: any non-array object type; x: Object :: x instanceof
+   * T}. Note: This is listed as throwing {@code Error}
+   * explicitly because the op <i>can</i> throw, but there are no
+   * other predefined exceptions for it.
+   */
+  public static final Rop INSTANCE_OF = new Rop(RegOps.INSTANCE_OF, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error, "instance-of");
 
-    /**
-     * {@code r: int; x: Object; f: instance field spec of
-     * type int :: r = x.f}
-     */
-    public static final Rop GET_FIELD_INT =
-        new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "get-field-int");
+  /**
+   * {@code r: int; x: Object; f: instance field spec of
+   * type int :: r = x.f}
+   */
+  public static final Rop GET_FIELD_INT = new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "get-field-int");
 
-    /**
-     * {@code r: long; x: Object; f: instance field spec of
-     * type long :: r = x.f}
-     */
-    public static final Rop GET_FIELD_LONG =
-        new Rop(RegOps.GET_FIELD, Type.LONG, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "get-field-long");
+  /**
+   * {@code r: long; x: Object; f: instance field spec of
+   * type long :: r = x.f}
+   */
+  public static final Rop GET_FIELD_LONG = new Rop(RegOps.GET_FIELD, Type.LONG, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "get-field-long");
 
-    /**
-     * {@code r: float; x: Object; f: instance field spec of
-     * type float :: r = x.f}
-     */
-    public static final Rop GET_FIELD_FLOAT =
-        new Rop(RegOps.GET_FIELD, Type.FLOAT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-float");
+  /**
+   * {@code r: float; x: Object; f: instance field spec of
+   * type float :: r = x.f}
+   */
+  public static final Rop GET_FIELD_FLOAT = new Rop(RegOps.GET_FIELD, Type.FLOAT,
+      StdTypeList.OBJECT, Exceptions.LIST_Error_NullPointerException, "get-field-float");
 
-    /**
-     * {@code r: double; x: Object; f: instance field spec of
-     * type double :: r = x.f}
-     */
-    public static final Rop GET_FIELD_DOUBLE =
-        new Rop(RegOps.GET_FIELD, Type.DOUBLE, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-double");
+  /**
+   * {@code r: double; x: Object; f: instance field spec of
+   * type double :: r = x.f}
+   */
+  public static final Rop GET_FIELD_DOUBLE = new Rop(RegOps.GET_FIELD, Type.DOUBLE,
+      StdTypeList.OBJECT, Exceptions.LIST_Error_NullPointerException, "get-field-double");
 
-    /**
-     * {@code r: Object; x: Object; f: instance field spec of
-     * type Object :: r = x.f}
-     */
-    public static final Rop GET_FIELD_OBJECT =
-        new Rop(RegOps.GET_FIELD, Type.OBJECT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-object");
+  /**
+   * {@code r: Object; x: Object; f: instance field spec of
+   * type Object :: r = x.f}
+   */
+  public static final Rop GET_FIELD_OBJECT = new Rop(RegOps.GET_FIELD, Type.OBJECT,
+      StdTypeList.OBJECT, Exceptions.LIST_Error_NullPointerException, "get-field-object");
 
-    /**
-     * {@code r: boolean; x: Object; f: instance field spec of
-     * type boolean :: r = x.f}
-     */
-    public static final Rop GET_FIELD_BOOLEAN =
-        new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-boolean");
+  /**
+   * {@code r: boolean; x: Object; f: instance field spec of
+   * type boolean :: r = x.f}
+   */
+  public static final Rop GET_FIELD_BOOLEAN = new Rop(RegOps.GET_FIELD, Type.INT,
+      StdTypeList.OBJECT, Exceptions.LIST_Error_NullPointerException, "get-field-boolean");
 
-    /**
-     * {@code r: byte; x: Object; f: instance field spec of
-     * type byte :: r = x.f}
-     */
-    public static final Rop GET_FIELD_BYTE =
-        new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-byte");
+  /**
+   * {@code r: byte; x: Object; f: instance field spec of
+   * type byte :: r = x.f}
+   */
+  public static final Rop GET_FIELD_BYTE = new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "get-field-byte");
 
-    /**
-     * {@code r: char; x: Object; f: instance field spec of
-     * type char :: r = x.f}
-     */
-    public static final Rop GET_FIELD_CHAR =
-        new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-char");
+  /**
+   * {@code r: char; x: Object; f: instance field spec of
+   * type char :: r = x.f}
+   */
+  public static final Rop GET_FIELD_CHAR = new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "get-field-char");
 
-    /**
-     * {@code r: short; x: Object; f: instance field spec of
-     * type short :: r = x.f}
-     */
-    public static final Rop GET_FIELD_SHORT =
-        new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "get-field-short");
+  /**
+   * {@code r: short; x: Object; f: instance field spec of
+   * type short :: r = x.f}
+   */
+  public static final Rop GET_FIELD_SHORT = new Rop(RegOps.GET_FIELD, Type.INT, StdTypeList.OBJECT,
+      Exceptions.LIST_Error_NullPointerException, "get-field-short");
 
-    /** {@code r: int; f: static field spec of type int :: r = f} */
-    public static final Rop GET_STATIC_INT =
-        new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-static-int");
+  /** {@code r: int; f: static field spec of type int :: r = f} */
+  public static final Rop GET_STATIC_INT = new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
+      Exceptions.LIST_Error, "get-static-int");
 
-    /** {@code r: long; f: static field spec of type long :: r = f} */
-    public static final Rop GET_STATIC_LONG =
-        new Rop(RegOps.GET_STATIC, Type.LONG, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-static-long");
+  /** {@code r: long; f: static field spec of type long :: r = f} */
+  public static final Rop GET_STATIC_LONG = new Rop(RegOps.GET_STATIC, Type.LONG, StdTypeList.EMPTY,
+      Exceptions.LIST_Error, "get-static-long");
 
-    /** {@code r: float; f: static field spec of type float :: r = f} */
-    public static final Rop GET_STATIC_FLOAT =
-        new Rop(RegOps.GET_STATIC, Type.FLOAT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-static-float");
+  /** {@code r: float; f: static field spec of type float :: r = f} */
+  public static final Rop GET_STATIC_FLOAT = new Rop(RegOps.GET_STATIC, Type.FLOAT,
+      StdTypeList.EMPTY, Exceptions.LIST_Error, "get-static-float");
 
-    /** {@code r: double; f: static field spec of type double :: r = f} */
-    public static final Rop GET_STATIC_DOUBLE =
-        new Rop(RegOps.GET_STATIC, Type.DOUBLE, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-static-double");
+  /** {@code r: double; f: static field spec of type double :: r = f} */
+  public static final Rop GET_STATIC_DOUBLE = new Rop(RegOps.GET_STATIC, Type.DOUBLE,
+      StdTypeList.EMPTY, Exceptions.LIST_Error, "get-static-double");
 
-    /** {@code r: Object; f: static field spec of type Object :: r = f} */
-    public static final Rop GET_STATIC_OBJECT =
-        new Rop(RegOps.GET_STATIC, Type.OBJECT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-static-object");
+  /** {@code r: Object; f: static field spec of type Object :: r = f} */
+  public static final Rop GET_STATIC_OBJECT = new Rop(RegOps.GET_STATIC, Type.OBJECT,
+      StdTypeList.EMPTY, Exceptions.LIST_Error, "get-static-object");
 
-    /** {@code r: boolean; f: static field spec of type boolean :: r = f} */
-    public static final Rop GET_STATIC_BOOLEAN =
-        new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-field-boolean");
+  /** {@code r: boolean; f: static field spec of type boolean :: r = f} */
+  public static final Rop GET_STATIC_BOOLEAN = new Rop(RegOps.GET_STATIC, Type.INT,
+      StdTypeList.EMPTY, Exceptions.LIST_Error, "get-field-boolean");
 
-    /** {@code r: byte; f: static field spec of type byte :: r = f} */
-    public static final Rop GET_STATIC_BYTE =
-        new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-field-byte");
+  /** {@code r: byte; f: static field spec of type byte :: r = f} */
+  public static final Rop GET_STATIC_BYTE = new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
+      Exceptions.LIST_Error, "get-field-byte");
 
-    /** {@code r: char; f: static field spec of type char :: r = f} */
-    public static final Rop GET_STATIC_CHAR =
-        new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-field-char");
+  /** {@code r: char; f: static field spec of type char :: r = f} */
+  public static final Rop GET_STATIC_CHAR = new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
+      Exceptions.LIST_Error, "get-field-char");
 
-    /** {@code r: short; f: static field spec of type short :: r = f} */
-    public static final Rop GET_STATIC_SHORT =
-        new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
-                Exceptions.LIST_Error, "get-field-short");
+  /** {@code r: short; f: static field spec of type short :: r = f} */
+  public static final Rop GET_STATIC_SHORT = new Rop(RegOps.GET_STATIC, Type.INT, StdTypeList.EMPTY,
+      Exceptions.LIST_Error, "get-field-short");
 
-    /**
-     * {@code x: int; y: Object; f: instance field spec of type
-     * int :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_INT =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.INT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "put-field-int");
+  /**
+   * {@code x: int; y: Object; f: instance field spec of type
+   * int :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_INT = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.INT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-int");
 
-    /**
-     * {@code x: long; y: Object; f: instance field spec of type
-     * long :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_LONG =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.LONG_OBJECT,
-                Exceptions.LIST_Error_NullPointerException, "put-field-long");
+  /**
+   * {@code x: long; y: Object; f: instance field spec of type
+   * long :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_LONG = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.LONG_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-long");
 
-    /**
-     * {@code x: float; y: Object; f: instance field spec of type
-     * float :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_FLOAT =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.FLOAT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-float");
+  /**
+   * {@code x: float; y: Object; f: instance field spec of type
+   * float :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_FLOAT = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.FLOAT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-float");
 
-    /**
-     * {@code x: double; y: Object; f: instance field spec of type
-     * double :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_DOUBLE =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.DOUBLE_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-double");
+  /**
+   * {@code x: double; y: Object; f: instance field spec of type
+   * double :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_DOUBLE = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.DOUBLE_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-double");
 
-    /**
-     * {@code x: Object; y: Object; f: instance field spec of type
-     * Object :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_OBJECT =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.OBJECT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-object");
+  /**
+   * {@code x: Object; y: Object; f: instance field spec of type
+   * Object :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_OBJECT = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.OBJECT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-object");
 
-    /**
-     * {@code x: int; y: Object; f: instance field spec of type
-     * boolean :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_BOOLEAN =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.INT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-boolean");
+  /**
+   * {@code x: int; y: Object; f: instance field spec of type
+   * boolean :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_BOOLEAN = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.INT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-boolean");
 
-    /**
-     * {@code x: int; y: Object; f: instance field spec of type
-     * byte :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_BYTE =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.INT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-byte");
+  /**
+   * {@code x: int; y: Object; f: instance field spec of type
+   * byte :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_BYTE = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.INT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-byte");
 
-    /**
-     * {@code x: int; y: Object; f: instance field spec of type
-     * char :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_CHAR =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.INT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-char");
+  /**
+   * {@code x: int; y: Object; f: instance field spec of type
+   * char :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_CHAR = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.INT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-char");
 
-    /**
-     * {@code x: int; y: Object; f: instance field spec of type
-     * short :: y.f = x}
-     */
-    public static final Rop PUT_FIELD_SHORT =
-        new Rop(RegOps.PUT_FIELD, Type.VOID, StdTypeList.INT_OBJECT,
-                Exceptions.LIST_Error_NullPointerException,
-                "put-field-short");
+  /**
+   * {@code x: int; y: Object; f: instance field spec of type
+   * short :: y.f = x}
+   */
+  public static final Rop PUT_FIELD_SHORT = new Rop(RegOps.PUT_FIELD, Type.VOID,
+      StdTypeList.INT_OBJECT, Exceptions.LIST_Error_NullPointerException, "put-field-short");
 
-    /** {@code f: static field spec of type int; x: int :: f = x} */
-    public static final Rop PUT_STATIC_INT =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
-                Exceptions.LIST_Error, "put-static-int");
+  /** {@code f: static field spec of type int; x: int :: f = x} */
+  public static final Rop PUT_STATIC_INT = new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
+      Exceptions.LIST_Error, "put-static-int");
 
-    /** {@code f: static field spec of type long; x: long :: f = x} */
-    public static final Rop PUT_STATIC_LONG =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.LONG,
-                Exceptions.LIST_Error, "put-static-long");
+  /** {@code f: static field spec of type long; x: long :: f = x} */
+  public static final Rop PUT_STATIC_LONG = new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.LONG,
+      Exceptions.LIST_Error, "put-static-long");
 
-    /** {@code f: static field spec of type float; x: float :: f = x} */
-    public static final Rop PUT_STATIC_FLOAT =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.FLOAT,
-                Exceptions.LIST_Error, "put-static-float");
+  /** {@code f: static field spec of type float; x: float :: f = x} */
+  public static final Rop PUT_STATIC_FLOAT = new Rop(RegOps.PUT_STATIC, Type.VOID,
+      StdTypeList.FLOAT, Exceptions.LIST_Error, "put-static-float");
 
-    /** {@code f: static field spec of type double; x: double :: f = x} */
-    public static final Rop PUT_STATIC_DOUBLE =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.DOUBLE,
-                Exceptions.LIST_Error, "put-static-double");
+  /** {@code f: static field spec of type double; x: double :: f = x} */
+  public static final Rop PUT_STATIC_DOUBLE = new Rop(RegOps.PUT_STATIC, Type.VOID,
+      StdTypeList.DOUBLE, Exceptions.LIST_Error, "put-static-double");
 
-    /** {@code f: static field spec of type Object; x: Object :: f = x} */
-    public static final Rop PUT_STATIC_OBJECT =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.OBJECT,
-                Exceptions.LIST_Error, "put-static-object");
+  /** {@code f: static field spec of type Object; x: Object :: f = x} */
+  public static final Rop PUT_STATIC_OBJECT = new Rop(RegOps.PUT_STATIC, Type.VOID,
+      StdTypeList.OBJECT, Exceptions.LIST_Error, "put-static-object");
 
-    /**
-     * {@code f: static field spec of type boolean; x: boolean :: f =
-     * x}
-     */
-    public static final Rop PUT_STATIC_BOOLEAN =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
-                Exceptions.LIST_Error, "put-static-boolean");
+  /**
+   * {@code f: static field spec of type boolean; x: boolean :: f =
+   * x}
+   */
+  public static final Rop PUT_STATIC_BOOLEAN = new Rop(RegOps.PUT_STATIC, Type.VOID,
+      StdTypeList.INT, Exceptions.LIST_Error, "put-static-boolean");
 
-    /** {@code f: static field spec of type byte; x: byte :: f = x} */
-    public static final Rop PUT_STATIC_BYTE =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
-                Exceptions.LIST_Error, "put-static-byte");
+  /** {@code f: static field spec of type byte; x: byte :: f = x} */
+  public static final Rop PUT_STATIC_BYTE = new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
+      Exceptions.LIST_Error, "put-static-byte");
 
-    /** {@code f: static field spec of type char; x: char :: f = x} */
-    public static final Rop PUT_STATIC_CHAR =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
-                Exceptions.LIST_Error, "put-static-char");
+  /** {@code f: static field spec of type char; x: char :: f = x} */
+  public static final Rop PUT_STATIC_CHAR = new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
+      Exceptions.LIST_Error, "put-static-char");
 
-    /** {@code f: static field spec of type short; x: short :: f = x} */
-    public static final Rop PUT_STATIC_SHORT =
-        new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
-                Exceptions.LIST_Error, "put-static-short");
+  /** {@code f: static field spec of type short; x: short :: f = x} */
+  public static final Rop PUT_STATIC_SHORT = new Rop(RegOps.PUT_STATIC, Type.VOID, StdTypeList.INT,
+      Exceptions.LIST_Error, "put-static-short");
 
-    /** {@code x: Int :: local variable begins in x} */
-    public static final Rop MARK_LOCAL_INT =
-            new Rop (RegOps.MARK_LOCAL, Type.VOID,
-                    StdTypeList.INT, "mark-local-int");
+  /** {@code x: Int :: local variable begins in x} */
+  public static final Rop MARK_LOCAL_INT =
+      new Rop(RegOps.MARK_LOCAL, Type.VOID, StdTypeList.INT, "mark-local-int");
 
-    /** {@code x: Long :: local variable begins in x} */
-    public static final Rop MARK_LOCAL_LONG =
-            new Rop (RegOps.MARK_LOCAL, Type.VOID,
-                    StdTypeList.LONG, "mark-local-long");
+  /** {@code x: Long :: local variable begins in x} */
+  public static final Rop MARK_LOCAL_LONG =
+      new Rop(RegOps.MARK_LOCAL, Type.VOID, StdTypeList.LONG, "mark-local-long");
 
-    /** {@code x: Float :: local variable begins in x} */
-    public static final Rop MARK_LOCAL_FLOAT =
-            new Rop (RegOps.MARK_LOCAL, Type.VOID,
-                    StdTypeList.FLOAT, "mark-local-float");
+  /** {@code x: Float :: local variable begins in x} */
+  public static final Rop MARK_LOCAL_FLOAT =
+      new Rop(RegOps.MARK_LOCAL, Type.VOID, StdTypeList.FLOAT, "mark-local-float");
 
-    /** {@code x: Double :: local variable begins in x} */
-    public static final Rop MARK_LOCAL_DOUBLE =
-            new Rop (RegOps.MARK_LOCAL, Type.VOID,
-                    StdTypeList.DOUBLE, "mark-local-double");
+  /** {@code x: Double :: local variable begins in x} */
+  public static final Rop MARK_LOCAL_DOUBLE =
+      new Rop(RegOps.MARK_LOCAL, Type.VOID, StdTypeList.DOUBLE, "mark-local-double");
 
-    /** {@code x: Object :: local variable begins in x} */
-    public static final Rop MARK_LOCAL_OBJECT =
-            new Rop (RegOps.MARK_LOCAL, Type.VOID,
-                    StdTypeList.OBJECT, "mark-local-object");
+  /** {@code x: Object :: local variable begins in x} */
+  public static final Rop MARK_LOCAL_OBJECT =
+      new Rop(RegOps.MARK_LOCAL, Type.VOID, StdTypeList.OBJECT, "mark-local-object");
 
-    /** {@code T: Any primitive type; v0..vx: T :: {v0, ..., vx}} */
-    public static final Rop FILL_ARRAY_DATA =
-        new Rop(RegOps.FILL_ARRAY_DATA, Type.VOID, StdTypeList.EMPTY,
-                "fill-array-data");
+  /** {@code T: Any primitive type; v0..vx: T :: {v0, ..., vx}} */
+  public static final Rop FILL_ARRAY_DATA =
+      new Rop(RegOps.FILL_ARRAY_DATA, Type.VOID, StdTypeList.EMPTY, "fill-array-data");
 
-    /**
-     * Returns the appropriate rop for the given opcode, destination,
-     * and sources. The result is typically, but not necessarily, a
-     * shared instance.
-     *
-     * <p><b>Note:</b> This method does not do complete error checking on
-     * its arguments, and so it may return an instance which seemed "right
-     * enough" even though in actuality the passed arguments don't quite
-     * match what is returned. TODO: Revisit this issue.</p>
-     *
-     * @param opcode the opcode
-     * @param dest {@code non-null;} destination (result) type, or
-     * {@link Type#VOID} if none
-     * @param sources {@code non-null;} list of source types
-     * @param cst {@code null-ok;} associated constant, if any
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop ropFor(int opcode, TypeBearer dest, TypeList sources,
-            Constant cst) {
-        switch (opcode) {
-            case RegOps.NOP: return NOP;
-            case RegOps.MOVE: return opMove(dest);
-            case RegOps.MOVE_PARAM: return opMoveParam(dest);
-            case RegOps.MOVE_EXCEPTION: return opMoveException(dest);
-            case RegOps.CONST: return opConst(dest);
-            case RegOps.GOTO: return GOTO;
-            case RegOps.IF_EQ: return opIfEq(sources);
-            case RegOps.IF_NE: return opIfNe(sources);
-            case RegOps.IF_LT: return opIfLt(sources);
-            case RegOps.IF_GE: return opIfGe(sources);
-            case RegOps.IF_LE: return opIfLe(sources);
-            case RegOps.IF_GT: return opIfGt(sources);
-            case RegOps.SWITCH: return SWITCH;
-            case RegOps.ADD: return opAdd(sources);
-            case RegOps.SUB: return opSub(sources);
-            case RegOps.MUL: return opMul(sources);
-            case RegOps.DIV: return opDiv(sources);
-            case RegOps.REM: return opRem(sources);
-            case RegOps.NEG: return opNeg(dest);
-            case RegOps.AND: return opAnd(sources);
-            case RegOps.OR: return opOr(sources);
-            case RegOps.XOR: return opXor(sources);
-            case RegOps.SHL: return opShl(sources);
-            case RegOps.SHR: return opShr(sources);
-            case RegOps.USHR: return opUshr(sources);
-            case RegOps.NOT: return opNot(dest);
-            case RegOps.CMPL: return opCmpl(sources.getType(0));
-            case RegOps.CMPG: return opCmpg(sources.getType(0));
-            case RegOps.CONV: return opConv(dest, sources.getType(0));
-            case RegOps.TO_BYTE: return TO_BYTE;
-            case RegOps.TO_CHAR: return TO_CHAR;
-            case RegOps.TO_SHORT: return TO_SHORT;
-            case RegOps.RETURN: {
-                if (sources.size() == 0) {
-                    return RETURN_VOID;
-                }
-                return opReturn(sources.getType(0));
-            }
-            case RegOps.ARRAY_LENGTH: return ARRAY_LENGTH;
-            case RegOps.THROW: return THROW;
-            case RegOps.MONITOR_ENTER: return MONITOR_ENTER;
-            case RegOps.MONITOR_EXIT: return MONITOR_EXIT;
-            case RegOps.AGET: {
-                Type source = sources.getType(0);
-                Type componentType;
-                if (source == Type.KNOWN_NULL) {
-                    /*
-                     * Treat a known-null as an array of the expected
-                     * result type.
-                     */
-                    componentType = dest.getType();
-                } else {
-                    componentType = source.getComponentType();
-                }
-                return opAget(componentType);
-            }
-            case RegOps.APUT: {
-                Type source = sources.getType(1);
-                Type componentType;
-                if (source == Type.KNOWN_NULL) {
-                    /*
-                     * Treat a known-null as an array of the type being
-                     * stored.
-                     */
-                    componentType = sources.getType(0);
-                } else {
-                    componentType = source.getComponentType();
-                }
-                return opAput(componentType);
-            }
-            case RegOps.NEW_INSTANCE: return NEW_INSTANCE;
-            case RegOps.NEW_ARRAY: return opNewArray(dest.getType());
-            case RegOps.CHECK_CAST: return CHECK_CAST;
-            case RegOps.INSTANCE_OF: return INSTANCE_OF;
-            case RegOps.GET_FIELD: return opGetField(dest);
-            case RegOps.GET_STATIC: return opGetStatic(dest);
-            case RegOps.PUT_FIELD: return opPutField(sources.getType(0));
-            case RegOps.PUT_STATIC: return opPutStatic(sources.getType(0));
-            case RegOps.INVOKE_STATIC: {
-                return opInvokeStatic(((CstMethodRef) cst).getPrototype());
-            }
-            case RegOps.INVOKE_VIRTUAL: {
-                CstBaseMethodRef cstMeth = (CstMethodRef) cst;
-                Prototype meth = cstMeth.getPrototype();
-                CstType definer = cstMeth.getDefiningClass();
-                meth = meth.withFirstParameter(definer.getClassType());
-                return opInvokeVirtual(meth);
-            }
-            case RegOps.INVOKE_SUPER: {
-                CstBaseMethodRef cstMeth = (CstMethodRef) cst;
-                Prototype meth = cstMeth.getPrototype();
-                CstType definer = cstMeth.getDefiningClass();
-                meth = meth.withFirstParameter(definer.getClassType());
-                return opInvokeSuper(meth);
-            }
-            case RegOps.INVOKE_DIRECT: {
-                CstBaseMethodRef cstMeth = (CstMethodRef) cst;
-                Prototype meth = cstMeth.getPrototype();
-                CstType definer = cstMeth.getDefiningClass();
-                meth = meth.withFirstParameter(definer.getClassType());
-                return opInvokeDirect(meth);
-            }
-            case RegOps.INVOKE_INTERFACE: {
-                CstBaseMethodRef cstMeth = (CstMethodRef) cst;
-                Prototype meth = cstMeth.getPrototype();
-                CstType definer = cstMeth.getDefiningClass();
-                meth = meth.withFirstParameter(definer.getClassType());
-                return opInvokeInterface(meth);
-            }
+  /**
+   * Returns the appropriate rop for the given opcode, destination,
+   * and sources. The result is typically, but not necessarily, a
+   * shared instance.
+   *
+   * <p><b>Note:</b> This method does not do complete error checking on
+   * its arguments, and so it may return an instance which seemed "right
+   * enough" even though in actuality the passed arguments don't quite
+   * match what is returned. TODO(dx team): Revisit this issue.</p>
+   *
+   * @param opcode the opcode
+   * @param dest {@code non-null;} destination (result) type, or
+   * {@link Type#VOID} if none
+   * @param sources {@code non-null;} list of source types
+   * @param cst {@code null-ok;} associated constant, if any
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop ropFor(int opcode, TypeBearer dest, TypeList sources, Constant cst) {
+    switch (opcode) {
+      case RegOps.NOP:
+        return NOP;
+      case RegOps.MOVE:
+        return opMove(dest);
+      case RegOps.MOVE_PARAM:
+        return opMoveParam(dest);
+      case RegOps.MOVE_EXCEPTION:
+        return opMoveException(dest);
+      case RegOps.CONST:
+        return opConst(dest);
+      case RegOps.GOTO:
+        return GOTO;
+      case RegOps.IF_EQ:
+        return opIfEq(sources);
+      case RegOps.IF_NE:
+        return opIfNe(sources);
+      case RegOps.IF_LT:
+        return opIfLt(sources);
+      case RegOps.IF_GE:
+        return opIfGe(sources);
+      case RegOps.IF_LE:
+        return opIfLe(sources);
+      case RegOps.IF_GT:
+        return opIfGt(sources);
+      case RegOps.SWITCH:
+        return SWITCH;
+      case RegOps.ADD:
+        return opAdd(sources);
+      case RegOps.SUB:
+        return opSub(sources);
+      case RegOps.MUL:
+        return opMul(sources);
+      case RegOps.DIV:
+        return opDiv(sources);
+      case RegOps.REM:
+        return opRem(sources);
+      case RegOps.NEG:
+        return opNeg(dest);
+      case RegOps.AND:
+        return opAnd(sources);
+      case RegOps.OR:
+        return opOr(sources);
+      case RegOps.XOR:
+        return opXor(sources);
+      case RegOps.SHL:
+        return opShl(sources);
+      case RegOps.SHR:
+        return opShr(sources);
+      case RegOps.USHR:
+        return opUshr(sources);
+      case RegOps.NOT:
+        return opNot(dest);
+      case RegOps.CMPL:
+        return opCmpl(sources.getType(0));
+      case RegOps.CMPG:
+        return opCmpg(sources.getType(0));
+      case RegOps.CONV:
+        return opConv(dest, sources.getType(0));
+      case RegOps.TO_BYTE:
+        return TO_BYTE;
+      case RegOps.TO_CHAR:
+        return TO_CHAR;
+      case RegOps.TO_SHORT:
+        return TO_SHORT;
+      case RegOps.RETURN: {
+        if (sources.size() == 0) {
+          return RETURN_VOID;
         }
-
-        throw new RuntimeException("unknown opcode " + RegOps.opName(opcode));
-    }
-
-    /**
-     * Returns the appropriate {@code move} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being moved
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMove(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return MOVE_INT;
-            case Type.BT_LONG:   return MOVE_LONG;
-            case Type.BT_FLOAT:  return MOVE_FLOAT;
-            case Type.BT_DOUBLE: return MOVE_DOUBLE;
-            case Type.BT_OBJECT: return MOVE_OBJECT;
-            case Type.BT_ADDR:   return MOVE_RETURN_ADDRESS;
+        return opReturn(sources.getType(0));
+      }
+      case RegOps.ARRAY_LENGTH:
+        return ARRAY_LENGTH;
+      case RegOps.THROW:
+        return THROW;
+      case RegOps.MONITOR_ENTER:
+        return MONITOR_ENTER;
+      case RegOps.MONITOR_EXIT:
+        return MONITOR_EXIT;
+      case RegOps.AGET: {
+        Type source = sources.getType(0);
+        Type componentType;
+        if (source == Type.KNOWN_NULL) {
+          /*
+           * Treat a known-null as an array of the expected
+           * result type.
+           */
+          componentType = dest.getType();
+        } else {
+          componentType = source.getComponentType();
         }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code move-param} rop for the
-     * given type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being moved
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMoveParam(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return MOVE_PARAM_INT;
-            case Type.BT_LONG:   return MOVE_PARAM_LONG;
-            case Type.BT_FLOAT:  return MOVE_PARAM_FLOAT;
-            case Type.BT_DOUBLE: return MOVE_PARAM_DOUBLE;
-            case Type.BT_OBJECT: return MOVE_PARAM_OBJECT;
+        return opAget(componentType);
+      }
+      case RegOps.APUT: {
+        Type source = sources.getType(1);
+        Type componentType;
+        if (source == Type.KNOWN_NULL) {
+          /*
+           * Treat a known-null as an array of the type being
+           * stored.
+           */
+          componentType = sources.getType(0);
+        } else {
+          componentType = source.getComponentType();
         }
-
-        return throwBadType(type);
+        return opAput(componentType);
+      }
+      case RegOps.NEW_INSTANCE:
+        return NEW_INSTANCE;
+      case RegOps.NEW_ARRAY:
+        return opNewArray(dest.getType());
+      case RegOps.CHECK_CAST:
+        return CHECK_CAST;
+      case RegOps.INSTANCE_OF:
+        return INSTANCE_OF;
+      case RegOps.GET_FIELD:
+        return opGetField(dest);
+      case RegOps.GET_STATIC:
+        return opGetStatic(dest);
+      case RegOps.PUT_FIELD:
+        return opPutField(sources.getType(0));
+      case RegOps.PUT_STATIC:
+        return opPutStatic(sources.getType(0));
+      case RegOps.INVOKE_STATIC: {
+        return opInvokeStatic(((CstMethodRef) cst).getPrototype());
+      }
+      case RegOps.INVOKE_VIRTUAL: {
+        CstBaseMethodRef cstMeth = (CstMethodRef) cst;
+        Prototype meth = cstMeth.getPrototype();
+        CstType definer = cstMeth.getDefiningClass();
+        meth = meth.withFirstParameter(definer.getClassType());
+        return opInvokeVirtual(meth);
+      }
+      case RegOps.INVOKE_SUPER: {
+        CstBaseMethodRef cstMeth = (CstMethodRef) cst;
+        Prototype meth = cstMeth.getPrototype();
+        CstType definer = cstMeth.getDefiningClass();
+        meth = meth.withFirstParameter(definer.getClassType());
+        return opInvokeSuper(meth);
+      }
+      case RegOps.INVOKE_DIRECT: {
+        CstBaseMethodRef cstMeth = (CstMethodRef) cst;
+        Prototype meth = cstMeth.getPrototype();
+        CstType definer = cstMeth.getDefiningClass();
+        meth = meth.withFirstParameter(definer.getClassType());
+        return opInvokeDirect(meth);
+      }
+      case RegOps.INVOKE_INTERFACE: {
+        CstBaseMethodRef cstMeth = (CstMethodRef) cst;
+        Prototype meth = cstMeth.getPrototype();
+        CstType definer = cstMeth.getDefiningClass();
+        meth = meth.withFirstParameter(definer.getClassType());
+        return opInvokeInterface(meth);
+      }
     }
 
-    /**
-     * Returns the appropriate {@code move-exception} rop for the
-     * given type. The result may be a shared instance.
-     *
-     * @param type {@code non-null;} type of the exception
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMoveException(TypeBearer type) {
-        return new Rop(RegOps.MOVE_EXCEPTION, type.getType(),
-                       StdTypeList.EMPTY, (String) null);
+    throw new RuntimeException("unknown opcode " + RegOps.opName(opcode));
+  }
+
+  /**
+   * Returns the appropriate {@code move} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being moved
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMove(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return MOVE_INT;
+      case Type.BT_LONG:
+        return MOVE_LONG;
+      case Type.BT_FLOAT:
+        return MOVE_FLOAT;
+      case Type.BT_DOUBLE:
+        return MOVE_DOUBLE;
+      case Type.BT_OBJECT:
+        return MOVE_OBJECT;
+      case Type.BT_ADDR:
+        return MOVE_RETURN_ADDRESS;
     }
 
-    /**
-     * Returns the appropriate {@code move-result} rop for the
-     * given type. The result may be a shared instance.
-     *
-     * @param type {@code non-null;} type of the parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMoveResult(TypeBearer type) {
-        return new Rop(RegOps.MOVE_RESULT, type.getType(),
-                       StdTypeList.EMPTY, (String) null);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code move-param} rop for the
+   * given type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being moved
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMoveParam(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return MOVE_PARAM_INT;
+      case Type.BT_LONG:
+        return MOVE_PARAM_LONG;
+      case Type.BT_FLOAT:
+        return MOVE_PARAM_FLOAT;
+      case Type.BT_DOUBLE:
+        return MOVE_PARAM_DOUBLE;
+      case Type.BT_OBJECT:
+        return MOVE_PARAM_OBJECT;
     }
 
-    /**
-     * Returns the appropriate {@code move-result-pseudo} rop for the
-     * given type. The result may be a shared instance.
-     *
-     * @param type {@code non-null;} type of the parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMoveResultPseudo(TypeBearer type) {
-        return new Rop(RegOps.MOVE_RESULT_PSEUDO, type.getType(),
-                       StdTypeList.EMPTY, (String) null);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code move-exception} rop for the
+   * given type. The result may be a shared instance.
+   *
+   * @param type {@code non-null;} type of the exception
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMoveException(TypeBearer type) {
+    return new Rop(RegOps.MOVE_EXCEPTION, type.getType(), StdTypeList.EMPTY, (String) null);
+  }
+
+  /**
+   * Returns the appropriate {@code move-result} rop for the
+   * given type. The result may be a shared instance.
+   *
+   * @param type {@code non-null;} type of the parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMoveResult(TypeBearer type) {
+    return new Rop(RegOps.MOVE_RESULT, type.getType(), StdTypeList.EMPTY, (String) null);
+  }
+
+  /**
+   * Returns the appropriate {@code move-result-pseudo} rop for the
+   * given type. The result may be a shared instance.
+   *
+   * @param type {@code non-null;} type of the parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMoveResultPseudo(TypeBearer type) {
+    return new Rop(RegOps.MOVE_RESULT_PSEUDO, type.getType(), StdTypeList.EMPTY, (String) null);
+  }
+
+  /**
+   * Returns the appropriate {@code const} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of the constant
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opConst(TypeBearer type) {
+    if (type.getType() == Type.KNOWN_NULL) {
+      return CONST_OBJECT_NOTHROW;
     }
 
-    /**
-     * Returns the appropriate {@code const} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of the constant
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opConst(TypeBearer type) {
-        if (type.getType() == Type.KNOWN_NULL) {
-            return CONST_OBJECT_NOTHROW;
-        }
-
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return CONST_INT;
-            case Type.BT_LONG:   return CONST_LONG;
-            case Type.BT_FLOAT:  return CONST_FLOAT;
-            case Type.BT_DOUBLE: return CONST_DOUBLE;
-            case Type.BT_OBJECT: return CONST_OBJECT;
-        }
-
-        return throwBadType(type);
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return CONST_INT;
+      case Type.BT_LONG:
+        return CONST_LONG;
+      case Type.BT_FLOAT:
+        return CONST_FLOAT;
+      case Type.BT_DOUBLE:
+        return CONST_DOUBLE;
+      case Type.BT_OBJECT:
+        return CONST_OBJECT;
     }
 
-    /**
-     * Returns the appropriate {@code if-eq} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfEq(TypeList types) {
-        return pickIf(types, IF_EQZ_INT, IF_EQZ_OBJECT,
-                      IF_EQ_INT, IF_EQ_OBJECT);
-    }
+    return throwBadType(type);
+  }
 
-    /**
-     * Returns the appropriate {@code if-ne} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfNe(TypeList types) {
-        return pickIf(types, IF_NEZ_INT, IF_NEZ_OBJECT,
-                      IF_NE_INT, IF_NE_OBJECT);
-    }
+  /**
+   * Returns the appropriate {@code if-eq} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfEq(TypeList types) {
+    return pickIf(types, IF_EQZ_INT, IF_EQZ_OBJECT, IF_EQ_INT, IF_EQ_OBJECT);
+  }
 
-    /**
-     * Returns the appropriate {@code if-lt} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfLt(TypeList types) {
-        return pickIf(types, IF_LTZ_INT, null, IF_LT_INT, null);
-    }
+  /**
+   * Returns the appropriate {@code if-ne} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfNe(TypeList types) {
+    return pickIf(types, IF_NEZ_INT, IF_NEZ_OBJECT, IF_NE_INT, IF_NE_OBJECT);
+  }
 
-    /**
-     * Returns the appropriate {@code if-ge} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfGe(TypeList types) {
-        return pickIf(types, IF_GEZ_INT, null, IF_GE_INT, null);
-    }
+  /**
+   * Returns the appropriate {@code if-lt} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfLt(TypeList types) {
+    return pickIf(types, IF_LTZ_INT, null, IF_LT_INT, null);
+  }
 
-    /**
-     * Returns the appropriate {@code if-gt} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfGt(TypeList types) {
-        return pickIf(types, IF_GTZ_INT, null, IF_GT_INT, null);
-    }
+  /**
+   * Returns the appropriate {@code if-ge} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfGe(TypeList types) {
+    return pickIf(types, IF_GEZ_INT, null, IF_GE_INT, null);
+  }
 
-    /**
-     * Returns the appropriate {@code if-le} rop for the given
-     * sources. The result is a shared instance.
-     *
-     * @param types {@code non-null;} source types
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opIfLe(TypeList types) {
-        return pickIf(types, IF_LEZ_INT, null, IF_LE_INT, null);
-    }
+  /**
+   * Returns the appropriate {@code if-gt} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfGt(TypeList types) {
+    return pickIf(types, IF_GTZ_INT, null, IF_GT_INT, null);
+  }
 
-    /**
-     * Helper for all the {@code if*}-related methods, which
-     * checks types and picks one of the four variants, throwing if
-     * there's a problem.
-     *
-     * @param types {@code non-null;} the types
-     * @param intZ {@code non-null;} the int-to-0 comparison
-     * @param objZ {@code null-ok;} the object-to-null comparison
-     * @param intInt {@code non-null;} the int-to-int comparison
-     * @param objObj {@code non-null;} the object-to-object comparison
-     * @return {@code non-null;} the appropriate instance
-     */
-    private static Rop pickIf(TypeList types, Rop intZ, Rop objZ, Rop intInt,
-                              Rop objObj) {
-        switch(types.size()) {
-            case 1: {
-                switch (types.getType(0).getBasicFrameType()) {
-                    case Type.BT_INT: {
-                        return intZ;
-                    }
-                    case Type.BT_OBJECT: {
-                        if (objZ != null) {
-                            return objZ;
-                        }
-                    }
-                }
-                break;
+  /**
+   * Returns the appropriate {@code if-le} rop for the given
+   * sources. The result is a shared instance.
+   *
+   * @param types {@code non-null;} source types
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opIfLe(TypeList types) {
+    return pickIf(types, IF_LEZ_INT, null, IF_LE_INT, null);
+  }
+
+  /**
+   * Helper for all the {@code if*}-related methods, which
+   * checks types and picks one of the four variants, throwing if
+   * there's a problem.
+   *
+   * @param types {@code non-null;} the types
+   * @param intZ {@code non-null;} the int-to-0 comparison
+   * @param objZ {@code null-ok;} the object-to-null comparison
+   * @param intInt {@code non-null;} the int-to-int comparison
+   * @param objObj {@code non-null;} the object-to-object comparison
+   * @return {@code non-null;} the appropriate instance
+   */
+  private static Rop pickIf(TypeList types, Rop intZ, Rop objZ, Rop intInt, Rop objObj) {
+    switch (types.size()) {
+      case 1: {
+        switch (types.getType(0).getBasicFrameType()) {
+          case Type.BT_INT: {
+            return intZ;
+          }
+          case Type.BT_OBJECT: {
+            if (objZ != null) {
+              return objZ;
             }
-            case 2: {
-                int bt = types.getType(0).getBasicFrameType();
-                if (bt == types.getType(1).getBasicFrameType()) {
-                    switch (bt) {
-                        case Type.BT_INT: {
-                            return intInt;
-                        }
-                        case Type.BT_OBJECT: {
-                            if (objObj != null) {
-                                return objObj;
-                            }
-                        }
-                    }
-                }
-                break;
-            }
+          }
         }
-
-        return throwBadTypes(types);
-    }
-
-    /**
-     * Returns the appropriate {@code add} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opAdd(TypeList types) {
-        return pickBinaryOp(types, ADD_CONST_INT, ADD_CONST_LONG,
-                            ADD_CONST_FLOAT, ADD_CONST_DOUBLE, ADD_INT,
-                            ADD_LONG, ADD_FLOAT, ADD_DOUBLE);
-    }
-
-    /**
-     * Returns the appropriate {@code sub} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opSub(TypeList types) {
-        return pickBinaryOp(types, SUB_CONST_INT, SUB_CONST_LONG,
-                            SUB_CONST_FLOAT, SUB_CONST_DOUBLE, SUB_INT,
-                            SUB_LONG, SUB_FLOAT, SUB_DOUBLE);
-    }
-
-    /**
-     * Returns the appropriate {@code mul} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMul(TypeList types) {
-        return pickBinaryOp(types, MUL_CONST_INT, MUL_CONST_LONG,
-                            MUL_CONST_FLOAT, MUL_CONST_DOUBLE, MUL_INT,
-                            MUL_LONG, MUL_FLOAT, MUL_DOUBLE);
-    }
-
-    /**
-     * Returns the appropriate {@code div} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opDiv(TypeList types) {
-        return pickBinaryOp(types, DIV_CONST_INT, DIV_CONST_LONG,
-                            DIV_CONST_FLOAT, DIV_CONST_DOUBLE, DIV_INT,
-                            DIV_LONG, DIV_FLOAT, DIV_DOUBLE);
-    }
-
-    /**
-     * Returns the appropriate {@code rem} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opRem(TypeList types) {
-        return pickBinaryOp(types, REM_CONST_INT, REM_CONST_LONG,
-                            REM_CONST_FLOAT, REM_CONST_DOUBLE, REM_INT,
-                            REM_LONG, REM_FLOAT, REM_DOUBLE);
-    }
-
-    /**
-     * Returns the appropriate {@code and} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opAnd(TypeList types) {
-        return pickBinaryOp(types, AND_CONST_INT, AND_CONST_LONG, null, null,
-                            AND_INT, AND_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate {@code or} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opOr(TypeList types) {
-        return pickBinaryOp(types, OR_CONST_INT, OR_CONST_LONG, null, null,
-                            OR_INT, OR_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate {@code xor} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opXor(TypeList types) {
-        return pickBinaryOp(types, XOR_CONST_INT, XOR_CONST_LONG, null, null,
-                            XOR_INT, XOR_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate {@code shl} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opShl(TypeList types) {
-        return pickBinaryOp(types, SHL_CONST_INT, SHL_CONST_LONG, null, null,
-                            SHL_INT, SHL_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate {@code shr} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opShr(TypeList types) {
-        return pickBinaryOp(types, SHR_CONST_INT, SHR_CONST_LONG, null, null,
-                            SHR_INT, SHR_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate {@code ushr} rop for the given
-     * types. The result is a shared instance.
-     *
-     * @param types {@code non-null;} types of the sources
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opUshr(TypeList types) {
-        return pickBinaryOp(types, USHR_CONST_INT, USHR_CONST_LONG, null, null,
-                            USHR_INT, USHR_LONG, null, null);
-    }
-
-    /**
-     * Returns the appropriate binary arithmetic rop for the given type
-     * and arguments. The result is a shared instance.
-     *
-     * @param types {@code non-null;} sources of the operation
-     * @param int1 {@code non-null;} the int-to-constant rop
-     * @param long1 {@code non-null;} the long-to-constant rop
-     * @param float1 {@code null-ok;} the float-to-constant rop, if any
-     * @param double1 {@code null-ok;} the double-to-constant rop, if any
-     * @param int2 {@code non-null;} the int-to-int rop
-     * @param long2 {@code non-null;} the long-to-long or long-to-int rop
-     * @param float2 {@code null-ok;} the float-to-float rop, if any
-     * @param double2 {@code null-ok;} the double-to-double rop, if any
-     * @return {@code non-null;} an appropriate instance
-     */
-    private static Rop pickBinaryOp(TypeList types, Rop int1, Rop long1,
-                                    Rop float1, Rop double1, Rop int2,
-                                    Rop long2, Rop float2, Rop double2) {
-        int bt1 = types.getType(0).getBasicFrameType();
-        Rop result = null;
-
-        switch (types.size()) {
-            case 1: {
-                switch(bt1) {
-                    case Type.BT_INT:    return int1;
-                    case Type.BT_LONG:   return long1;
-                    case Type.BT_FLOAT:  result = float1; break;
-                    case Type.BT_DOUBLE: result = double1; break;
-                }
-                break;
-            }
-            case 2: {
-                switch(bt1) {
-                    case Type.BT_INT:    return int2;
-                    case Type.BT_LONG:   return long2;
-                    case Type.BT_FLOAT:  result = float2; break;
-                    case Type.BT_DOUBLE: result = double2; break;
-                }
-                break;
-            }
-        }
-
-        if (result == null) {
-            return throwBadTypes(types);
-        }
-
-        return result;
-    }
-
-    /**
-     * Returns the appropriate {@code neg} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being operated on
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opNeg(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return NEG_INT;
-            case Type.BT_LONG:   return NEG_LONG;
-            case Type.BT_FLOAT:  return NEG_FLOAT;
-            case Type.BT_DOUBLE: return NEG_DOUBLE;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code not} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being operated on
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opNot(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:  return NOT_INT;
-            case Type.BT_LONG: return NOT_LONG;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code cmpl} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being compared
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opCmpl(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_LONG:   return CMPL_LONG;
-            case Type.BT_FLOAT:  return CMPL_FLOAT;
-            case Type.BT_DOUBLE: return CMPL_DOUBLE;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code cmpg} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being compared
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opCmpg(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_FLOAT:  return CMPG_FLOAT;
-            case Type.BT_DOUBLE: return CMPG_DOUBLE;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code conv} rop for the given types. The
-     * result is a shared instance.
-     *
-     * @param dest {@code non-null;} target value type
-     * @param source {@code non-null;} source value type
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opConv(TypeBearer dest, TypeBearer source) {
-        int dbt = dest.getBasicFrameType();
-        switch (source.getBasicFrameType()) {
+        break;
+      }
+      case 2: {
+        int bt = types.getType(0).getBasicFrameType();
+        if (bt == types.getType(1).getBasicFrameType()) {
+          switch (bt) {
             case Type.BT_INT: {
-                switch (dbt) {
-                    case Type.BT_LONG:   return CONV_I2L;
-                    case Type.BT_FLOAT:  return CONV_I2F;
-                    case Type.BT_DOUBLE: return CONV_I2D;
-                    default:             break;
-                }
+              return intInt;
             }
-            case Type.BT_LONG: {
-                switch (dbt) {
-                    case Type.BT_INT:    return CONV_L2I;
-                    case Type.BT_FLOAT:  return CONV_L2F;
-                    case Type.BT_DOUBLE: return CONV_L2D;
-                    default:             break;
-                }
-            }
-            case Type.BT_FLOAT: {
-                switch (dbt) {
-                    case Type.BT_INT:    return CONV_F2I;
-                    case Type.BT_LONG:   return CONV_F2L;
-                    case Type.BT_DOUBLE: return CONV_F2D;
-                    default:             break;
-                }
-            }
-            case Type.BT_DOUBLE: {
-                switch (dbt) {
-                    case Type.BT_INT:    return CONV_D2I;
-                    case Type.BT_LONG:   return CONV_D2L;
-                    case Type.BT_FLOAT:  return CONV_D2F;
-                    default:             break;
-                }
-            }
-        }
-
-        return throwBadTypes(StdTypeList.make(dest.getType(),
-                                              source.getType()));
-    }
-
-    /**
-     * Returns the appropriate {@code return} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being returned
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opReturn(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return RETURN_INT;
-            case Type.BT_LONG:   return RETURN_LONG;
-            case Type.BT_FLOAT:  return RETURN_FLOAT;
-            case Type.BT_DOUBLE: return RETURN_DOUBLE;
-            case Type.BT_OBJECT: return RETURN_OBJECT;
-            case Type.BT_VOID:   return RETURN_VOID;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code aget} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} element type of array being accessed
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opAget(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return AGET_INT;
-            case Type.BT_LONG:    return AGET_LONG;
-            case Type.BT_FLOAT:   return AGET_FLOAT;
-            case Type.BT_DOUBLE:  return AGET_DOUBLE;
-            case Type.BT_OBJECT:  return AGET_OBJECT;
-            case Type.BT_BOOLEAN: return AGET_BOOLEAN;
-            case Type.BT_BYTE:    return AGET_BYTE;
-            case Type.BT_CHAR:    return AGET_CHAR;
-            case Type.BT_SHORT:   return AGET_SHORT;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code aput} rop for the given type. The
-     * result is a shared instance.
-     *
-     * @param type {@code non-null;} element type of array being accessed
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opAput(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return APUT_INT;
-            case Type.BT_LONG:    return APUT_LONG;
-            case Type.BT_FLOAT:   return APUT_FLOAT;
-            case Type.BT_DOUBLE:  return APUT_DOUBLE;
-            case Type.BT_OBJECT:  return APUT_OBJECT;
-            case Type.BT_BOOLEAN: return APUT_BOOLEAN;
-            case Type.BT_BYTE:    return APUT_BYTE;
-            case Type.BT_CHAR:    return APUT_CHAR;
-            case Type.BT_SHORT:   return APUT_SHORT;
-        }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code new-array} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param arrayType {@code non-null;} array type of array being created
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opNewArray(TypeBearer arrayType) {
-        Type type = arrayType.getType();
-        Type elementType = type.getComponentType();
-
-        switch (elementType.getBasicType()) {
-            case Type.BT_INT:     return NEW_ARRAY_INT;
-            case Type.BT_LONG:    return NEW_ARRAY_LONG;
-            case Type.BT_FLOAT:   return NEW_ARRAY_FLOAT;
-            case Type.BT_DOUBLE:  return NEW_ARRAY_DOUBLE;
-            case Type.BT_BOOLEAN: return NEW_ARRAY_BOOLEAN;
-            case Type.BT_BYTE:    return NEW_ARRAY_BYTE;
-            case Type.BT_CHAR:    return NEW_ARRAY_CHAR;
-            case Type.BT_SHORT:   return NEW_ARRAY_SHORT;
             case Type.BT_OBJECT: {
-                return new Rop(RegOps.NEW_ARRAY, type, StdTypeList.INT,
-                        Exceptions.LIST_Error_NegativeArraySizeException,
-                        "new-array-object");
+              if (objObj != null) {
+                return objObj;
+              }
             }
+          }
         }
-
-        return throwBadType(type);
+        break;
+      }
     }
 
-    /**
-     * Returns the appropriate {@code filled-new-array} rop for the given
-     * type. The result may be a shared instance.
-     *
-     * @param arrayType {@code non-null;} type of array being created
-     * @param count {@code >= 0;} number of elements that the array should have
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opFilledNewArray(TypeBearer arrayType, int count) {
-        Type type = arrayType.getType();
-        Type elementType = type.getComponentType();
+    return throwBadTypes(types);
+  }
 
-        if (elementType.isCategory2()) {
-            return throwBadType(arrayType);
+  /**
+   * Returns the appropriate {@code add} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opAdd(TypeList types) {
+    return pickBinaryOp(types,
+        ADD_CONST_INT,
+        ADD_CONST_LONG,
+        ADD_CONST_FLOAT,
+        ADD_CONST_DOUBLE,
+        ADD_INT,
+        ADD_LONG,
+        ADD_FLOAT,
+        ADD_DOUBLE);
+  }
+
+  /**
+   * Returns the appropriate {@code sub} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opSub(TypeList types) {
+    return pickBinaryOp(types,
+        SUB_CONST_INT,
+        SUB_CONST_LONG,
+        SUB_CONST_FLOAT,
+        SUB_CONST_DOUBLE,
+        SUB_INT,
+        SUB_LONG,
+        SUB_FLOAT,
+        SUB_DOUBLE);
+  }
+
+  /**
+   * Returns the appropriate {@code mul} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMul(TypeList types) {
+    return pickBinaryOp(types,
+        MUL_CONST_INT,
+        MUL_CONST_LONG,
+        MUL_CONST_FLOAT,
+        MUL_CONST_DOUBLE,
+        MUL_INT,
+        MUL_LONG,
+        MUL_FLOAT,
+        MUL_DOUBLE);
+  }
+
+  /**
+   * Returns the appropriate {@code div} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opDiv(TypeList types) {
+    return pickBinaryOp(types,
+        DIV_CONST_INT,
+        DIV_CONST_LONG,
+        DIV_CONST_FLOAT,
+        DIV_CONST_DOUBLE,
+        DIV_INT,
+        DIV_LONG,
+        DIV_FLOAT,
+        DIV_DOUBLE);
+  }
+
+  /**
+   * Returns the appropriate {@code rem} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opRem(TypeList types) {
+    return pickBinaryOp(types,
+        REM_CONST_INT,
+        REM_CONST_LONG,
+        REM_CONST_FLOAT,
+        REM_CONST_DOUBLE,
+        REM_INT,
+        REM_LONG,
+        REM_FLOAT,
+        REM_DOUBLE);
+  }
+
+  /**
+   * Returns the appropriate {@code and} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opAnd(TypeList types) {
+    return pickBinaryOp(types,
+        AND_CONST_INT,
+        AND_CONST_LONG,
+        null,
+        null,
+        AND_INT,
+        AND_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate {@code or} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opOr(TypeList types) {
+    return pickBinaryOp(types,
+        OR_CONST_INT,
+        OR_CONST_LONG,
+        null,
+        null,
+        OR_INT,
+        OR_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate {@code xor} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opXor(TypeList types) {
+    return pickBinaryOp(types,
+        XOR_CONST_INT,
+        XOR_CONST_LONG,
+        null,
+        null,
+        XOR_INT,
+        XOR_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate {@code shl} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opShl(TypeList types) {
+    return pickBinaryOp(types,
+        SHL_CONST_INT,
+        SHL_CONST_LONG,
+        null,
+        null,
+        SHL_INT,
+        SHL_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate {@code shr} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opShr(TypeList types) {
+    return pickBinaryOp(types,
+        SHR_CONST_INT,
+        SHR_CONST_LONG,
+        null,
+        null,
+        SHR_INT,
+        SHR_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate {@code ushr} rop for the given
+   * types. The result is a shared instance.
+   *
+   * @param types {@code non-null;} types of the sources
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opUshr(TypeList types) {
+    return pickBinaryOp(types,
+        USHR_CONST_INT,
+        USHR_CONST_LONG,
+        null,
+        null,
+        USHR_INT,
+        USHR_LONG,
+        null,
+        null);
+  }
+
+  /**
+   * Returns the appropriate binary arithmetic rop for the given type
+   * and arguments. The result is a shared instance.
+   *
+   * @param types {@code non-null;} sources of the operation
+   * @param int1 {@code non-null;} the int-to-constant rop
+   * @param long1 {@code non-null;} the long-to-constant rop
+   * @param float1 {@code null-ok;} the float-to-constant rop, if any
+   * @param double1 {@code null-ok;} the double-to-constant rop, if any
+   * @param int2 {@code non-null;} the int-to-int rop
+   * @param long2 {@code non-null;} the long-to-long or long-to-int rop
+   * @param float2 {@code null-ok;} the float-to-float rop, if any
+   * @param double2 {@code null-ok;} the double-to-double rop, if any
+   * @return {@code non-null;} an appropriate instance
+   */
+  private static Rop pickBinaryOp(TypeList types,
+      Rop int1,
+      Rop long1,
+      Rop float1,
+      Rop double1,
+      Rop int2,
+      Rop long2,
+      Rop float2,
+      Rop double2) {
+    int bt1 = types.getType(0).getBasicFrameType();
+    Rop result = null;
+
+    switch (types.size()) {
+      case 1: {
+        switch (bt1) {
+          case Type.BT_INT:
+            return int1;
+          case Type.BT_LONG:
+            return long1;
+          case Type.BT_FLOAT:
+            result = float1;
+            break;
+          case Type.BT_DOUBLE:
+            result = double1;
+            break;
         }
-
-        if (count < 0) {
-            throw new IllegalArgumentException("count < 0");
+        break;
+      }
+      case 2: {
+        switch (bt1) {
+          case Type.BT_INT:
+            return int2;
+          case Type.BT_LONG:
+            return long2;
+          case Type.BT_FLOAT:
+            result = float2;
+            break;
+          case Type.BT_DOUBLE:
+            result = double2;
+            break;
         }
+        break;
+      }
+    }
 
-        StdTypeList sourceTypes = new StdTypeList(count);
+    if (result == null) {
+      return throwBadTypes(types);
+    }
 
-        for (int i = 0; i < count; i++) {
-            sourceTypes.set(i, elementType);
+    return result;
+  }
+
+  /**
+   * Returns the appropriate {@code neg} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being operated on
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opNeg(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return NEG_INT;
+      case Type.BT_LONG:
+        return NEG_LONG;
+      case Type.BT_FLOAT:
+        return NEG_FLOAT;
+      case Type.BT_DOUBLE:
+        return NEG_DOUBLE;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code not} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being operated on
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opNot(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return NOT_INT;
+      case Type.BT_LONG:
+        return NOT_LONG;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code cmpl} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being compared
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opCmpl(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_LONG:
+        return CMPL_LONG;
+      case Type.BT_FLOAT:
+        return CMPL_FLOAT;
+      case Type.BT_DOUBLE:
+        return CMPL_DOUBLE;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code cmpg} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being compared
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opCmpg(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_FLOAT:
+        return CMPG_FLOAT;
+      case Type.BT_DOUBLE:
+        return CMPG_DOUBLE;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code conv} rop for the given types. The
+   * result is a shared instance.
+   *
+   * @param dest {@code non-null;} target value type
+   * @param source {@code non-null;} source value type
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opConv(TypeBearer dest, TypeBearer source) {
+    int dbt = dest.getBasicFrameType();
+    switch (source.getBasicFrameType()) {
+      case Type.BT_INT: {
+        switch (dbt) {
+          case Type.BT_LONG:
+            return CONV_I2L;
+          case Type.BT_FLOAT:
+            return CONV_I2F;
+          case Type.BT_DOUBLE:
+            return CONV_I2D;
+          default:
+            break;
         }
-
-        // Note: The resulting rop is considered call-like.
-        return new Rop(RegOps.FILLED_NEW_ARRAY,
-                       sourceTypes,
-                       Exceptions.LIST_Error);
-    }
-
-    /**
-     * Returns the appropriate {@code get-field} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of the field in question
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opGetField(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return GET_FIELD_INT;
-            case Type.BT_LONG:    return GET_FIELD_LONG;
-            case Type.BT_FLOAT:   return GET_FIELD_FLOAT;
-            case Type.BT_DOUBLE:  return GET_FIELD_DOUBLE;
-            case Type.BT_OBJECT:  return GET_FIELD_OBJECT;
-            case Type.BT_BOOLEAN: return GET_FIELD_BOOLEAN;
-            case Type.BT_BYTE:    return GET_FIELD_BYTE;
-            case Type.BT_CHAR:    return GET_FIELD_CHAR;
-            case Type.BT_SHORT:   return GET_FIELD_SHORT;
+        break;
+      }
+      case Type.BT_LONG: {
+        switch (dbt) {
+          case Type.BT_INT:
+            return CONV_L2I;
+          case Type.BT_FLOAT:
+            return CONV_L2F;
+          case Type.BT_DOUBLE:
+            return CONV_L2D;
+          default:
+            break;
         }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code put-field} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of the field in question
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opPutField(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return PUT_FIELD_INT;
-            case Type.BT_LONG:    return PUT_FIELD_LONG;
-            case Type.BT_FLOAT:   return PUT_FIELD_FLOAT;
-            case Type.BT_DOUBLE:  return PUT_FIELD_DOUBLE;
-            case Type.BT_OBJECT:  return PUT_FIELD_OBJECT;
-            case Type.BT_BOOLEAN: return PUT_FIELD_BOOLEAN;
-            case Type.BT_BYTE:    return PUT_FIELD_BYTE;
-            case Type.BT_CHAR:    return PUT_FIELD_CHAR;
-            case Type.BT_SHORT:   return PUT_FIELD_SHORT;
+        break;
+      }
+      case Type.BT_FLOAT: {
+        switch (dbt) {
+          case Type.BT_INT:
+            return CONV_F2I;
+          case Type.BT_LONG:
+            return CONV_F2L;
+          case Type.BT_DOUBLE:
+            return CONV_F2D;
+          default:
+            break;
         }
-
-        return throwBadType(type);
-    }
-
-    /**
-     * Returns the appropriate {@code get-static} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of the field in question
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opGetStatic(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return GET_STATIC_INT;
-            case Type.BT_LONG:    return GET_STATIC_LONG;
-            case Type.BT_FLOAT:   return GET_STATIC_FLOAT;
-            case Type.BT_DOUBLE:  return GET_STATIC_DOUBLE;
-            case Type.BT_OBJECT:  return GET_STATIC_OBJECT;
-            case Type.BT_BOOLEAN: return GET_STATIC_BOOLEAN;
-            case Type.BT_BYTE:    return GET_STATIC_BYTE;
-            case Type.BT_CHAR:    return GET_STATIC_CHAR;
-            case Type.BT_SHORT:   return GET_STATIC_SHORT;
+        break;
+      }
+      case Type.BT_DOUBLE: {
+        switch (dbt) {
+          case Type.BT_INT:
+            return CONV_D2I;
+          case Type.BT_LONG:
+            return CONV_D2L;
+          case Type.BT_FLOAT:
+            return CONV_D2F;
+          default:
+            break;
         }
-
-        return throwBadType(type);
+      }
     }
 
-    /**
-     * Returns the appropriate {@code put-static} rop for the given
-     * type. The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of the field in question
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opPutStatic(TypeBearer type) {
-        switch (type.getBasicType()) {
-            case Type.BT_INT:     return PUT_STATIC_INT;
-            case Type.BT_LONG:    return PUT_STATIC_LONG;
-            case Type.BT_FLOAT:   return PUT_STATIC_FLOAT;
-            case Type.BT_DOUBLE:  return PUT_STATIC_DOUBLE;
-            case Type.BT_OBJECT:  return PUT_STATIC_OBJECT;
-            case Type.BT_BOOLEAN: return PUT_STATIC_BOOLEAN;
-            case Type.BT_BYTE:    return PUT_STATIC_BYTE;
-            case Type.BT_CHAR:    return PUT_STATIC_CHAR;
-            case Type.BT_SHORT:   return PUT_STATIC_SHORT;
-        }
+    return throwBadTypes(StdTypeList.make(dest.getType(), source.getType()));
+  }
 
-        return throwBadType(type);
+  /**
+   * Returns the appropriate {@code return} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being returned
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opReturn(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return RETURN_INT;
+      case Type.BT_LONG:
+        return RETURN_LONG;
+      case Type.BT_FLOAT:
+        return RETURN_FLOAT;
+      case Type.BT_DOUBLE:
+        return RETURN_DOUBLE;
+      case Type.BT_OBJECT:
+        return RETURN_OBJECT;
+      case Type.BT_VOID:
+        return RETURN_VOID;
     }
 
-    /**
-     * Returns the appropriate {@code invoke-static} rop for the
-     * given type. The result is typically a newly-allocated instance.
-     *
-     * @param meth {@code non-null;} descriptor of the method
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opInvokeStatic(Prototype meth) {
-        return new Rop(RegOps.INVOKE_STATIC,
-                       meth.getParameterFrameTypes(),
-                       StdTypeList.THROWABLE);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code aget} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} element type of array being accessed
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opAget(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return AGET_INT;
+      case Type.BT_LONG:
+        return AGET_LONG;
+      case Type.BT_FLOAT:
+        return AGET_FLOAT;
+      case Type.BT_DOUBLE:
+        return AGET_DOUBLE;
+      case Type.BT_OBJECT:
+        return AGET_OBJECT;
+      case Type.BT_BOOLEAN:
+        return AGET_BOOLEAN;
+      case Type.BT_BYTE:
+        return AGET_BYTE;
+      case Type.BT_CHAR:
+        return AGET_CHAR;
+      case Type.BT_SHORT:
+        return AGET_SHORT;
     }
 
-    /**
-     * Returns the appropriate {@code invoke-virtual} rop for the
-     * given type. The result is typically a newly-allocated instance.
-     *
-     * @param meth {@code non-null;} descriptor of the method, including the
-     * {@code this} parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opInvokeVirtual(Prototype meth) {
-        return new Rop(RegOps.INVOKE_VIRTUAL,
-                       meth.getParameterFrameTypes(),
-                       StdTypeList.THROWABLE);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code aput} rop for the given type. The
+   * result is a shared instance.
+   *
+   * @param type {@code non-null;} element type of array being accessed
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opAput(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return APUT_INT;
+      case Type.BT_LONG:
+        return APUT_LONG;
+      case Type.BT_FLOAT:
+        return APUT_FLOAT;
+      case Type.BT_DOUBLE:
+        return APUT_DOUBLE;
+      case Type.BT_OBJECT:
+        return APUT_OBJECT;
+      case Type.BT_BOOLEAN:
+        return APUT_BOOLEAN;
+      case Type.BT_BYTE:
+        return APUT_BYTE;
+      case Type.BT_CHAR:
+        return APUT_CHAR;
+      case Type.BT_SHORT:
+        return APUT_SHORT;
     }
 
-    /**
-     * Returns the appropriate {@code invoke-super} rop for the
-     * given type. The result is typically a newly-allocated instance.
-     *
-     * @param meth {@code non-null;} descriptor of the method, including the
-     * {@code this} parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opInvokeSuper(Prototype meth) {
-        return new Rop(RegOps.INVOKE_SUPER,
-                       meth.getParameterFrameTypes(),
-                       StdTypeList.THROWABLE);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code new-array} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param arrayType {@code non-null;} array type of array being created
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opNewArray(TypeBearer arrayType) {
+    Type type = arrayType.getType();
+    Type elementType = type.getComponentType();
+
+    switch (elementType.getBasicType()) {
+      case Type.BT_INT:
+        return NEW_ARRAY_INT;
+      case Type.BT_LONG:
+        return NEW_ARRAY_LONG;
+      case Type.BT_FLOAT:
+        return NEW_ARRAY_FLOAT;
+      case Type.BT_DOUBLE:
+        return NEW_ARRAY_DOUBLE;
+      case Type.BT_BOOLEAN:
+        return NEW_ARRAY_BOOLEAN;
+      case Type.BT_BYTE:
+        return NEW_ARRAY_BYTE;
+      case Type.BT_CHAR:
+        return NEW_ARRAY_CHAR;
+      case Type.BT_SHORT:
+        return NEW_ARRAY_SHORT;
+      case Type.BT_OBJECT: {
+        return new Rop(RegOps.NEW_ARRAY, type, StdTypeList.INT,
+            Exceptions.LIST_Error_NegativeArraySizeException, "new-array-object");
+      }
     }
 
-    /**
-     * Returns the appropriate {@code invoke-direct} rop for the
-     * given type. The result is typically a newly-allocated instance.
-     *
-     * @param meth {@code non-null;} descriptor of the method, including the
-     * {@code this} parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opInvokeDirect(Prototype meth) {
-        return new Rop(RegOps.INVOKE_DIRECT,
-                       meth.getParameterFrameTypes(),
-                       StdTypeList.THROWABLE);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code filled-new-array} rop for the given
+   * type. The result may be a shared instance.
+   *
+   * @param arrayType {@code non-null;} type of array being created
+   * @param count {@code >= 0;} number of elements that the array should have
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opFilledNewArray(TypeBearer arrayType, int count) {
+    Type type = arrayType.getType();
+    Type elementType = type.getComponentType();
+
+    if (elementType.isCategory2()) {
+      return throwBadType(arrayType);
     }
 
-    /**
-     * Returns the appropriate {@code invoke-interface} rop for the
-     * given type. The result is typically a newly-allocated instance.
-     *
-     * @param meth {@code non-null;} descriptor of the method, including the
-     * {@code this} parameter
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opInvokeInterface(Prototype meth) {
-        return new Rop(RegOps.INVOKE_INTERFACE,
-                       meth.getParameterFrameTypes(),
-                       StdTypeList.THROWABLE);
+    if (count < 0) {
+      throw new IllegalArgumentException("count < 0");
     }
 
-    /**
-     * Returns the appropriate {@code mark-local} rop for the given type.
-     * The result is a shared instance.
-     *
-     * @param type {@code non-null;} type of value being marked
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static Rop opMarkLocal(TypeBearer type) {
-        switch (type.getBasicFrameType()) {
-            case Type.BT_INT:    return MARK_LOCAL_INT;
-            case Type.BT_LONG:   return MARK_LOCAL_LONG;
-            case Type.BT_FLOAT:  return MARK_LOCAL_FLOAT;
-            case Type.BT_DOUBLE: return MARK_LOCAL_DOUBLE;
-            case Type.BT_OBJECT: return MARK_LOCAL_OBJECT;
-        }
+    StdTypeList sourceTypes = new StdTypeList(count);
 
-        return throwBadType(type);
+    for (int i = 0; i < count; i++) {
+      sourceTypes.set(i, elementType);
     }
 
-    /**
-     * This class is uninstantiable.
-     */
-    private Rops() {
-        // This space intentionally left blank.
+    // Note: The resulting rop is considered call-like.
+    return new Rop(RegOps.FILLED_NEW_ARRAY, sourceTypes, Exceptions.LIST_Error);
+  }
+
+  /**
+   * Returns the appropriate {@code get-field} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of the field in question
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opGetField(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return GET_FIELD_INT;
+      case Type.BT_LONG:
+        return GET_FIELD_LONG;
+      case Type.BT_FLOAT:
+        return GET_FIELD_FLOAT;
+      case Type.BT_DOUBLE:
+        return GET_FIELD_DOUBLE;
+      case Type.BT_OBJECT:
+        return GET_FIELD_OBJECT;
+      case Type.BT_BOOLEAN:
+        return GET_FIELD_BOOLEAN;
+      case Type.BT_BYTE:
+        return GET_FIELD_BYTE;
+      case Type.BT_CHAR:
+        return GET_FIELD_CHAR;
+      case Type.BT_SHORT:
+        return GET_FIELD_SHORT;
     }
 
-    /**
-     * Throws the right exception to complain about a bogus type.
-     *
-     * @param type {@code non-null;} the bad type
-     * @return never
-     */
-    private static Rop throwBadType(TypeBearer type) {
-        throw new IllegalArgumentException("bad type: " + type);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code put-field} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of the field in question
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opPutField(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return PUT_FIELD_INT;
+      case Type.BT_LONG:
+        return PUT_FIELD_LONG;
+      case Type.BT_FLOAT:
+        return PUT_FIELD_FLOAT;
+      case Type.BT_DOUBLE:
+        return PUT_FIELD_DOUBLE;
+      case Type.BT_OBJECT:
+        return PUT_FIELD_OBJECT;
+      case Type.BT_BOOLEAN:
+        return PUT_FIELD_BOOLEAN;
+      case Type.BT_BYTE:
+        return PUT_FIELD_BYTE;
+      case Type.BT_CHAR:
+        return PUT_FIELD_CHAR;
+      case Type.BT_SHORT:
+        return PUT_FIELD_SHORT;
     }
 
-    /**
-     * Throws the right exception to complain about a bogus list of types.
-     *
-     * @param types {@code non-null;} the bad types
-     * @return never
-     */
-    private static Rop throwBadTypes(TypeList types) {
-        throw new IllegalArgumentException("bad types: " + types);
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code get-static} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of the field in question
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opGetStatic(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return GET_STATIC_INT;
+      case Type.BT_LONG:
+        return GET_STATIC_LONG;
+      case Type.BT_FLOAT:
+        return GET_STATIC_FLOAT;
+      case Type.BT_DOUBLE:
+        return GET_STATIC_DOUBLE;
+      case Type.BT_OBJECT:
+        return GET_STATIC_OBJECT;
+      case Type.BT_BOOLEAN:
+        return GET_STATIC_BOOLEAN;
+      case Type.BT_BYTE:
+        return GET_STATIC_BYTE;
+      case Type.BT_CHAR:
+        return GET_STATIC_CHAR;
+      case Type.BT_SHORT:
+        return GET_STATIC_SHORT;
     }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code put-static} rop for the given
+   * type. The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of the field in question
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opPutStatic(TypeBearer type) {
+    switch (type.getBasicType()) {
+      case Type.BT_INT:
+        return PUT_STATIC_INT;
+      case Type.BT_LONG:
+        return PUT_STATIC_LONG;
+      case Type.BT_FLOAT:
+        return PUT_STATIC_FLOAT;
+      case Type.BT_DOUBLE:
+        return PUT_STATIC_DOUBLE;
+      case Type.BT_OBJECT:
+        return PUT_STATIC_OBJECT;
+      case Type.BT_BOOLEAN:
+        return PUT_STATIC_BOOLEAN;
+      case Type.BT_BYTE:
+        return PUT_STATIC_BYTE;
+      case Type.BT_CHAR:
+        return PUT_STATIC_CHAR;
+      case Type.BT_SHORT:
+        return PUT_STATIC_SHORT;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * Returns the appropriate {@code invoke-static} rop for the
+   * given type. The result is typically a newly-allocated instance.
+   *
+   * @param meth {@code non-null;} descriptor of the method
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opInvokeStatic(Prototype meth) {
+    return new Rop(RegOps.INVOKE_STATIC, meth.getParameterFrameTypes(), StdTypeList.THROWABLE);
+  }
+
+  /**
+   * Returns the appropriate {@code invoke-virtual} rop for the
+   * given type. The result is typically a newly-allocated instance.
+   *
+   * @param meth {@code non-null;} descriptor of the method, including the
+   * {@code this} parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opInvokeVirtual(Prototype meth) {
+    return new Rop(RegOps.INVOKE_VIRTUAL, meth.getParameterFrameTypes(), StdTypeList.THROWABLE);
+  }
+
+  /**
+   * Returns the appropriate {@code invoke-super} rop for the
+   * given type. The result is typically a newly-allocated instance.
+   *
+   * @param meth {@code non-null;} descriptor of the method, including the
+   * {@code this} parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opInvokeSuper(Prototype meth) {
+    return new Rop(RegOps.INVOKE_SUPER, meth.getParameterFrameTypes(), StdTypeList.THROWABLE);
+  }
+
+  /**
+   * Returns the appropriate {@code invoke-direct} rop for the
+   * given type. The result is typically a newly-allocated instance.
+   *
+   * @param meth {@code non-null;} descriptor of the method, including the
+   * {@code this} parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opInvokeDirect(Prototype meth) {
+    return new Rop(RegOps.INVOKE_DIRECT, meth.getParameterFrameTypes(), StdTypeList.THROWABLE);
+  }
+
+  /**
+   * Returns the appropriate {@code invoke-interface} rop for the
+   * given type. The result is typically a newly-allocated instance.
+   *
+   * @param meth {@code non-null;} descriptor of the method, including the
+   * {@code this} parameter
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opInvokeInterface(Prototype meth) {
+    return new Rop(RegOps.INVOKE_INTERFACE, meth.getParameterFrameTypes(), StdTypeList.THROWABLE);
+  }
+
+  /**
+   * Returns the appropriate {@code mark-local} rop for the given type.
+   * The result is a shared instance.
+   *
+   * @param type {@code non-null;} type of value being marked
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static Rop opMarkLocal(TypeBearer type) {
+    switch (type.getBasicFrameType()) {
+      case Type.BT_INT:
+        return MARK_LOCAL_INT;
+      case Type.BT_LONG:
+        return MARK_LOCAL_LONG;
+      case Type.BT_FLOAT:
+        return MARK_LOCAL_FLOAT;
+      case Type.BT_DOUBLE:
+        return MARK_LOCAL_DOUBLE;
+      case Type.BT_OBJECT:
+        return MARK_LOCAL_OBJECT;
+    }
+
+    return throwBadType(type);
+  }
+
+  /**
+   * This class is uninstantiable.
+   */
+  private Rops() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Throws the right exception to complain about a bogus type.
+   *
+   * @param type {@code non-null;} the bad type
+   * @return never
+   */
+  private static Rop throwBadType(TypeBearer type) {
+    throw new IllegalArgumentException("bad type: " + type);
+  }
+
+  /**
+   * Throws the right exception to complain about a bogus list of types.
+   *
+   * @param types {@code non-null;} the bad types
+   * @return never
+   */
+  private static Rop throwBadTypes(TypeList types) {
+    throw new IllegalArgumentException("bad types: " + types);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/SourcePosition.java b/dx/src/com/android/jack/dx/rop/code/SourcePosition.java
index 0c4c122..0aeea9a 100644
--- a/dx/src/com/android/jack/dx/rop/code/SourcePosition.java
+++ b/dx/src/com/android/jack/dx/rop/code/SourcePosition.java
@@ -24,145 +24,143 @@
  * line number and original bytecode address.
  */
 public final class SourcePosition {
-    /** {@code non-null;} convenient "no information known" instance */
-    public static final SourcePosition NO_INFO =
-        new SourcePosition(null, -1, -1);
+  /** {@code non-null;} convenient "no information known" instance */
+  public static final SourcePosition NO_INFO = new SourcePosition(null, -1, -1);
 
-    /** {@code null-ok;} name of the file of origin or {@code null} if unknown */
-    private final CstString sourceFile;
+  /** {@code null-ok;} name of the file of origin or {@code null} if unknown */
+  private final CstString sourceFile;
 
-    /**
-     * {@code >= -1;} the bytecode address, or {@code -1} if that
-     * information is unknown
-     */
-    private final int address;
+  /**
+   * {@code >= -1;} the bytecode address, or {@code -1} if that
+   * information is unknown
+   */
+  private final int address;
 
-    /**
-     * {@code >= -1;} the line number, or {@code -1} if that
-     * information is unknown
-     */
-    private final int line;
+  /**
+   * {@code >= -1;} the line number, or {@code -1} if that
+   * information is unknown
+   */
+  private final int line;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param sourceFile {@code null-ok;} name of the file of origin or
-     * {@code null} if unknown
-     * @param address {@code >= -1;} original bytecode address or {@code -1}
-     * if unknown
-     * @param line {@code >= -1;} original line number or {@code -1} if
-     * unknown
-     */
-    public SourcePosition(CstString sourceFile, int address, int line) {
-        if (address < -1) {
-            throw new IllegalArgumentException("address < -1");
-        }
-
-        if (line < -1) {
-            throw new IllegalArgumentException("line < -1");
-        }
-
-        this.sourceFile = sourceFile;
-        this.address = address;
-        this.line = line;
+  /**
+   * Constructs an instance.
+   *
+   * @param sourceFile {@code null-ok;} name of the file of origin or
+   * {@code null} if unknown
+   * @param address {@code >= -1;} original bytecode address or {@code -1}
+   * if unknown
+   * @param line {@code >= -1;} original line number or {@code -1} if
+   * unknown
+   */
+  public SourcePosition(CstString sourceFile, int address, int line) {
+    if (address < -1) {
+      throw new IllegalArgumentException("address < -1");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(50);
-
-        if (sourceFile != null) {
-            sb.append(sourceFile.toHuman());
-            sb.append(":");
-        }
-
-        if (line >= 0) {
-            sb.append(line);
-        }
-
-        sb.append('@');
-
-        if (address < 0) {
-            sb.append("????");
-        } else {
-            sb.append(Hex.u2(address));
-        }
-
-        return sb.toString();
+    if (line < -1) {
+      throw new IllegalArgumentException("line < -1");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof SourcePosition)) {
-            return false;
-        }
+    this.sourceFile = sourceFile;
+    this.address = address;
+    this.line = line;
+  }
 
-        if (this == other) {
-            return true;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(50);
 
-        SourcePosition pos = (SourcePosition) other;
-
-        return (address == pos.address) && sameLineAndFile(pos);
+    if (sourceFile != null) {
+      sb.append(sourceFile.toHuman());
+      sb.append(":");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return sourceFile.hashCode() + address + line;
+    if (line >= 0) {
+      sb.append(line);
     }
 
-    /**
-     * Returns whether the lines match between this instance and
-     * the one given.
-     *
-     * @param other {@code non-null;} the instance to compare to
-     * @return {@code true} iff the lines match
-     */
-    public boolean sameLine(SourcePosition other) {
-        return (line == other.line);
+    sb.append('@');
+
+    if (address < 0) {
+      sb.append("????");
+    } else {
+      sb.append(Hex.u2(address));
     }
 
-    /**
-     * Returns whether the lines and files match between this instance and
-     * the one given.
-     *
-     * @param other {@code non-null;} the instance to compare to
-     * @return {@code true} iff the lines and files match
-     */
-    public boolean sameLineAndFile(SourcePosition other) {
-        return (line == other.line) &&
-            ((sourceFile == other.sourceFile) ||
-             ((sourceFile != null) && sourceFile.equals(other.sourceFile)));
+    return sb.toString();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof SourcePosition)) {
+      return false;
     }
 
-    /**
-     * Gets the source file, if known.
-     *
-     * @return {@code null-ok;} the source file or {@code null} if unknown
-     */
-    public CstString getSourceFile() {
-        return sourceFile;
+    if (this == other) {
+      return true;
     }
 
-    /**
-     * Gets the original bytecode address.
-     *
-     * @return {@code >= -1;} the address or {@code -1} if unknown
-     */
-    public int getAddress() {
-        return address;
-    }
+    SourcePosition pos = (SourcePosition) other;
 
-    /**
-     * Gets the original line number.
-     *
-     * @return {@code >= -1;} the original line number or {@code -1} if
-     * unknown
-     */
-    public int getLine() {
-        return line;
-    }
+    return (address == pos.address) && sameLineAndFile(pos);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return sourceFile.hashCode() + address + line;
+  }
+
+  /**
+   * Returns whether the lines match between this instance and
+   * the one given.
+   *
+   * @param other {@code non-null;} the instance to compare to
+   * @return {@code true} iff the lines match
+   */
+  public boolean sameLine(SourcePosition other) {
+    return (line == other.line);
+  }
+
+  /**
+   * Returns whether the lines and files match between this instance and
+   * the one given.
+   *
+   * @param other {@code non-null;} the instance to compare to
+   * @return {@code true} iff the lines and files match
+   */
+  public boolean sameLineAndFile(SourcePosition other) {
+    return (line == other.line) && ((sourceFile == other.sourceFile)
+        || ((sourceFile != null) && sourceFile.equals(other.sourceFile)));
+  }
+
+  /**
+   * Gets the source file, if known.
+   *
+   * @return {@code null-ok;} the source file or {@code null} if unknown
+   */
+  public CstString getSourceFile() {
+    return sourceFile;
+  }
+
+  /**
+   * Gets the original bytecode address.
+   *
+   * @return {@code >= -1;} the address or {@code -1} if unknown
+   */
+  public int getAddress() {
+    return address;
+  }
+
+  /**
+   * Gets the original line number.
+   *
+   * @return {@code >= -1;} the original line number or {@code -1} if
+   * unknown
+   */
+  public int getLine() {
+    return line;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/SwitchInsn.java b/dx/src/com/android/jack/dx/rop/code/SwitchInsn.java
index a91b624..81e286b 100644
--- a/dx/src/com/android/jack/dx/rop/code/SwitchInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/SwitchInsn.java
@@ -24,96 +24,89 @@
 /**
  * Instruction which contains switch cases.
  */
-public final class SwitchInsn
-        extends Insn {
-    /** {@code non-null;} list of switch cases */
-    private final IntList cases;
+public final class SwitchInsn extends Insn {
+  /** {@code non-null;} list of switch cases */
+  private final IntList cases;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param result {@code null-ok;} spec for the result, if any
-     * @param sources {@code non-null;} specs for all the sources
-     * @param cases {@code non-null;} list of switch cases
-     */
-    public SwitchInsn(Rop opcode, SourcePosition position, RegisterSpec result,
-                      RegisterSpecList sources, IntList cases) {
-        super(opcode, position, result, sources);
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param result {@code null-ok;} spec for the result, if any
+   * @param sources {@code non-null;} specs for all the sources
+   * @param cases {@code non-null;} list of switch cases
+   */
+  public SwitchInsn(Rop opcode, SourcePosition position, RegisterSpec result,
+      RegisterSpecList sources, IntList cases) {
+    super(opcode, position, result, sources);
 
-        if (opcode.getBranchingness() != Rop.BRANCH_SWITCH) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
-
-        if (cases == null) {
-            throw new NullPointerException("cases == null");
-        }
-
-        this.cases = cases;
+    if (opcode.getBranchingness() != Rop.BRANCH_SWITCH) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String getInlineString() {
-        return cases.toString();
+    if (cases == null) {
+      throw new NullPointerException("cases == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return StdTypeList.EMPTY;
-    }
+    this.cases = cases;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitSwitchInsn(this);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String getInlineString() {
+    return cases.toString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        throw new UnsupportedOperationException("unsupported");
-    }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return StdTypeList.EMPTY;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new SwitchInsn(getOpcode(), getPosition(),
-                              getResult().withOffset(delta),
-                              getSources().withOffset(delta),
-                              cases);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitSwitchInsn(this);
+  }
 
-    /**
-     * {@inheritDoc}
-     *
-     * <p> SwitchInsn always compares false. The current use for this method
-     * never encounters {@code SwitchInsn}s
-     */
-    @Override
-    public boolean contentEquals(Insn b) {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    throw new UnsupportedOperationException("unsupported");
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new SwitchInsn(getOpcode(), getPosition(), getResult().withOffset(delta),
+        getSources().withOffset(delta), cases);
+  }
 
-        return new SwitchInsn(getOpcode(), getPosition(),
-                              result,
-                              sources,
-                              cases);
-    }
+  /**
+   * {@inheritDoc}
+   *
+   * <p> SwitchInsn always compares false. The current use for this method
+   * never encounters {@code SwitchInsn}s
+   */
+  @Override
+  public boolean contentEquals(Insn b) {
+    return false;
+  }
 
-    /**
-     * Gets the list of switch cases.
-     *
-     * @return {@code non-null;} the case list
-     */
-    public IntList getCases() {
-        return cases;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
+
+    return new SwitchInsn(getOpcode(), getPosition(), result, sources, cases);
+  }
+
+  /**
+   * Gets the list of switch cases.
+   *
+   * @return {@code non-null;} the case list
+   */
+  public IntList getCases() {
+    return cases;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/ThrowingCstInsn.java b/dx/src/com/android/jack/dx/rop/code/ThrowingCstInsn.java
index aad2a03..b8c93e8 100644
--- a/dx/src/com/android/jack/dx/rop/code/ThrowingCstInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/ThrowingCstInsn.java
@@ -25,86 +25,77 @@
  * Instruction which contains an explicit reference to a constant
  * and which might throw an exception.
  */
-public final class ThrowingCstInsn
-        extends CstInsn {
-    /** {@code non-null;} list of exceptions caught */
-    private final TypeList catches;
+public final class ThrowingCstInsn extends CstInsn {
+  /** {@code non-null;} list of exceptions caught */
+  private final TypeList catches;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param sources {@code non-null;} specs for all the sources
-     * @param catches {@code non-null;} list of exceptions caught
-     * @param cst {@code non-null;} the constant
-     */
-    public ThrowingCstInsn(Rop opcode, SourcePosition position,
-                           RegisterSpecList sources,
-                           TypeList catches, Constant cst) {
-        super(opcode, position, null, sources, cst);
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param sources {@code non-null;} specs for all the sources
+   * @param catches {@code non-null;} list of exceptions caught
+   * @param cst {@code non-null;} the constant
+   */
+  public ThrowingCstInsn(Rop opcode, SourcePosition position, RegisterSpecList sources,
+      TypeList catches, Constant cst) {
+    super(opcode, position, null, sources, cst);
 
-        if (opcode.getBranchingness() != Rop.BRANCH_THROW) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
-
-        if (catches == null) {
-            throw new NullPointerException("catches == null");
-        }
-
-        this.catches = catches;
+    if (opcode.getBranchingness() != Rop.BRANCH_THROW) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String getInlineString() {
-        Constant cst = getConstant();
-        String constantString = cst.toHuman();
-        if (cst instanceof CstString) {
-            constantString = ((CstString) cst).toQuoted();
-        }
-        return constantString + " " + ThrowingInsn.toCatchString(catches);
+    if (catches == null) {
+      throw new NullPointerException("catches == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return catches;
-    }
+    this.catches = catches;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitThrowingCstInsn(this);
+  /** {@inheritDoc} */
+  @Override
+  public String getInlineString() {
+    Constant cst = getConstant();
+    String constantString = cst.toHuman();
+    if (cst instanceof CstString) {
+      constantString = ((CstString) cst).toQuoted();
     }
+    return constantString + " " + ThrowingInsn.toCatchString(catches);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        return new ThrowingCstInsn(getOpcode(), getPosition(),
-                                   getSources(), catches.withAddedType(type),
-                                   getConstant());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return catches;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new ThrowingCstInsn(getOpcode(), getPosition(),
-                                   getSources().withOffset(delta),
-                                   catches,
-                                   getConstant());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitThrowingCstInsn(this);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    return new ThrowingCstInsn(getOpcode(), getPosition(), getSources(),
+        catches.withAddedType(type), getConstant());
+  }
 
-        return new ThrowingCstInsn(getOpcode(), getPosition(),
-                                   sources,
-                                   catches,
-                                   getConstant());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new ThrowingCstInsn(getOpcode(), getPosition(), getSources().withOffset(delta), catches,
+        getConstant());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
+
+    return new ThrowingCstInsn(getOpcode(), getPosition(), sources, catches, getConstant());
+  }
 
 
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/ThrowingInsn.java b/dx/src/com/android/jack/dx/rop/code/ThrowingInsn.java
index cc12194..21956cf 100644
--- a/dx/src/com/android/jack/dx/rop/code/ThrowingInsn.java
+++ b/dx/src/com/android/jack/dx/rop/code/ThrowingInsn.java
@@ -25,96 +25,88 @@
  * the list of exceptions handled by this instruction, with the
  * no-exception case appended as the final target.
  */
-public final class ThrowingInsn
-        extends Insn {
-    /** {@code non-null;} list of exceptions caught */
-    private final TypeList catches;
+public final class ThrowingInsn extends Insn {
+  /** {@code non-null;} list of exceptions caught */
+  private final TypeList catches;
 
-    /**
-     * Gets the string form of a register spec list to be used as a catches
-     * list.
-     *
-     * @param catches {@code non-null;} the catches list
-     * @return {@code non-null;} the string form
-     */
-    public static String toCatchString(TypeList catches) {
-        StringBuffer sb = new StringBuffer(100);
+  /**
+   * Gets the string form of a register spec list to be used as a catches
+   * list.
+   *
+   * @param catches {@code non-null;} the catches list
+   * @return {@code non-null;} the string form
+   */
+  public static String toCatchString(TypeList catches) {
+    StringBuffer sb = new StringBuffer(100);
 
-        sb.append("catch");
+    sb.append("catch");
 
-        int sz = catches.size();
-        for (int i = 0; i < sz; i++) {
-            sb.append(" ");
-            sb.append(catches.getType(i).toHuman());
-        }
-
-        return sb.toString();
+    int sz = catches.size();
+    for (int i = 0; i < sz; i++) {
+      sb.append(" ");
+      sb.append(catches.getType(i).toHuman());
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param position {@code non-null;} source position
-     * @param sources {@code non-null;} specs for all the sources
-     * @param catches {@code non-null;} list of exceptions caught
-     */
-    public ThrowingInsn(Rop opcode, SourcePosition position,
-                        RegisterSpecList sources,
-                        TypeList catches) {
-        super(opcode, position, null, sources);
+    return sb.toString();
+  }
 
-        if (opcode.getBranchingness() != Rop.BRANCH_THROW) {
-            throw new IllegalArgumentException("bogus branchingness");
-        }
+  /**
+   * Constructs an instance.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param position {@code non-null;} source position
+   * @param sources {@code non-null;} specs for all the sources
+   * @param catches {@code non-null;} list of exceptions caught
+   */
+  public ThrowingInsn(Rop opcode, SourcePosition position, RegisterSpecList sources,
+      TypeList catches) {
+    super(opcode, position, null, sources);
 
-        if (catches == null) {
-            throw new NullPointerException("catches == null");
-        }
-
-        this.catches = catches;
+    if (opcode.getBranchingness() != Rop.BRANCH_THROW) {
+      throw new IllegalArgumentException("bogus branchingness");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String getInlineString() {
-        return toCatchString(catches);
+    if (catches == null) {
+      throw new NullPointerException("catches == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public TypeList getCatches() {
-        return catches;
-    }
+    this.catches = catches;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor visitor) {
-        visitor.visitThrowingInsn(this);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String getInlineString() {
+    return toCatchString(catches);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withAddedCatch(Type type) {
-        return new ThrowingInsn(getOpcode(), getPosition(),
-                                getSources(), catches.withAddedType(type));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList getCatches() {
+    return catches;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withRegisterOffset(int delta) {
-        return new ThrowingInsn(getOpcode(), getPosition(),
-                                getSources().withOffset(delta),
-                                catches);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor visitor) {
+    visitor.visitThrowingInsn(this);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn withNewRegisters(RegisterSpec result,
-            RegisterSpecList sources) {
+  /** {@inheritDoc} */
+  @Override
+  public Insn withAddedCatch(Type type) {
+    return new ThrowingInsn(getOpcode(), getPosition(), getSources(), catches.withAddedType(type));
+  }
 
-        return new ThrowingInsn(getOpcode(), getPosition(),
-                                sources,
-                                catches);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Insn withRegisterOffset(int delta) {
+    return new ThrowingInsn(getOpcode(), getPosition(), getSources().withOffset(delta), catches);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn withNewRegisters(RegisterSpec result, RegisterSpecList sources) {
+
+    return new ThrowingInsn(getOpcode(), getPosition(), sources, catches);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/code/TranslationAdvice.java b/dx/src/com/android/jack/dx/rop/code/TranslationAdvice.java
index 32936ba..af78386 100644
--- a/dx/src/com/android/jack/dx/rop/code/TranslationAdvice.java
+++ b/dx/src/com/android/jack/dx/rop/code/TranslationAdvice.java
@@ -23,40 +23,39 @@
  * the early stage code be explicitly tied to the target.
  */
 public interface TranslationAdvice {
-    /**
-     * Returns an indication of whether the target can directly represent an
-     * instruction with the given opcode operating on the given arguments,
-     * where the last source argument is used as a constant. (That is, the
-     * last argument must have a type which indicates it is a known constant.)
-     * The instruction associated must have exactly two sources.
-     *
-     * @param opcode {@code non-null;} the opcode
-     * @param sourceA {@code non-null;} the first source
-     * @param sourceB {@code non-null;} the second source
-     * @return {@code true} iff the target can represent the operation
-     * using a constant for the last argument
-     */
-    public boolean hasConstantOperation(Rop opcode,
-            RegisterSpec sourceA, RegisterSpec sourceB);
+  /**
+   * Returns an indication of whether the target can directly represent an
+   * instruction with the given opcode operating on the given arguments,
+   * where the last source argument is used as a constant. (That is, the
+   * last argument must have a type which indicates it is a known constant.)
+   * The instruction associated must have exactly two sources.
+   *
+   * @param opcode {@code non-null;} the opcode
+   * @param sourceA {@code non-null;} the first source
+   * @param sourceB {@code non-null;} the second source
+   * @return {@code true} iff the target can represent the operation
+   * using a constant for the last argument
+   */
+  public boolean hasConstantOperation(Rop opcode, RegisterSpec sourceA, RegisterSpec sourceB);
 
-    /**
-     * Returns true if the translation target requires the sources of the
-     * specified opcode to be in order and contiguous (eg, for an invoke-range)
-     *
-     * @param opcode {@code non-null;} opcode
-     * @param sources {@code non-null;} source list
-     * @return {@code true} iff the target requires the sources to be
-     * in order and contiguous.
-     */
-    public boolean requiresSourcesInOrder(Rop opcode, RegisterSpecList sources);
+  /**
+   * Returns true if the translation target requires the sources of the
+   * specified opcode to be in order and contiguous (eg, for an invoke-range)
+   *
+   * @param opcode {@code non-null;} opcode
+   * @param sources {@code non-null;} source list
+   * @return {@code true} iff the target requires the sources to be
+   * in order and contiguous.
+   */
+  public boolean requiresSourcesInOrder(Rop opcode, RegisterSpecList sources);
 
-    /**
-     * Gets the maximum register width that can be represented optimally.
-     * For example, Dex bytecode does not have instruction forms that take
-     * register numbers larger than 15 for all instructions so
-     * DexTranslationAdvice returns 15 here.
-     *
-     * @return register count noted above
-     */
-    public int getMaxOptimalRegisterCount();
+  /**
+   * Gets the maximum register width that can be represented optimally.
+   * For example, Dex bytecode does not have instruction forms that take
+   * register numbers larger than 15 for all instructions so
+   * DexTranslationAdvice returns 15 here.
+   *
+   * @return register count noted above
+   */
+  public int getMaxOptimalRegisterCount();
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/Constant.java b/dx/src/com/android/jack/dx/rop/cst/Constant.java
index 7c756e2..a0d572d 100644
--- a/dx/src/com/android/jack/dx/rop/cst/Constant.java
+++ b/dx/src/com/android/jack/dx/rop/cst/Constant.java
@@ -21,48 +21,48 @@
 /**
  * Base class for constants of all sorts.
  */
-public abstract class Constant
-        implements ToHuman, Comparable<Constant> {
-    /**
-     * Returns {@code true} if this instance is a category-2 constant,
-     * meaning it takes up two slots in the constant pool, or
-     * {@code false} if this instance is category-1.
-     *
-     * @return {@code true} iff this instance is category-2
-     */
-    public abstract boolean isCategory2();
+public abstract class Constant implements ToHuman, Comparable<Constant> {
+  /**
+   * Returns {@code true} if this instance is a category-2 constant,
+   * meaning it takes up two slots in the constant pool, or
+   * {@code false} if this instance is category-1.
+   *
+   * @return {@code true} iff this instance is category-2
+   */
+  public abstract boolean isCategory2();
 
-    /**
-     * Returns the human name for the particular type of constant
-     * this instance is.
-     *
-     * @return {@code non-null;} the name
-     */
-    public abstract String typeName();
+  /**
+   * Returns the human name for the particular type of constant
+   * this instance is.
+   *
+   * @return {@code non-null;} the name
+   */
+  public abstract String typeName();
 
-    /**
-     * {@inheritDoc}
-     *
-     * This compares in class-major and value-minor order.
-     */
-    public final int compareTo(Constant other) {
-        Class clazz = getClass();
-        Class otherClazz = other.getClass();
+  /**
+   * {@inheritDoc}
+   *
+   * This compares in class-major and value-minor order.
+   */
+  @Override
+  public final int compareTo(Constant other) {
+    Class<? extends Constant> clazz = getClass();
+    Class<? extends Constant> otherClazz = other.getClass();
 
-        if (clazz != otherClazz) {
-            return clazz.getName().compareTo(otherClazz.getName());
-        }
-
-        return compareTo0(other);
+    if (clazz != otherClazz) {
+      return clazz.getName().compareTo(otherClazz.getName());
     }
 
-    /**
-     * Compare the values of this and another instance, which are guaranteed
-     * to be of the same class. Subclasses must implement this.
-     *
-     * @param other {@code non-null;} the instance to compare to
-     * @return {@code -1}, {@code 0}, or {@code 1}, as usual
-     * for a comparison
-     */
-    protected abstract int compareTo0(Constant other);
+    return compareTo0(other);
+  }
+
+  /**
+   * Compare the values of this and another instance, which are guaranteed
+   * to be of the same class. Subclasses must implement this.
+   *
+   * @param other {@code non-null;} the instance to compare to
+   * @return {@code -1}, {@code 0}, or {@code 1}, as usual
+   * for a comparison
+   */
+  protected abstract int compareTo0(Constant other);
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/ConstantPool.java b/dx/src/com/android/jack/dx/rop/cst/ConstantPool.java
index 218f3c4..c1099fe 100644
--- a/dx/src/com/android/jack/dx/rop/cst/ConstantPool.java
+++ b/dx/src/com/android/jack/dx/rop/cst/ConstantPool.java
@@ -21,50 +21,50 @@
  * {@link Constant} objects.
  */
 public interface ConstantPool {
-    /**
-     * Get the "size" of the constant pool. This corresponds to the
-     * class file field {@code constant_pool_count}, and is in fact
-     * always at least one more than the actual size of the constant pool,
-     * as element {@code 0} is always invalid.
-     *
-     * @return {@code >= 1;} the size
-     */
-    public int size();
+  /**
+   * Get the "size" of the constant pool. This corresponds to the
+   * class file field {@code constant_pool_count}, and is in fact
+   * always at least one more than the actual size of the constant pool,
+   * as element {@code 0} is always invalid.
+   *
+   * @return {@code >= 1;} the size
+   */
+  public int size();
 
-    /**
-     * Get the {@code n}th entry in the constant pool, which must
-     * be valid.
-     *
-     * @param n {@code n >= 0, n < size();} the constant pool index
-     * @return {@code non-null;} the corresponding entry
-     * @throws IllegalArgumentException thrown if {@code n} is
-     * in-range but invalid
-     */
-    public Constant get(int n);
+  /**
+   * Get the {@code n}th entry in the constant pool, which must
+   * be valid.
+   *
+   * @param n {@code n >= 0, n < size();} the constant pool index
+   * @return {@code non-null;} the corresponding entry
+   * @throws IllegalArgumentException thrown if {@code n} is
+   * in-range but invalid
+   */
+  public Constant get(int n);
 
-    /**
-     * Get the {@code n}th entry in the constant pool, which must
-     * be valid unless {@code n == 0}, in which case {@code null}
-     * is returned.
-     *
-     * @param n {@code n >= 0, n < size();} the constant pool index
-     * @return {@code null-ok;} the corresponding entry, if {@code n != 0}
-     * @throws IllegalArgumentException thrown if {@code n} is
-     * in-range and non-zero but invalid
-     */
-    public Constant get0Ok(int n);
+  /**
+   * Get the {@code n}th entry in the constant pool, which must
+   * be valid unless {@code n == 0}, in which case {@code null}
+   * is returned.
+   *
+   * @param n {@code n >= 0, n < size();} the constant pool index
+   * @return {@code null-ok;} the corresponding entry, if {@code n != 0}
+   * @throws IllegalArgumentException thrown if {@code n} is
+   * in-range and non-zero but invalid
+   */
+  public Constant get0Ok(int n);
 
-    /**
-     * Get the {@code n}th entry in the constant pool, or
-     * {@code null} if the index is in-range but invalid. In
-     * particular, {@code null} is returned for index {@code 0}
-     * as well as the index after any entry which is defined to take up
-     * two slots (that is, {@code Long} and {@code Double}
-     * entries).
-     *
-     * @param n {@code n >= 0, n < size();} the constant pool index
-     * @return {@code null-ok;} the corresponding entry, or {@code null} if
-     * the index is in-range but invalid
-     */
-    public Constant getOrNull(int n);
+  /**
+   * Get the {@code n}th entry in the constant pool, or
+   * {@code null} if the index is in-range but invalid. In
+   * particular, {@code null} is returned for index {@code 0}
+   * as well as the index after any entry which is defined to take up
+   * two slots (that is, {@code Long} and {@code Double}
+   * entries).
+   *
+   * @param n {@code n >= 0, n < size();} the constant pool index
+   * @return {@code null-ok;} the corresponding entry, or {@code null} if
+   * the index is in-range but invalid
+   */
+  public Constant getOrNull(int n);
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstAnnotation.java b/dx/src/com/android/jack/dx/rop/cst/CstAnnotation.java
index 84dd61f..87a97ca 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstAnnotation.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstAnnotation.java
@@ -22,75 +22,76 @@
  * Constant type that represents an annotation.
  */
 public final class CstAnnotation extends Constant {
-    /** {@code non-null;} the actual annotation */
-    private final Annotation annotation;
+  /** {@code non-null;} the actual annotation */
+  private final Annotation annotation;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param annotation {@code non-null;} the annotation to hold
-     */
-    public CstAnnotation(Annotation annotation) {
-        if (annotation == null) {
-            throw new NullPointerException("annotation == null");
-        }
-
-        annotation.throwIfMutable();
-
-        this.annotation = annotation;
+  /**
+   * Constructs an instance.
+   *
+   * @param annotation {@code non-null;} the annotation to hold
+   */
+  public CstAnnotation(Annotation annotation) {
+    if (annotation == null) {
+      throw new NullPointerException("annotation == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (! (other instanceof CstAnnotation)) {
-            return false;
-        }
+    annotation.throwIfMutable();
 
-        return annotation.equals(((CstAnnotation) other).annotation);
+    this.annotation = annotation;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof CstAnnotation)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return annotation.hashCode();
-    }
+    return annotation.equals(((CstAnnotation) other).annotation);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        return annotation.compareTo(((CstAnnotation) other).annotation);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return annotation.hashCode();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return annotation.toString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    return annotation.compareTo(((CstAnnotation) other).annotation);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "annotation";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return annotation.toString();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "annotation";
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return annotation.toString();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
 
-    /**
-     * Get the underlying annotation.
-     *
-     * @return {@code non-null;} the annotation
-     */
-    public Annotation getAnnotation() {
-        return annotation;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return annotation.toString();
+  }
+
+  /**
+   * Get the underlying annotation.
+   *
+   * @return {@code non-null;} the annotation
+   */
+  public Annotation getAnnotation() {
+    return annotation;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstArray.java b/dx/src/com/android/jack/dx/rop/cst/CstArray.java
index 080bb69..4d1c745 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstArray.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstArray.java
@@ -16,144 +16,144 @@
 
 package com.android.jack.dx.rop.cst;
 
-import com.android.jack.dx.rop.type.Type;
 import com.android.jack.dx.util.FixedSizeList;
 
 /**
  * Constant type to represent a fixed array of other constants.
  */
 public final class CstArray extends Constant {
-    /** {@code non-null;} the actual list of contents */
-    private final List list;
+  /** {@code non-null;} the actual list of contents */
+  private final List list;
 
+  /**
+   * Constructs an instance.
+   *
+   * @param list {@code non-null;} the actual list of contents
+   */
+  public CstArray(List list) {
+    if (list == null) {
+      throw new NullPointerException("list == null");
+    }
+
+    list.throwIfMutable();
+
+    this.list = list;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof CstArray)) {
+      return false;
+    }
+
+    return list.equals(((CstArray) other).list);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return list.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    return list.compareTo(((CstArray) other).list);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return list.toString("array{", ", ", "}");
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "array";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return list.toHuman("{", ", ", "}");
+  }
+
+  /**
+   * Get the underlying list.
+   *
+   * @return {@code non-null;} the list
+   */
+  public List getList() {
+    return list;
+  }
+
+  /**
+   * List of {@link Constant} instances.
+   */
+  public static final class List extends FixedSizeList implements Comparable<List> {
     /**
-     * Constructs an instance.
+     * Constructs an instance. All indices initially contain
+     * {@code null}.
      *
-     * @param list {@code non-null;} the actual list of contents
+     * @param size the size of the list
      */
-    public CstArray(List list) {
-        if (list == null) {
-            throw new NullPointerException("list == null");
+    public List(int size) {
+      super(size);
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public int compareTo(List other) {
+      int thisSize = size();
+      int otherSize = other.size();
+      int compareSize = (thisSize < otherSize) ? thisSize : otherSize;
+
+      for (int i = 0; i < compareSize; i++) {
+        Constant thisItem = (Constant) get0(i);
+        Constant otherItem = (Constant) other.get0(i);
+        int compare = thisItem.compareTo(otherItem);
+        if (compare != 0) {
+          return compare;
         }
+      }
 
-        list.throwIfMutable();
+      if (thisSize < otherSize) {
+        return -1;
+      } else if (thisSize > otherSize) {
+        return 1;
+      }
 
-        this.list = list;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (! (other instanceof CstArray)) {
-            return false;
-        }
-
-        return list.equals(((CstArray) other).list);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return list.hashCode();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        return list.compareTo(((CstArray) other).list);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return list.toString("array{", ", ", "}");
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "array";
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return list.toHuman("{", ", ", "}");
+      return 0;
     }
 
     /**
-     * Get the underlying list.
+     * Gets the element at the given index. It is an error to call
+     * this with the index for an element which was never set; if you
+     * do that, this will throw {@code NullPointerException}.
      *
-     * @return {@code non-null;} the list
+     * @param n {@code >= 0, < size();} which index
+     * @return {@code non-null;} element at that index
      */
-    public List getList() {
-        return list;
+    public Constant get(int n) {
+      return (Constant) get0(n);
     }
 
     /**
-     * List of {@link Constant} instances.
+     * Sets the element at the given index.
+     *
+     * @param n {@code >= 0, < size();} which index
+     * @param a {@code null-ok;} the element to set at {@code n}
      */
-    public static final class List
-            extends FixedSizeList implements Comparable<List> {
-        /**
-         * Constructs an instance. All indices initially contain
-         * {@code null}.
-         *
-         * @param size the size of the list
-         */
-        public List(int size) {
-            super(size);
-        }
-
-        /** {@inheritDoc} */
-        public int compareTo(List other) {
-            int thisSize = size();
-            int otherSize = other.size();
-            int compareSize = (thisSize < otherSize) ? thisSize : otherSize;
-
-            for (int i = 0; i < compareSize; i++) {
-                Constant thisItem = (Constant) get0(i);
-                Constant otherItem = (Constant) other.get0(i);
-                int compare = thisItem.compareTo(otherItem);
-                if (compare != 0) {
-                    return compare;
-                }
-            }
-
-            if (thisSize < otherSize) {
-                return -1;
-            } else if (thisSize > otherSize) {
-                return 1;
-            }
-
-            return 0;
-        }
-
-        /**
-         * Gets the element at the given index. It is an error to call
-         * this with the index for an element which was never set; if you
-         * do that, this will throw {@code NullPointerException}.
-         *
-         * @param n {@code >= 0, < size();} which index
-         * @return {@code non-null;} element at that index
-         */
-        public Constant get(int n) {
-            return (Constant) get0(n);
-        }
-
-        /**
-         * Sets the element at the given index.
-         *
-         * @param n {@code >= 0, < size();} which index
-         * @param a {@code null-ok;} the element to set at {@code n}
-         */
-        public void set(int n, Constant a) {
-            set0(n, a);
-        }
+    public void set(int n, Constant a) {
+      set0(n, a);
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstBaseMethodRef.java b/dx/src/com/android/jack/dx/rop/cst/CstBaseMethodRef.java
index fedb208..1ba7d88 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstBaseMethodRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstBaseMethodRef.java
@@ -18,134 +18,133 @@
 
 import com.android.jack.dx.rop.type.Prototype;
 import com.android.jack.dx.rop.type.Type;
-import com.android.jack.dx.rop.type.TypeBearer;
 
 /**
  * Base class for constants of "methodish" type.
  *
- * <p><b>Note:</b> As a {@link TypeBearer}, this class bears the return type
+ * <p><b>Note:</b> As a {@code TypeBearer}, this class bears the return type
  * of the method.</p>
  */
-public abstract class CstBaseMethodRef
-        extends CstMemberRef {
-    /** {@code non-null;} the raw prototype for this method */
-    private final Prototype prototype;
+public abstract class CstBaseMethodRef extends CstMemberRef {
+  /** {@code non-null;} the raw prototype for this method */
+  private final Prototype prototype;
 
-    /**
-     * {@code null-ok;} the prototype for this method taken to be an instance
-     * method, or {@code null} if not yet calculated
-     */
-    private Prototype instancePrototype;
+  /**
+   * {@code null-ok;} the prototype for this method taken to be an instance
+   * method, or {@code null} if not yet calculated
+   */
+  private Prototype instancePrototype;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param definingClass {@code non-null;} the type of the defining class
-     * @param nat {@code non-null;} the name-and-type
-     */
-    /*package*/ CstBaseMethodRef(CstType definingClass, CstNat nat) {
-        super(definingClass, nat);
+  /**
+   * Constructs an instance.
+   *
+   * @param definingClass {@code non-null;} the type of the defining class
+   * @param nat {@code non-null;} the name-and-type
+   */
+  /*package*/CstBaseMethodRef(CstType definingClass, CstNat nat) {
+    super(definingClass, nat);
 
-        String descriptor = getNat().getDescriptor().getString();
-        this.prototype = Prototype.intern(descriptor);
-        this.instancePrototype = null;
+    String descriptor = getNat().getDescriptor().getString();
+    this.prototype = Prototype.intern(descriptor);
+    this.instancePrototype = null;
+  }
+
+  /**
+   * Gets the raw prototype of this method. This doesn't include a
+   * {@code this} argument.
+   *
+   * @return {@code non-null;} the method prototype
+   */
+  public final Prototype getPrototype() {
+    return prototype;
+  }
+
+  /**
+   * Gets the prototype of this method as either a
+   * {@code static} or instance method. In the case of a
+   * {@code static} method, this is the same as the raw
+   * prototype. In the case of an instance method, this has an
+   * appropriately-typed {@code this} argument as the first
+   * one.
+   *
+   * @param isStatic whether the method should be considered static
+   * @return {@code non-null;} the method prototype
+   */
+  public final Prototype getPrototype(boolean isStatic) {
+    if (isStatic) {
+      return prototype;
+    } else {
+      if (instancePrototype == null) {
+        Type thisType = getDefiningClass().getClassType();
+        instancePrototype = prototype.withFirstParameter(thisType);
+      }
+      return instancePrototype;
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected final int compareTo0(Constant other) {
+    int cmp = super.compareTo0(other);
+
+    if (cmp != 0) {
+      return cmp;
     }
 
-    /**
-     * Gets the raw prototype of this method. This doesn't include a
-     * {@code this} argument.
-     *
-     * @return {@code non-null;} the method prototype
-     */
-    public final Prototype getPrototype() {
-        return prototype;
-    }
+    CstBaseMethodRef otherMethod = (CstBaseMethodRef) other;
+    return prototype.compareTo(otherMethod.prototype);
+  }
 
-    /**
-     * Gets the prototype of this method as either a
-     * {@code static} or instance method. In the case of a
-     * {@code static} method, this is the same as the raw
-     * prototype. In the case of an instance method, this has an
-     * appropriately-typed {@code this} argument as the first
-     * one.
-     *
-     * @param isStatic whether the method should be considered static
-     * @return {@code non-null;} the method prototype
-     */
-    public final Prototype getPrototype(boolean isStatic) {
-        if (isStatic) {
-            return prototype;
-        } else {
-            if (instancePrototype == null) {
-                Type thisType = getDefiningClass().getClassType();
-                instancePrototype = prototype.withFirstParameter(thisType);
-            }
-            return instancePrototype;
-        }
-    }
+  /**
+   * {@inheritDoc}
+   *
+   * In this case, this method returns the <i>return type</i> of this method.
+   *
+   * @return {@code non-null;} the method's return type
+   */
+  @Override
+  public final Type getType() {
+    return prototype.getReturnType();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected final int compareTo0(Constant other) {
-        int cmp = super.compareTo0(other);
+  /**
+   * Gets the number of words of parameters required by this
+   * method's descriptor. Since instances of this class have no way
+   * to know if they will be used in a {@code static} or
+   * instance context, one has to indicate this explicitly as an
+   * argument. This method is just a convenient shorthand for
+   * {@code getPrototype().getParameterTypes().getWordCount()},
+   * plus {@code 1} if the method is to be treated as an
+   * instance method.
+   *
+   * @param isStatic whether the method should be considered static
+   * @return {@code >= 0;} the argument word count
+   */
+  public final int getParameterWordCount(boolean isStatic) {
+    return getPrototype(isStatic).getParameterTypes().getWordCount();
+  }
 
-        if (cmp != 0) {
-            return cmp;
-        }
+  /**
+   * Gets whether this is a reference to an instance initialization
+   * method. This is just a convenient shorthand for
+   * {@code getNat().isInstanceInit()}.
+   *
+   * @return {@code true} iff this is a reference to an
+   * instance initialization method
+   */
+  public final boolean isInstanceInit() {
+    return getNat().isInstanceInit();
+  }
 
-        CstBaseMethodRef otherMethod = (CstBaseMethodRef) other;
-        return prototype.compareTo(otherMethod.prototype);
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * In this case, this method returns the <i>return type</i> of this method.
-     *
-     * @return {@code non-null;} the method's return type
-     */
-    public final Type getType() {
-        return prototype.getReturnType();
-    }
-
-    /**
-     * Gets the number of words of parameters required by this
-     * method's descriptor. Since instances of this class have no way
-     * to know if they will be used in a {@code static} or
-     * instance context, one has to indicate this explicitly as an
-     * argument. This method is just a convenient shorthand for
-     * {@code getPrototype().getParameterTypes().getWordCount()},
-     * plus {@code 1} if the method is to be treated as an
-     * instance method.
-     *
-     * @param isStatic whether the method should be considered static
-     * @return {@code >= 0;} the argument word count
-     */
-    public final int getParameterWordCount(boolean isStatic) {
-        return getPrototype(isStatic).getParameterTypes().getWordCount();
-    }
-
-    /**
-     * Gets whether this is a reference to an instance initialization
-     * method. This is just a convenient shorthand for
-     * {@code getNat().isInstanceInit()}.
-     *
-     * @return {@code true} iff this is a reference to an
-     * instance initialization method
-     */
-    public final boolean isInstanceInit() {
-        return getNat().isInstanceInit();
-    }
-
-    /**
-     * Gets whether this is a reference to a class initialization
-     * method. This is just a convenient shorthand for
-     * {@code getNat().isClassInit()}.
-     *
-     * @return {@code true} iff this is a reference to an
-     * instance initialization method
-     */
-    public final boolean isClassInit() {
-        return getNat().isClassInit();
-    }
+  /**
+   * Gets whether this is a reference to a class initialization
+   * method. This is just a convenient shorthand for
+   * {@code getNat().isClassInit()}.
+   *
+   * @return {@code true} iff this is a reference to an
+   * instance initialization method
+   */
+  public final boolean isClassInit() {
+    return getNat().isClassInit();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstBoolean.java b/dx/src/com/android/jack/dx/rop/cst/CstBoolean.java
index 81a0e27..ad4a063 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstBoolean.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstBoolean.java
@@ -21,79 +21,80 @@
 /**
  * Constants of type {@code boolean}.
  */
-public final class CstBoolean
-        extends CstLiteral32 {
-    /** {@code non-null;} instance representing {@code false} */
-    public static final CstBoolean VALUE_FALSE = new CstBoolean(false);
+public final class CstBoolean extends CstLiteral32 {
+  /** {@code non-null;} instance representing {@code false} */
+  public static final CstBoolean VALUE_FALSE = new CstBoolean(false);
 
-    /** {@code non-null;} instance representing {@code true} */
-    public static final CstBoolean VALUE_TRUE = new CstBoolean(true);
+  /** {@code non-null;} instance representing {@code true} */
+  public static final CstBoolean VALUE_TRUE = new CstBoolean(true);
 
-    /**
-     * Makes an instance for the given value. This will return an
-     * already-allocated instance.
-     *
-     * @param value the {@code boolean} value
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstBoolean make(boolean value) {
-        return value ? VALUE_TRUE : VALUE_FALSE;
+  /**
+   * Makes an instance for the given value. This will return an
+   * already-allocated instance.
+   *
+   * @param value the {@code boolean} value
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstBoolean make(boolean value) {
+    return value ? VALUE_TRUE : VALUE_FALSE;
+  }
+
+  /**
+   * Makes an instance for the given {@code int} value. This
+   * will return an already-allocated instance.
+   *
+   * @param value must be either {@code 0} or {@code 1}
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstBoolean make(int value) {
+    if (value == 0) {
+      return VALUE_FALSE;
+    } else if (value == 1) {
+      return VALUE_TRUE;
+    } else {
+      throw new IllegalArgumentException("bogus value: " + value);
     }
+  }
 
-    /**
-     * Makes an instance for the given {@code int} value. This
-     * will return an already-allocated instance.
-     *
-     * @param value must be either {@code 0} or {@code 1}
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstBoolean make(int value) {
-        if (value == 0) {
-            return VALUE_FALSE;
-        } else if (value == 1) {
-            return VALUE_TRUE;
-        } else {
-            throw new IllegalArgumentException("bogus value: " + value);
-        }
-    }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code boolean} value
+   */
+  private CstBoolean(boolean value) {
+    super(value ? 1 : 0);
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code boolean} value
-     */
-    private CstBoolean(boolean value) {
-        super(value ? 1 : 0);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return getValue() ? "boolean{true}" : "boolean{false}";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return getValue() ? "boolean{true}" : "boolean{false}";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.BOOLEAN;
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.BOOLEAN;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "boolean";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "boolean";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return getValue() ? "true" : "false";
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return getValue() ? "true" : "false";
-    }
-
-    /**
-     * Gets the {@code boolean} value.
-     *
-     * @return the value
-     */
-    public boolean getValue() {
-        return (getIntBits() == 0) ? false : true;
-    }
+  /**
+   * Gets the {@code boolean} value.
+   *
+   * @return the value
+   */
+  public boolean getValue() {
+    return (getIntBits() == 0) ? false : true;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstByte.java b/dx/src/com/android/jack/dx/rop/cst/CstByte.java
index 5ab4188..f92bfd0 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstByte.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstByte.java
@@ -22,78 +22,78 @@
 /**
  * Constants of type {@code byte}.
  */
-public final class CstByte
-        extends CstLiteral32 {
-    /** {@code non-null;} the value {@code 0} as an instance of this class */
-    public static final CstByte VALUE_0 = make((byte) 0);
+public final class CstByte extends CstLiteral32 {
+  /** {@code non-null;} the value {@code 0} as an instance of this class */
+  public static final CstByte VALUE_0 = make((byte) 0);
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param value the {@code byte} value
-     */
-    public static CstByte make(byte value) {
-        return new CstByte(value);
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param value the {@code byte} value
+   */
+  public static CstByte make(byte value) {
+    return new CstByte(value);
+  }
+
+  /**
+   * Makes an instance for the given {@code int} value. This
+   * may (but does not necessarily) return an already-allocated
+   * instance.
+   *
+   * @param value the value, which must be in range for a {@code byte}
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstByte make(int value) {
+    byte cast = (byte) value;
+
+    if (cast != value) {
+      throw new IllegalArgumentException("bogus byte value: " + value);
     }
 
-    /**
-     * Makes an instance for the given {@code int} value. This
-     * may (but does not necessarily) return an already-allocated
-     * instance.
-     *
-     * @param value the value, which must be in range for a {@code byte}
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstByte make(int value) {
-        byte cast = (byte) value;
+    return make(cast);
+  }
 
-        if (cast != value) {
-            throw new IllegalArgumentException("bogus byte value: " +
-                    value);
-        }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code byte} value
+   */
+  private CstByte(byte value) {
+    super(value);
+  }
 
-        return make(cast);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int value = getIntBits();
+    return "byte{0x" + Hex.u1(value) + " / " + value + '}';
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code byte} value
-     */
-    private CstByte(byte value) {
-        super(value);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.BYTE;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int value = getIntBits();
-        return "byte{0x" + Hex.u1(value) + " / " + value + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "byte";
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.BYTE;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Integer.toString(getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "byte";
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Integer.toString(getIntBits());
-    }
-
-    /**
-     * Gets the {@code byte} value.
-     *
-     * @return the value
-     */
-    public byte getValue() {
-        return (byte) getIntBits();
-    }
+  /**
+   * Gets the {@code byte} value.
+   *
+   * @return the value
+   */
+  public byte getValue() {
+    return (byte) getIntBits();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstChar.java b/dx/src/com/android/jack/dx/rop/cst/CstChar.java
index b4cd303..3804542 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstChar.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstChar.java
@@ -22,78 +22,78 @@
 /**
  * Constants of type {@code char}.
  */
-public final class CstChar
-        extends CstLiteral32 {
-    /** {@code non-null;} the value {@code 0} as an instance of this class */
-    public static final CstChar VALUE_0 = make((char) 0);
+public final class CstChar extends CstLiteral32 {
+  /** {@code non-null;} the value {@code 0} as an instance of this class */
+  public static final CstChar VALUE_0 = make((char) 0);
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param value the {@code char} value
-     */
-    public static CstChar make(char value) {
-        return new CstChar(value);
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param value the {@code char} value
+   */
+  public static CstChar make(char value) {
+    return new CstChar(value);
+  }
+
+  /**
+   * Makes an instance for the given {@code int} value. This
+   * may (but does not necessarily) return an already-allocated
+   * instance.
+   *
+   * @param value the value, which must be in range for a {@code char}
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstChar make(int value) {
+    char cast = (char) value;
+
+    if (cast != value) {
+      throw new IllegalArgumentException("bogus char value: " + value);
     }
 
-    /**
-     * Makes an instance for the given {@code int} value. This
-     * may (but does not necessarily) return an already-allocated
-     * instance.
-     *
-     * @param value the value, which must be in range for a {@code char}
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstChar make(int value) {
-        char cast = (char) value;
+    return make(cast);
+  }
 
-        if (cast != value) {
-            throw new IllegalArgumentException("bogus char value: " +
-                    value);
-        }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code char} value
+   */
+  private CstChar(char value) {
+    super(value);
+  }
 
-        return make(cast);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int value = getIntBits();
+    return "char{0x" + Hex.u2(value) + " / " + value + '}';
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code char} value
-     */
-    private CstChar(char value) {
-        super(value);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.CHAR;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int value = getIntBits();
-        return "char{0x" + Hex.u2(value) + " / " + value + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "char";
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.CHAR;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Integer.toString(getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "char";
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Integer.toString(getIntBits());
-    }
-
-    /**
-     * Gets the {@code char} value.
-     *
-     * @return the value
-     */
-    public char getValue() {
-        return (char) getIntBits();
-    }
+  /**
+   * Gets the {@code char} value.
+   *
+   * @return the value
+   */
+  public char getValue() {
+    return (char) getIntBits();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstDouble.java b/dx/src/com/android/jack/dx/rop/cst/CstDouble.java
index c000e6a..46d4c72 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstDouble.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstDouble.java
@@ -22,69 +22,67 @@
 /**
  * Constants of type {@code CONSTANT_Double_info}.
  */
-public final class CstDouble
-        extends CstLiteral64 {
-    /** {@code non-null;} instance representing {@code 0} */
-    public static final CstDouble VALUE_0 =
-        new CstDouble(Double.doubleToLongBits(0.0));
+public final class CstDouble extends CstLiteral64 {
+  /** {@code non-null;} instance representing {@code 0} */
+  public static final CstDouble VALUE_0 = new CstDouble(Double.doubleToLongBits(0.0));
 
-    /** {@code non-null;} instance representing {@code 1} */
-    public static final CstDouble VALUE_1 =
-        new CstDouble(Double.doubleToLongBits(1.0));
+  /** {@code non-null;} instance representing {@code 1} */
+  public static final CstDouble VALUE_1 = new CstDouble(Double.doubleToLongBits(1.0));
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param bits the {@code double} value as {@code long} bits
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param bits the {@code double} value as {@code long} bits
+   */
+  public static CstDouble make(long bits) {
+    /*
+     * Note: Javadoc notwithstanding, this implementation always
+     * allocates.
      */
-    public static CstDouble make(long bits) {
-        /*
-         * Note: Javadoc notwithstanding, this implementation always
-         * allocates.
-         */
-        return new CstDouble(bits);
-    }
+    return new CstDouble(bits);
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param bits the {@code double} value as {@code long} bits
-     */
-    private CstDouble(long bits) {
-        super(bits);
-    }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param bits the {@code double} value as {@code long} bits
+   */
+  private CstDouble(long bits) {
+    super(bits);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        long bits = getLongBits();
-        return "double{0x" + Hex.u8(bits) + " / " +
-            Double.longBitsToDouble(bits) + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    long bits = getLongBits();
+    return "double{0x" + Hex.u8(bits) + " / " + Double.longBitsToDouble(bits) + '}';
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.DOUBLE;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.DOUBLE;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "double";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "double";
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Double.toString(Double.longBitsToDouble(getLongBits()));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Double.toString(Double.longBitsToDouble(getLongBits()));
+  }
 
-    /**
-     * Gets the {@code double} value.
-     *
-     * @return the value
-     */
-    public double getValue() {
-        return Double.longBitsToDouble(getLongBits());
-    }
+  /**
+   * Gets the {@code double} value.
+   *
+   * @return the value
+   */
+  public double getValue() {
+    return Double.longBitsToDouble(getLongBits());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstEnumRef.java b/dx/src/com/android/jack/dx/rop/cst/CstEnumRef.java
index 9be4634..b2528e2 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstEnumRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstEnumRef.java
@@ -23,46 +23,47 @@
  * value of an enumerated type.
  */
 public final class CstEnumRef extends CstMemberRef {
-    /** {@code null-ok;} the corresponding field ref, lazily initialized */
-    private CstFieldRef fieldRef;
+  /** {@code null-ok;} the corresponding field ref, lazily initialized */
+  private CstFieldRef fieldRef;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param nat {@code non-null;} the name-and-type; the defining class is derived
-     * from this
-     */
-    public CstEnumRef(CstNat nat) {
-        super(new CstType(nat.getFieldType()), nat);
+  /**
+   * Constructs an instance.
+   *
+   * @param nat {@code non-null;} the name-and-type; the defining class is derived
+   * from this
+   */
+  public CstEnumRef(CstNat nat) {
+    super(new CstType(nat.getFieldType()), nat);
 
-        fieldRef = null;
+    fieldRef = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "enum";
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * <b>Note:</b> This returns the enumerated type.
+   */
+  @Override
+  public Type getType() {
+    return getDefiningClass().getClassType();
+  }
+
+  /**
+   * Get a {@link CstFieldRef} that corresponds with this instance.
+   *
+   * @return {@code non-null;} the corresponding field reference
+   */
+  public CstFieldRef getFieldRef() {
+    if (fieldRef == null) {
+      fieldRef = new CstFieldRef(getDefiningClass(), getNat());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "enum";
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * <b>Note:</b> This returns the enumerated type.
-     */
-    public Type getType() {
-        return getDefiningClass().getClassType();
-    }
-
-    /**
-     * Get a {@link CstFieldRef} that corresponds with this instance.
-     *
-     * @return {@code non-null;} the corresponding field reference
-     */
-    public CstFieldRef getFieldRef() {
-        if (fieldRef == null) {
-            fieldRef = new CstFieldRef(getDefiningClass(), getNat());
-        }
-
-        return fieldRef;
-    }
+    return fieldRef;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstFieldRef.java b/dx/src/com/android/jack/dx/rop/cst/CstFieldRef.java
index 76e7f25..3121114 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstFieldRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstFieldRef.java
@@ -22,58 +22,58 @@
  * Constants of type {@code CONSTANT_Fieldref_info}.
  */
 public final class CstFieldRef extends CstMemberRef {
-    /**
-     * Returns an instance of this class that represents the static
-     * field which should hold the class corresponding to a given
-     * primitive type. For example, if given {@link Type#INT}, this
-     * method returns an instance corresponding to the field
-     * {@code java.lang.Integer.TYPE}.
-     *
-     * @param primitiveType {@code non-null;} the primitive type
-     * @return {@code non-null;} the corresponding static field
-     */
-    public static CstFieldRef forPrimitiveType(Type primitiveType) {
-        return new CstFieldRef(CstType.forBoxedPrimitiveType(primitiveType),
-                CstNat.PRIMITIVE_TYPE_NAT);
+  /**
+   * Returns an instance of this class that represents the static
+   * field which should hold the class corresponding to a given
+   * primitive type. For example, if given {@link Type#INT}, this
+   * method returns an instance corresponding to the field
+   * {@code java.lang.Integer.TYPE}.
+   *
+   * @param primitiveType {@code non-null;} the primitive type
+   * @return {@code non-null;} the corresponding static field
+   */
+  public static CstFieldRef forPrimitiveType(Type primitiveType) {
+    return new CstFieldRef(CstType.forBoxedPrimitiveType(primitiveType), CstNat.PRIMITIVE_TYPE_NAT);
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param definingClass {@code non-null;} the type of the defining class
+   * @param nat {@code non-null;} the name-and-type
+   */
+  public CstFieldRef(CstType definingClass, CstNat nat) {
+    super(definingClass, nat);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "field";
+  }
+
+  /**
+   * Returns the type of this field.
+   *
+   * @return {@code non-null;} the field's type
+   */
+  @Override
+  public Type getType() {
+    return getNat().getFieldType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    int cmp = super.compareTo0(other);
+
+    if (cmp != 0) {
+      return cmp;
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param definingClass {@code non-null;} the type of the defining class
-     * @param nat {@code non-null;} the name-and-type
-     */
-    public CstFieldRef(CstType definingClass, CstNat nat) {
-        super(definingClass, nat);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "field";
-    }
-
-    /**
-     * Returns the type of this field.
-     *
-     * @return {@code non-null;} the field's type
-     */
-    public Type getType() {
-        return getNat().getFieldType();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        int cmp = super.compareTo0(other);
-
-        if (cmp != 0) {
-            return cmp;
-        }
-
-        CstFieldRef otherField = (CstFieldRef) other;
-        CstString thisDescriptor = getNat().getDescriptor();
-        CstString otherDescriptor = otherField.getNat().getDescriptor();
-        return thisDescriptor.compareTo(otherDescriptor);
-    }
+    CstFieldRef otherField = (CstFieldRef) other;
+    CstString thisDescriptor = getNat().getDescriptor();
+    CstString otherDescriptor = otherField.getNat().getDescriptor();
+    return thisDescriptor.compareTo(otherDescriptor);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstFloat.java b/dx/src/com/android/jack/dx/rop/cst/CstFloat.java
index e257fae..b599ae4 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstFloat.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstFloat.java
@@ -22,70 +22,70 @@
 /**
  * Constants of type {@code CONSTANT_Float_info}.
  */
-public final class CstFloat
-        extends CstLiteral32 {
-    /** {@code non-null;} instance representing {@code 0} */
-    public static final CstFloat VALUE_0 = make(Float.floatToIntBits(0.0f));
+public final class CstFloat extends CstLiteral32 {
+  /** {@code non-null;} instance representing {@code 0} */
+  public static final CstFloat VALUE_0 = make(Float.floatToIntBits(0.0f));
 
-    /** {@code non-null;} instance representing {@code 1} */
-    public static final CstFloat VALUE_1 = make(Float.floatToIntBits(1.0f));
+  /** {@code non-null;} instance representing {@code 1} */
+  public static final CstFloat VALUE_1 = make(Float.floatToIntBits(1.0f));
 
-    /** {@code non-null;} instance representing {@code 2} */
-    public static final CstFloat VALUE_2 = make(Float.floatToIntBits(2.0f));
+  /** {@code non-null;} instance representing {@code 2} */
+  public static final CstFloat VALUE_2 = make(Float.floatToIntBits(2.0f));
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param bits the {@code float} value as {@code int} bits
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param bits the {@code float} value as {@code int} bits
+   */
+  public static CstFloat make(int bits) {
+    /*
+     * Note: Javadoc notwithstanding, this implementation always
+     * allocates.
      */
-    public static CstFloat make(int bits) {
-        /*
-         * Note: Javadoc notwithstanding, this implementation always
-         * allocates.
-         */
-        return new CstFloat(bits);
-    }
+    return new CstFloat(bits);
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param bits the {@code float} value as {@code int} bits
-     */
-    private CstFloat(int bits) {
-        super(bits);
-    }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param bits the {@code float} value as {@code int} bits
+   */
+  private CstFloat(int bits) {
+    super(bits);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int bits = getIntBits();
-        return "float{0x" + Hex.u4(bits) + " / " +
-            Float.intBitsToFloat(bits) + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int bits = getIntBits();
+    return "float{0x" + Hex.u4(bits) + " / " + Float.intBitsToFloat(bits) + '}';
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.FLOAT;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.FLOAT;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "float";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "float";
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Float.toString(Float.intBitsToFloat(getIntBits()));
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Float.toString(Float.intBitsToFloat(getIntBits()));
+  }
 
-    /**
-     * Gets the {@code float} value.
-     *
-     * @return the value
-     */
-    public float getValue() {
-        return Float.intBitsToFloat(getIntBits());
-    }
+  /**
+   * Gets the {@code float} value.
+   *
+   * @return the value
+   */
+  public float getValue() {
+    return Float.intBitsToFloat(getIntBits());
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstIndexMap.java b/dx/src/com/android/jack/dx/rop/cst/CstIndexMap.java
index 3d84830..9a5d55e 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstIndexMap.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstIndexMap.java
@@ -15,13 +15,13 @@
  */
 package com.android.jack.dx.rop.cst;
 
+import com.android.jack.dx.dex.file.DexFile;
+import com.android.jack.dx.dex.file.IndexedItem;
+
 import java.util.Collection;
 import java.util.HashMap;
 import java.util.Map;
 
-import com.android.jack.dx.dex.file.DexFile;
-import com.android.jack.dx.dex.file.IndexedItem;
-
 /**
  * Maps {@link TypedConstant} index offsets from a dex file to those into another.
  */
@@ -38,8 +38,7 @@
       new HashMap<Integer, CstBaseMethodRef>();
 
   /** Mapping between index and {@link CstFieldRef} value of a dex file.*/
-  private final Map<Integer, CstFieldRef> fieldsIndexMap =
-      new HashMap<Integer, CstFieldRef>();
+  private final Map<Integer, CstFieldRef> fieldsIndexMap = new HashMap<Integer, CstFieldRef>();
 
   /**
    * Keeps string mapping of a dex file.
@@ -47,10 +46,9 @@
    * @param cstString The string.
    */
   public void addStringMapping(int index, CstString cstString) {
-    Integer key = new Integer (index);
+    Integer key = new Integer(index);
     assert index >= 0;
-    assert stringsIndexMap.get(key) == null
-        || stringsIndexMap.get(key).compareTo(cstString) == 0;
+    assert stringsIndexMap.get(key) == null || stringsIndexMap.get(key).compareTo(cstString) == 0;
 
     if (!stringsIndexMap.containsKey(key)) {
       stringsIndexMap.put(key, cstString);
@@ -63,10 +61,9 @@
    * @param cstType The type.
    */
   public void addTypeMapping(int index, CstType cstType) {
-    Integer key = new Integer (index);
+    Integer key = new Integer(index);
     assert index >= 0;
-    assert typesIndexMap.get(key) == null
-        || typesIndexMap.get(key).compareTo(cstType) == 0;
+    assert typesIndexMap.get(key) == null || typesIndexMap.get(key).compareTo(cstType) == 0;
 
     if (!typesIndexMap.containsKey(key)) {
       typesIndexMap.put(key, cstType);
@@ -79,10 +76,9 @@
    * @param methodRef The method.
    */
   public void addMethodMapping(int index, CstBaseMethodRef methodRef) {
-    Integer key = new Integer (index);
+    Integer key = new Integer(index);
     assert index >= 0;
-    assert methodsIndexMap.get(key) == null
-        || methodsIndexMap.get(key).compareTo(methodRef) == 0;
+    assert methodsIndexMap.get(key) == null || methodsIndexMap.get(key).compareTo(methodRef) == 0;
 
     if (!methodsIndexMap.containsKey(key)) {
       methodsIndexMap.put(key, methodRef);
@@ -95,10 +91,9 @@
    * @param fieldRef The Field.
    */
   public void addFieldMapping(int index, CstFieldRef fieldRef) {
-    Integer key = new Integer (index);
+    Integer key = new Integer(index);
     assert index >= 0;
-    assert fieldsIndexMap.get(key) == null
-        || fieldsIndexMap.get(key).compareTo(fieldRef) == 0;
+    assert fieldsIndexMap.get(key) == null || fieldsIndexMap.get(key).compareTo(fieldRef) == 0;
 
     if (!fieldsIndexMap.containsKey(key)) {
       fieldsIndexMap.put(key, fieldRef);
@@ -109,7 +104,7 @@
    * Merge all {@link TypedConstant} of one dex file into another.
    * @param dex The dex file where values are merged.
    */
-  public void mergeConstantsIntoDexFile(DexFile dex)  {
+  public void mergeConstantsIntoDexFile(DexFile dex) {
     for (CstString cst : stringsIndexMap.values()) {
       dex.getStringIds().intern(cst);
     }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstInteger.java b/dx/src/com/android/jack/dx/rop/cst/CstInteger.java
index 10ae236..e6ee29a 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstInteger.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstInteger.java
@@ -22,95 +22,96 @@
 /**
  * Constants of type {@code CONSTANT_Integer_info}.
  */
-public final class CstInteger
-        extends CstLiteral32 {
-    /** {@code non-null;} array of cached instances */
-    private static final CstInteger[] cache = new CstInteger[511];
+public final class CstInteger extends CstLiteral32 {
+  /** {@code non-null;} array of cached instances */
+  private static final CstInteger[] cache = new CstInteger[511];
 
-    /** {@code non-null;} instance representing {@code -1} */
-    public static final CstInteger VALUE_M1 = make(-1);
+  /** {@code non-null;} instance representing {@code -1} */
+  public static final CstInteger VALUE_M1 = make(-1);
 
-    /** {@code non-null;} instance representing {@code 0} */
-    public static final CstInteger VALUE_0 = make(0);
+  /** {@code non-null;} instance representing {@code 0} */
+  public static final CstInteger VALUE_0 = make(0);
 
-    /** {@code non-null;} instance representing {@code 1} */
-    public static final CstInteger VALUE_1 = make(1);
+  /** {@code non-null;} instance representing {@code 1} */
+  public static final CstInteger VALUE_1 = make(1);
 
-    /** {@code non-null;} instance representing {@code 2} */
-    public static final CstInteger VALUE_2 = make(2);
+  /** {@code non-null;} instance representing {@code 2} */
+  public static final CstInteger VALUE_2 = make(2);
 
-    /** {@code non-null;} instance representing {@code 3} */
-    public static final CstInteger VALUE_3 = make(3);
+  /** {@code non-null;} instance representing {@code 3} */
+  public static final CstInteger VALUE_3 = make(3);
 
-    /** {@code non-null;} instance representing {@code 4} */
-    public static final CstInteger VALUE_4 = make(4);
+  /** {@code non-null;} instance representing {@code 4} */
+  public static final CstInteger VALUE_4 = make(4);
 
-    /** {@code non-null;} instance representing {@code 5} */
-    public static final CstInteger VALUE_5 = make(5);
+  /** {@code non-null;} instance representing {@code 5} */
+  public static final CstInteger VALUE_5 = make(5);
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param value the {@code int} value
-     * @return {@code non-null;} the appropriate instance
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param value the {@code int} value
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstInteger make(int value) {
+    /*
+     * Note: No need to synchronize, since we don't make any sort
+     * of guarantee about ==, and it's okay to overwrite existing
+     * entries too.
      */
-    public static CstInteger make(int value) {
-        /*
-         * Note: No need to synchronize, since we don't make any sort
-         * of guarantee about ==, and it's okay to overwrite existing
-         * entries too.
-         */
-        int idx = (value & 0x7fffffff) % cache.length;
-        CstInteger obj = cache[idx];
+    int idx = (value & 0x7fffffff) % cache.length;
+    CstInteger obj = cache[idx];
 
-        if ((obj != null) && (obj.getValue() == value)) {
-            return obj;
-        }
-
-        obj = new CstInteger(value);
-        cache[idx] = obj;
-        return obj;
+    if ((obj != null) && (obj.getValue() == value)) {
+      return obj;
     }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code int} value
-     */
-    private CstInteger(int value) {
-        super(value);
-    }
+    obj = new CstInteger(value);
+    cache[idx] = obj;
+    return obj;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int value = getIntBits();
-        return "int{0x" + Hex.u4(value) + " / " + value + '}';
-    }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code int} value
+   */
+  private CstInteger(int value) {
+    super(value);
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.INT;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int value = getIntBits();
+    return "int{0x" + Hex.u4(value) + " / " + value + '}';
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "int";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.INT;
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Integer.toString(getIntBits());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "int";
+  }
 
-    /**
-     * Gets the {@code int} value.
-     *
-     * @return the value
-     */
-    public int getValue() {
-        return getIntBits();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Integer.toString(getIntBits());
+  }
+
+  /**
+   * Gets the {@code int} value.
+   *
+   * @return the value
+   */
+  public int getValue() {
+    return getIntBits();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstInterfaceMethodRef.java b/dx/src/com/android/jack/dx/rop/cst/CstInterfaceMethodRef.java
index 66c3dd6..7aef26a 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstInterfaceMethodRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstInterfaceMethodRef.java
@@ -19,42 +19,41 @@
 /**
  * Constants of type {@code CONSTANT_InterfaceMethodref_info}.
  */
-public final class CstInterfaceMethodRef
-        extends CstBaseMethodRef {
-    /**
-     * {@code null-ok;} normal {@link CstMethodRef} that corresponds to this
-     * instance, if calculated
-     */
-    private CstMethodRef methodRef;
+public final class CstInterfaceMethodRef extends CstBaseMethodRef {
+  /**
+   * {@code null-ok;} normal {@link CstMethodRef} that corresponds to this
+   * instance, if calculated
+   */
+  private CstMethodRef methodRef;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param definingClass {@code non-null;} the type of the defining class
-     * @param nat {@code non-null;} the name-and-type
-     */
-    public CstInterfaceMethodRef(CstType definingClass, CstNat nat) {
-        super(definingClass, nat);
-        methodRef = null;
+  /**
+   * Constructs an instance.
+   *
+   * @param definingClass {@code non-null;} the type of the defining class
+   * @param nat {@code non-null;} the name-and-type
+   */
+  public CstInterfaceMethodRef(CstType definingClass, CstNat nat) {
+    super(definingClass, nat);
+    methodRef = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "ifaceMethod";
+  }
+
+  /**
+   * Gets a normal (non-interface) {@link CstMethodRef} that corresponds to
+   * this instance.
+   *
+   * @return {@code non-null;} an appropriate instance
+   */
+  public CstMethodRef toMethodRef() {
+    if (methodRef == null) {
+      methodRef = new CstMethodRef(getDefiningClass(), getNat());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "ifaceMethod";
-    }
-
-    /**
-     * Gets a normal (non-interface) {@link CstMethodRef} that corresponds to
-     * this instance.
-     *
-     * @return {@code non-null;} an appropriate instance
-     */
-    public CstMethodRef toMethodRef() {
-        if (methodRef == null) {
-            methodRef = new CstMethodRef(getDefiningClass(), getNat());
-        }
-
-        return methodRef;
-    }
+    return methodRef;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstKnownNull.java b/dx/src/com/android/jack/dx/rop/cst/CstKnownNull.java
index fe471f3..a7b6355 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstKnownNull.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstKnownNull.java
@@ -22,89 +22,91 @@
  * Constant type to represent a known-{@code null} value.
  */
 public final class CstKnownNull extends CstLiteralBits {
-    /** {@code non-null;} unique instance of this class */
-    public static final CstKnownNull THE_ONE = new CstKnownNull();
+  /** {@code non-null;} unique instance of this class */
+  public static final CstKnownNull THE_ONE = new CstKnownNull();
 
-    /**
-     * Constructs an instance. This class is not publicly instantiable. Use
-     * {@link #THE_ONE}.
-     */
-    private CstKnownNull() {
-        // This space intentionally left blank.
-    }
+  /**
+   * Constructs an instance. This class is not publicly instantiable. Use
+   * {@link #THE_ONE}.
+   */
+  private CstKnownNull() {
+    // This space intentionally left blank.
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        return (other instanceof CstKnownNull);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    return (other instanceof CstKnownNull);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return 0x4466757a;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return 0x4466757a;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        return 0;
-    }
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    return 0;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return "known-null";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "known-null";
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.KNOWN_NULL;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.KNOWN_NULL;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "known-null";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "known-null";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return "null";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return "null";
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean fitsInInt() {
-        // See comment in getIntBits().
-        return true;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean fitsInInt() {
+    // See comment in getIntBits().
+    return true;
+  }
 
-    /**
-     * {@inheritDoc}
-     *
-     * As "literal bits," a known-null is always represented as the
-     * number zero.
-     */
-    @Override
-    public int getIntBits() {
-        return 0;
-    }
+  /**
+   * {@inheritDoc}
+   *
+   * As "literal bits," a known-null is always represented as the
+   * number zero.
+   */
+  @Override
+  public int getIntBits() {
+    return 0;
+  }
 
-    /**
-     * {@inheritDoc}
-     *
-     * As "literal bits," a known-null is always represented as the
-     * number zero.
-     */
-    @Override
-    public long getLongBits() {
-        return 0;
-    }
+  /**
+   * {@inheritDoc}
+   *
+   * As "literal bits," a known-null is always represented as the
+   * number zero.
+   */
+  @Override
+  public long getLongBits() {
+    return 0;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstLiteral32.java b/dx/src/com/android/jack/dx/rop/cst/CstLiteral32.java
index 488c015..8e2cec2 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstLiteral32.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstLiteral32.java
@@ -19,69 +19,67 @@
 /**
  * Constants which are literal 32-bit values of some sort.
  */
-public abstract class CstLiteral32
-        extends CstLiteralBits {
-    /** the value as {@code int} bits */
-    private final int bits;
+public abstract class CstLiteral32 extends CstLiteralBits {
+  /** the value as {@code int} bits */
+  private final int bits;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param bits the value as {@code int} bits
-     */
-    /*package*/ CstLiteral32(int bits) {
-        this.bits = bits;
+  /**
+   * Constructs an instance.
+   *
+   * @param bits the value as {@code int} bits
+   */
+  /*package*/CstLiteral32(int bits) {
+    this.bits = bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final boolean equals(Object other) {
+    return (other != null) && (getClass() == other.getClass())
+        && bits == ((CstLiteral32) other).bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int hashCode() {
+    return bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    int otherBits = ((CstLiteral32) other).bits;
+
+    if (bits < otherBits) {
+      return -1;
+    } else if (bits > otherBits) {
+      return 1;
+    } else {
+      return 0;
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final boolean equals(Object other) {
-        return (other != null) &&
-            (getClass() == other.getClass()) &&
-            bits == ((CstLiteral32) other).bits;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean isCategory2() {
+    return false;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final int hashCode() {
-        return bits;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean fitsInInt() {
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        int otherBits = ((CstLiteral32) other).bits;
+  /** {@inheritDoc} */
+  @Override
+  public final int getIntBits() {
+    return bits;
+  }
 
-        if (bits < otherBits) {
-            return -1;
-        } else if (bits > otherBits) {
-            return 1;
-        } else {
-            return 0;
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final boolean isCategory2() {
-        return false;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final boolean fitsInInt() {
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final int getIntBits() {
-        return bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final long getLongBits() {
-        return (long) bits;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final long getLongBits() {
+    return bits;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstLiteral64.java b/dx/src/com/android/jack/dx/rop/cst/CstLiteral64.java
index e72b089..1c3e976 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstLiteral64.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstLiteral64.java
@@ -19,69 +19,67 @@
 /**
  * Constants which are literal 64-bit values of some sort.
  */
-public abstract class CstLiteral64
-        extends CstLiteralBits {
-    /** the value as {@code long} bits */
-    private final long bits;
+public abstract class CstLiteral64 extends CstLiteralBits {
+  /** the value as {@code long} bits */
+  private final long bits;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param bits the value as {@code long} bits
-     */
-    /*package*/ CstLiteral64(long bits) {
-        this.bits = bits;
+  /**
+   * Constructs an instance.
+   *
+   * @param bits the value as {@code long} bits
+   */
+  /*package*/CstLiteral64(long bits) {
+    this.bits = bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final boolean equals(Object other) {
+    return (other != null) && (getClass() == other.getClass())
+        && bits == ((CstLiteral64) other).bits;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int hashCode() {
+    return (int) bits ^ (int) (bits >> 32);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    long otherBits = ((CstLiteral64) other).bits;
+
+    if (bits < otherBits) {
+      return -1;
+    } else if (bits > otherBits) {
+      return 1;
+    } else {
+      return 0;
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final boolean equals(Object other) {
-        return (other != null) &&
-            (getClass() == other.getClass()) &&
-            bits == ((CstLiteral64) other).bits;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean isCategory2() {
+    return true;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public final int hashCode() {
-        return (int) bits ^ (int) (bits >> 32);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean fitsInInt() {
+    return (int) bits == bits;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        long otherBits = ((CstLiteral64) other).bits;
+  /** {@inheritDoc} */
+  @Override
+  public final int getIntBits() {
+    return (int) bits;
+  }
 
-        if (bits < otherBits) {
-            return -1;
-        } else if (bits > otherBits) {
-            return 1;
-        } else {
-            return 0;
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final boolean isCategory2() {
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final boolean fitsInInt() {
-        return (int) bits == bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final int getIntBits() {
-        return (int) bits;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public final long getLongBits() {
-        return bits;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final long getLongBits() {
+    return bits;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstLiteralBits.java b/dx/src/com/android/jack/dx/rop/cst/CstLiteralBits.java
index 0615aa7..4b8ead6 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstLiteralBits.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstLiteralBits.java
@@ -19,64 +19,63 @@
 /**
  * Constants which are literal bitwise values of some sort.
  */
-public abstract class CstLiteralBits
-        extends TypedConstant {
-    /**
-     * Returns whether or not this instance's value may be accurately
-     * represented as an {@code int}. The rule is that if there
-     * is an {@code int} which may be sign-extended to yield this
-     * instance's value, then this method returns {@code true}.
-     * Otherwise, it returns {@code false}.
-     *
-     * @return {@code true} iff this instance fits in an {@code int}
-     */
-    public abstract boolean fitsInInt();
+public abstract class CstLiteralBits extends TypedConstant {
+  /**
+   * Returns whether or not this instance's value may be accurately
+   * represented as an {@code int}. The rule is that if there
+   * is an {@code int} which may be sign-extended to yield this
+   * instance's value, then this method returns {@code true}.
+   * Otherwise, it returns {@code false}.
+   *
+   * @return {@code true} iff this instance fits in an {@code int}
+   */
+  public abstract boolean fitsInInt();
 
-    /**
-     * Gets the value as {@code int} bits. If this instance contains
-     * more bits than fit in an {@code int}, then this returns only
-     * the low-order bits.
-     *
-     * @return the bits
-     */
-    public abstract int getIntBits();
+  /**
+   * Gets the value as {@code int} bits. If this instance contains
+   * more bits than fit in an {@code int}, then this returns only
+   * the low-order bits.
+   *
+   * @return the bits
+   */
+  public abstract int getIntBits();
 
-    /**
-     * Gets the value as {@code long} bits. If this instance contains
-     * fewer bits than fit in a {@code long}, then the result of this
-     * method is the sign extension of the value.
-     *
-     * @return the bits
-     */
-    public abstract long getLongBits();
+  /**
+   * Gets the value as {@code long} bits. If this instance contains
+   * fewer bits than fit in a {@code long}, then the result of this
+   * method is the sign extension of the value.
+   *
+   * @return the bits
+   */
+  public abstract long getLongBits();
 
-    /**
-     * Returns true if this value can fit in 16 bits with sign-extension.
-     *
-     * @return true if the sign-extended lower 16 bits are the same as
-     * the value.
-     */
-    public boolean fitsIn16Bits() {
-        if (! fitsInInt()) {
-            return false;
-        }
-
-        int bits = getIntBits();
-        return (short) bits == bits;
+  /**
+   * Returns true if this value can fit in 16 bits with sign-extension.
+   *
+   * @return true if the sign-extended lower 16 bits are the same as
+   * the value.
+   */
+  public boolean fitsIn16Bits() {
+    if (!fitsInInt()) {
+      return false;
     }
 
-    /**
-     * Returns true if this value can fit in 8 bits with sign-extension.
-     *
-     * @return true if the sign-extended lower 8 bits are the same as
-     * the value.
-     */
-    public boolean fitsIn8Bits() {
-        if (! fitsInInt()) {
-            return false;
-        }
+    int bits = getIntBits();
+    return (short) bits == bits;
+  }
 
-        int bits = getIntBits();
-        return (byte) bits == bits;
+  /**
+   * Returns true if this value can fit in 8 bits with sign-extension.
+   *
+   * @return true if the sign-extended lower 8 bits are the same as
+   * the value.
+   */
+  public boolean fitsIn8Bits() {
+    if (!fitsInInt()) {
+      return false;
     }
+
+    int bits = getIntBits();
+    return (byte) bits == bits;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstLong.java b/dx/src/com/android/jack/dx/rop/cst/CstLong.java
index 58c2b9b..6265566 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstLong.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstLong.java
@@ -22,66 +22,67 @@
 /**
  * Constants of type {@code CONSTANT_Long_info}.
  */
-public final class CstLong
-        extends CstLiteral64 {
-    /** {@code non-null;} instance representing {@code 0} */
-    public static final CstLong VALUE_0 = make(0);
+public final class CstLong extends CstLiteral64 {
+  /** {@code non-null;} instance representing {@code 0} */
+  public static final CstLong VALUE_0 = make(0);
 
-    /** {@code non-null;} instance representing {@code 1} */
-    public static final CstLong VALUE_1 = make(1);
+  /** {@code non-null;} instance representing {@code 1} */
+  public static final CstLong VALUE_1 = make(1);
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param value the {@code long} value
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param value the {@code long} value
+   */
+  public static CstLong make(long value) {
+    /*
+     * Note: Javadoc notwithstanding, this implementation always
+     * allocates.
      */
-    public static CstLong make(long value) {
-        /*
-         * Note: Javadoc notwithstanding, this implementation always
-         * allocates.
-         */
-        return new CstLong(value);
-    }
+    return new CstLong(value);
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code long} value
-     */
-    private CstLong(long value) {
-        super(value);
-    }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code long} value
+   */
+  private CstLong(long value) {
+    super(value);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        long value = getLongBits();
-        return "long{0x" + Hex.u8(value) + " / " + value + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    long value = getLongBits();
+    return "long{0x" + Hex.u8(value) + " / " + value + '}';
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.LONG;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.LONG;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "long";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "long";
+  }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Long.toString(getLongBits());
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Long.toString(getLongBits());
+  }
 
-    /**
-     * Gets the {@code long} value.
-     *
-     * @return the value
-     */
-    public long getValue() {
-        return getLongBits();
-    }
+  /**
+   * Gets the {@code long} value.
+   *
+   * @return the value
+   */
+  public long getValue() {
+    return getLongBits();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstMemberRef.java b/dx/src/com/android/jack/dx/rop/cst/CstMemberRef.java
index 3415946..2b36a7d 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstMemberRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstMemberRef.java
@@ -20,103 +20,103 @@
  * Constants of type {@code CONSTANT_*ref_info}.
  */
 public abstract class CstMemberRef extends TypedConstant {
-    /** {@code non-null;} the type of the defining class */
-    private final CstType definingClass;
+  /** {@code non-null;} the type of the defining class */
+  private final CstType definingClass;
 
-    /** {@code non-null;} the name-and-type */
-    private final CstNat nat;
+  /** {@code non-null;} the name-and-type */
+  private final CstNat nat;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param definingClass {@code non-null;} the type of the defining class
-     * @param nat {@code non-null;} the name-and-type
-     */
-    /*package*/ CstMemberRef(CstType definingClass, CstNat nat) {
-        if (definingClass == null) {
-            throw new NullPointerException("definingClass == null");
-        }
-
-        if (nat == null) {
-            throw new NullPointerException("nat == null");
-        }
-
-        this.definingClass = definingClass;
-        this.nat = nat;
+  /**
+   * Constructs an instance.
+   *
+   * @param definingClass {@code non-null;} the type of the defining class
+   * @param nat {@code non-null;} the name-and-type
+   */
+  /*package*/CstMemberRef(CstType definingClass, CstNat nat) {
+    if (definingClass == null) {
+      throw new NullPointerException("definingClass == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final boolean equals(Object other) {
-        if ((other == null) || (getClass() != other.getClass())) {
-            return false;
-        }
-
-        CstMemberRef otherRef = (CstMemberRef) other;
-        return definingClass.equals(otherRef.definingClass) &&
-            nat.equals(otherRef.nat);
+    if (nat == null) {
+      throw new NullPointerException("nat == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final int hashCode() {
-        return (definingClass.hashCode() * 31) ^ nat.hashCode();
+    this.definingClass = definingClass;
+    this.nat = nat;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final boolean equals(Object other) {
+    if ((other == null) || (getClass() != other.getClass())) {
+      return false;
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * <p><b>Note:</b> This implementation just compares the defining
-     * class and name, and it is up to subclasses to compare the rest
-     * after calling {@code super.compareTo0()}.</p>
-     */
-    @Override
-    protected int compareTo0(Constant other) {
-        CstMemberRef otherMember = (CstMemberRef) other;
-        int cmp = definingClass.compareTo(otherMember.definingClass);
+    CstMemberRef otherRef = (CstMemberRef) other;
+    return definingClass.equals(otherRef.definingClass) && nat.equals(otherRef.nat);
+  }
 
-        if (cmp != 0) {
-            return cmp;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public final int hashCode() {
+    return (definingClass.hashCode() * 31) ^ nat.hashCode();
+  }
 
-        CstString thisName = nat.getName();
-        CstString otherName = otherMember.nat.getName();
+  /**
+   * {@inheritDoc}
+   *
+   * <p><b>Note:</b> This implementation just compares the defining
+   * class and name, and it is up to subclasses to compare the rest
+   * after calling {@code super.compareTo0()}.</p>
+   */
+  @Override
+  protected int compareTo0(Constant other) {
+    CstMemberRef otherMember = (CstMemberRef) other;
+    int cmp = definingClass.compareTo(otherMember.definingClass);
 
-        return thisName.compareTo(otherName);
+    if (cmp != 0) {
+      return cmp;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final String toString() {
-        return typeName() + '{' + toHuman() + '}';
-    }
+    CstString thisName = nat.getName();
+    CstString otherName = otherMember.nat.getName();
 
-    /** {@inheritDoc} */
-    @Override
-    public final boolean isCategory2() {
-        return false;
-    }
+    return thisName.compareTo(otherName);
+  }
 
-    /** {@inheritDoc} */
-    public final String toHuman() {
-        return definingClass.toHuman() + '.' + nat.toHuman();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final String toString() {
+    return typeName() + '{' + toHuman() + '}';
+  }
 
-    /**
-     * Gets the type of the defining class.
-     *
-     * @return {@code non-null;} the type of defining class
-     */
-    public final CstType getDefiningClass() {
-        return definingClass;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean isCategory2() {
+    return false;
+  }
 
-    /**
-     * Gets the defining name-and-type.
-     *
-     * @return {@code non-null;} the name-and-type
-     */
-    public final CstNat getNat() {
-        return nat;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final String toHuman() {
+    return definingClass.toHuman() + '.' + nat.toHuman();
+  }
+
+  /**
+   * Gets the type of the defining class.
+   *
+   * @return {@code non-null;} the type of defining class
+   */
+  public final CstType getDefiningClass() {
+    return definingClass;
+  }
+
+  /**
+   * Gets the defining name-and-type.
+   *
+   * @return {@code non-null;} the name-and-type
+   */
+  public final CstNat getNat() {
+    return nat;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstMethodRef.java b/dx/src/com/android/jack/dx/rop/cst/CstMethodRef.java
index 3b6d2a4..f28e050 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstMethodRef.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstMethodRef.java
@@ -19,21 +19,20 @@
 /**
  * Constants of type {@code CONSTANT_Methodref_info}.
  */
-public final class CstMethodRef
-        extends CstBaseMethodRef {
-    /**
-     * Constructs an instance.
-     *
-     * @param definingClass {@code non-null;} the type of the defining class
-     * @param nat {@code non-null;} the name-and-type
-     */
-    public CstMethodRef(CstType definingClass, CstNat nat) {
-        super(definingClass, nat);
-    }
+public final class CstMethodRef extends CstBaseMethodRef {
+  /**
+   * Constructs an instance.
+   *
+   * @param definingClass {@code non-null;} the type of the defining class
+   * @param nat {@code non-null;} the name-and-type
+   */
+  public CstMethodRef(CstType definingClass, CstNat nat) {
+    super(definingClass, nat);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "method";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "method";
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstNat.java b/dx/src/com/android/jack/dx/rop/cst/CstNat.java
index 75c521e..6abdbb7 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstNat.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstNat.java
@@ -22,149 +22,148 @@
  * Constants of type {@code CONSTANT_NameAndType_info}.
  */
 public final class CstNat extends Constant {
-    /**
-     * {@code non-null;} the instance for name {@code TYPE} and descriptor
-     * {@code java.lang.Class}, which is useful when dealing with
-     * wrapped primitives
-     */
-    public static final CstNat PRIMITIVE_TYPE_NAT =
-        new CstNat(new CstString("TYPE"),
-                   new CstString("Ljava/lang/Class;"));
+  /**
+   * {@code non-null;} the instance for name {@code TYPE} and descriptor
+   * {@code java.lang.Class}, which is useful when dealing with
+   * wrapped primitives
+   */
+  public static final CstNat PRIMITIVE_TYPE_NAT =
+      new CstNat(new CstString("TYPE"), new CstString("Ljava/lang/Class;"));
 
-    /** {@code non-null;} the name */
-    private final CstString name;
+  /** {@code non-null;} the name */
+  private final CstString name;
 
-    /** {@code non-null;} the descriptor (type) */
-    private final CstString descriptor;
+  /** {@code non-null;} the descriptor (type) */
+  private final CstString descriptor;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param name {@code non-null;} the name
-     * @param descriptor {@code non-null;} the descriptor
-     */
-    public CstNat(CstString name, CstString descriptor) {
-        if (name == null) {
-            throw new NullPointerException("name == null");
-        }
-
-        if (descriptor == null) {
-            throw new NullPointerException("descriptor == null");
-        }
-
-        this.name = name;
-        this.descriptor = descriptor;
+  /**
+   * Constructs an instance.
+   *
+   * @param name {@code non-null;} the name
+   * @param descriptor {@code non-null;} the descriptor
+   */
+  public CstNat(CstString name, CstString descriptor) {
+    if (name == null) {
+      throw new NullPointerException("name == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof CstNat)) {
-            return false;
-        }
-
-        CstNat otherNat = (CstNat) other;
-        return name.equals(otherNat.name) &&
-            descriptor.equals(otherNat.descriptor);
+    if (descriptor == null) {
+      throw new NullPointerException("descriptor == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return (name.hashCode() * 31) ^ descriptor.hashCode();
+    this.name = name;
+    this.descriptor = descriptor;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof CstNat)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        CstNat otherNat = (CstNat) other;
-        int cmp = name.compareTo(otherNat.name);
+    CstNat otherNat = (CstNat) other;
+    return name.equals(otherNat.name) && descriptor.equals(otherNat.descriptor);
+  }
 
-        if (cmp != 0) {
-            return cmp;
-        }
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return (name.hashCode() * 31) ^ descriptor.hashCode();
+  }
 
-        return descriptor.compareTo(otherNat.descriptor);
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    CstNat otherNat = (CstNat) other;
+    int cmp = name.compareTo(otherNat.name);
+
+    if (cmp != 0) {
+      return cmp;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return "nat{" + toHuman() + '}';
-    }
+    return descriptor.compareTo(otherNat.descriptor);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "nat";
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "nat{" + toHuman() + '}';
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "nat";
+  }
 
-    /**
-     * Gets the name.
-     *
-     * @return {@code non-null;} the name
-     */
-    public CstString getName() {
-        return name;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
 
-    /**
-     * Gets the descriptor.
-     *
-     * @return {@code non-null;} the descriptor
-     */
-    public CstString getDescriptor() {
-        return descriptor;
-    }
+  /**
+   * Gets the name.
+   *
+   * @return {@code non-null;} the name
+   */
+  public CstString getName() {
+    return name;
+  }
 
-    /**
-     * Returns an unadorned but human-readable version of the name-and-type
-     * value.
-     *
-     * @return {@code non-null;} the human form
-     */
-    public String toHuman() {
-        return name.toHuman() + ':' + descriptor.toHuman();
-    }
+  /**
+   * Gets the descriptor.
+   *
+   * @return {@code non-null;} the descriptor
+   */
+  public CstString getDescriptor() {
+    return descriptor;
+  }
 
-    /**
-     * Gets the field type corresponding to this instance's descriptor.
-     * This method is only valid to call if the descriptor in fact describes
-     * a field (and not a method).
-     *
-     * @return {@code non-null;} the field type
-     */
-    public Type getFieldType() {
-        return Type.intern(descriptor.getString());
-    }
+  /**
+   * Returns an unadorned but human-readable version of the name-and-type
+   * value.
+   *
+   * @return {@code non-null;} the human form
+   */
+  @Override
+  public String toHuman() {
+    return name.toHuman() + ':' + descriptor.toHuman();
+  }
 
-    /**
-     * Gets whether this instance has the name of a standard instance
-     * initialization method. This is just a convenient shorthand for
-     * {@code getName().getString().equals("<init>")}.
-     *
-     * @return {@code true} iff this is a reference to an
-     * instance initialization method
-     */
-    public final boolean isInstanceInit() {
-        return name.getString().equals("<init>");
-    }
+  /**
+   * Gets the field type corresponding to this instance's descriptor.
+   * This method is only valid to call if the descriptor in fact describes
+   * a field (and not a method).
+   *
+   * @return {@code non-null;} the field type
+   */
+  public Type getFieldType() {
+    return Type.intern(descriptor.getString());
+  }
 
-    /**
-     * Gets whether this instance has the name of a standard class
-     * initialization method. This is just a convenient shorthand for
-     * {@code getName().getString().equals("<clinit>")}.
-     *
-     * @return {@code true} iff this is a reference to an
-     * instance initialization method
-     */
-    public final boolean isClassInit() {
-        return name.getString().equals("<clinit>");
-    }
+  /**
+   * Gets whether this instance has the name of a standard instance
+   * initialization method. This is just a convenient shorthand for
+   * {@code getName().getString().equals("<init>")}.
+   *
+   * @return {@code true} iff this is a reference to an
+   * instance initialization method
+   */
+  public final boolean isInstanceInit() {
+    return name.getString().equals("<init>");
+  }
+
+  /**
+   * Gets whether this instance has the name of a standard class
+   * initialization method. This is just a convenient shorthand for
+   * {@code getName().getString().equals("<clinit>")}.
+   *
+   * @return {@code true} iff this is a reference to an
+   * instance initialization method
+   */
+  public final boolean isClassInit() {
+    return name.getString().equals("<clinit>");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstShort.java b/dx/src/com/android/jack/dx/rop/cst/CstShort.java
index 688ae6d..3038c91 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstShort.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstShort.java
@@ -22,79 +22,79 @@
 /**
  * Constants of type {@code short}.
  */
-public final class CstShort
-        extends CstLiteral32 {
-    /** {@code non-null;} the value {@code 0} as an instance of this class */
-    public static final CstShort VALUE_0 = make((short) 0);
+public final class CstShort extends CstLiteral32 {
+  /** {@code non-null;} the value {@code 0} as an instance of this class */
+  public static final CstShort VALUE_0 = make((short) 0);
 
-    /**
-     * Makes an instance for the given value. This may (but does not
-     * necessarily) return an already-allocated instance.
-     *
-     * @param value the {@code short} value
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstShort make(short value) {
-        return new CstShort(value);
+  /**
+   * Makes an instance for the given value. This may (but does not
+   * necessarily) return an already-allocated instance.
+   *
+   * @param value the {@code short} value
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstShort make(short value) {
+    return new CstShort(value);
+  }
+
+  /**
+   * Makes an instance for the given {@code int} value. This
+   * may (but does not necessarily) return an already-allocated
+   * instance.
+   *
+   * @param value the value, which must be in range for a {@code short}
+   * @return {@code non-null;} the appropriate instance
+   */
+  public static CstShort make(int value) {
+    short cast = (short) value;
+
+    if (cast != value) {
+      throw new IllegalArgumentException("bogus short value: " + value);
     }
 
-    /**
-     * Makes an instance for the given {@code int} value. This
-     * may (but does not necessarily) return an already-allocated
-     * instance.
-     *
-     * @param value the value, which must be in range for a {@code short}
-     * @return {@code non-null;} the appropriate instance
-     */
-    public static CstShort make(int value) {
-        short cast = (short) value;
+    return make(cast);
+  }
 
-        if (cast != value) {
-            throw new IllegalArgumentException("bogus short value: " +
-                    value);
-        }
+  /**
+   * Constructs an instance. This constructor is private; use {@link #make}.
+   *
+   * @param value the {@code short} value
+   */
+  private CstShort(short value) {
+    super(value);
+  }
 
-        return make(cast);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    int value = getIntBits();
+    return "short{0x" + Hex.u2(value) + " / " + value + '}';
+  }
 
-    /**
-     * Constructs an instance. This constructor is private; use {@link #make}.
-     *
-     * @param value the {@code short} value
-     */
-    private CstShort(short value) {
-        super(value);
-    }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.SHORT;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        int value = getIntBits();
-        return "short{0x" + Hex.u2(value) + " / " + value + '}';
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "short";
+  }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.SHORT;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return Integer.toString(getIntBits());
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "short";
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return Integer.toString(getIntBits());
-    }
-
-    /**
-     * Gets the {@code short} value.
-     *
-     * @return the value
-     */
-    public short getValue() {
-        return (short) getIntBits();
-    }
+  /**
+   * Gets the {@code short} value.
+   *
+   * @return the value
+   */
+  public short getValue() {
+    return (short) getIntBits();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstString.java b/dx/src/com/android/jack/dx/rop/cst/CstString.java
index 42cf62d..94d547c 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstString.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstString.java
@@ -24,352 +24,364 @@
  * Constants of type {@code CONSTANT_Utf8_info} or {@code CONSTANT_String_info}.
  */
 public final class CstString extends TypedConstant {
-    /**
-     * {@code non-null;} instance representing {@code ""}, that is, the
-     * empty string
-     */
-    public static final CstString EMPTY_STRING = new CstString("");
+  /**
+   * {@code non-null;} instance representing {@code ""}, that is, the
+   * empty string
+   */
+  public static final CstString EMPTY_STRING = new CstString("");
 
-    /** {@code non-null;} the UTF-8 value as a string */
-    private final String string;
+  /** {@code non-null;} the UTF-8 value as a string */
+  private final String string;
 
-    /** {@code non-null;} the UTF-8 value as bytes */
-    private final ByteArray bytes;
+  /** {@code non-null;} the UTF-8 value as bytes */
+  private final ByteArray bytes;
 
-    /**
-     * Converts a string into its MUTF-8 form. MUTF-8 differs from normal UTF-8
-     * in the handling of character '\0' and surrogate pairs.
-     *
-     * @param string {@code non-null;} the string to convert
-     * @return {@code non-null;} the UTF-8 bytes for it
-     */
-    public static byte[] stringToUtf8Bytes(String string) {
-        int len = string.length();
-        byte[] bytes = new byte[len * 3]; // Avoid having to reallocate.
-        int outAt = 0;
+  /**
+   * Converts a string into its MUTF-8 form. MUTF-8 differs from normal UTF-8
+   * in the handling of character '\0' and surrogate pairs.
+   *
+   * @param string {@code non-null;} the string to convert
+   * @return {@code non-null;} the UTF-8 bytes for it
+   */
+  public static byte[] stringToUtf8Bytes(String string) {
+    int len = string.length();
+    byte[] bytes = new byte[len * 3]; // Avoid having to reallocate.
+    int outAt = 0;
 
-        for (int i = 0; i < len; i++) {
-            char c = string.charAt(i);
-            if ((c != 0) && (c < 0x80)) {
-                bytes[outAt] = (byte) c;
-                outAt++;
-            } else if (c < 0x800) {
-                bytes[outAt] = (byte) (((c >> 6) & 0x1f) | 0xc0);
-                bytes[outAt + 1] = (byte) ((c & 0x3f) | 0x80);
-                outAt += 2;
-            } else {
-                bytes[outAt] = (byte) (((c >> 12) & 0x0f) | 0xe0);
-                bytes[outAt + 1] = (byte) (((c >> 6) & 0x3f) | 0x80);
-                bytes[outAt + 2] = (byte) ((c & 0x3f) | 0x80);
-                outAt += 3;
+    for (int i = 0; i < len; i++) {
+      char c = string.charAt(i);
+      if ((c != 0) && (c < 0x80)) {
+        bytes[outAt] = (byte) c;
+        outAt++;
+      } else if (c < 0x800) {
+        bytes[outAt] = (byte) (((c >> 6) & 0x1f) | 0xc0);
+        bytes[outAt + 1] = (byte) ((c & 0x3f) | 0x80);
+        outAt += 2;
+      } else {
+        bytes[outAt] = (byte) (((c >> 12) & 0x0f) | 0xe0);
+        bytes[outAt + 1] = (byte) (((c >> 6) & 0x3f) | 0x80);
+        bytes[outAt + 2] = (byte) ((c & 0x3f) | 0x80);
+        outAt += 3;
+      }
+    }
+
+    byte[] result = new byte[outAt];
+    System.arraycopy(bytes, 0, result, 0, outAt);
+    return result;
+  }
+
+  /**
+   * Converts an array of UTF-8 bytes into a string.
+   *
+   * @param bytes {@code non-null;} the bytes to convert
+   * @return {@code non-null;} the converted string
+   */
+  public static String utf8BytesToString(ByteArray bytes) {
+    int length = bytes.size();
+    char[] chars = new char[length]; // This is sized to avoid a realloc.
+    int outAt = 0;
+
+    for (int at = 0; length > 0; /*at*/) {
+      int v0 = bytes.getUnsignedByte(at);
+      char out;
+      switch (v0 >> 4) {
+        case 0x00:
+        case 0x01:
+        case 0x02:
+        case 0x03:
+        case 0x04:
+        case 0x05:
+        case 0x06:
+        case 0x07: {
+          // 0XXXXXXX -- single-byte encoding
+          length--;
+          if (v0 == 0) {
+            // A single zero byte is illegal.
+            return throwBadUtf8(v0, at);
+          }
+          out = (char) v0;
+          at++;
+          break;
+        }
+        case 0x0c:
+        case 0x0d: {
+          // 110XXXXX -- two-byte encoding
+          length -= 2;
+          if (length < 0) {
+            return throwBadUtf8(v0, at);
+          }
+          int v1 = bytes.getUnsignedByte(at + 1);
+          if ((v1 & 0xc0) != 0x80) {
+            return throwBadUtf8(v1, at + 1);
+          }
+          int value = ((v0 & 0x1f) << 6) | (v1 & 0x3f);
+          if ((value != 0) && (value < 0x80)) {
+            /*
+             * This should have been represented with
+             * one-byte encoding.
+             */
+            return throwBadUtf8(v1, at + 1);
+          }
+          out = (char) value;
+          at += 2;
+          break;
+        }
+        case 0x0e: {
+          // 1110XXXX -- three-byte encoding
+          length -= 3;
+          if (length < 0) {
+            return throwBadUtf8(v0, at);
+          }
+          int v1 = bytes.getUnsignedByte(at + 1);
+          if ((v1 & 0xc0) != 0x80) {
+            return throwBadUtf8(v1, at + 1);
+          }
+          int v2 = bytes.getUnsignedByte(at + 2);
+          if ((v1 & 0xc0) != 0x80) {
+            return throwBadUtf8(v2, at + 2);
+          }
+          int value = ((v0 & 0x0f) << 12) | ((v1 & 0x3f) << 6) | (v2 & 0x3f);
+          if (value < 0x800) {
+            /*
+             * This should have been represented with one- or
+             * two-byte encoding.
+             */
+            return throwBadUtf8(v2, at + 2);
+          }
+          out = (char) value;
+          at += 3;
+          break;
+        }
+        default: {
+          // 10XXXXXX, 1111XXXX -- illegal
+          return throwBadUtf8(v0, at);
+        }
+      }
+      chars[outAt] = out;
+      outAt++;
+    }
+
+    return new String(chars, 0, outAt);
+  }
+
+  /**
+   * Helper for {@link #utf8BytesToString}, which throws the right
+   * exception for a bogus utf-8 byte.
+   *
+   * @param value the byte value
+   * @param offset the file offset
+   * @return never
+   * @throws IllegalArgumentException always thrown
+   */
+  private static String throwBadUtf8(int value, int offset) {
+    throw new IllegalArgumentException(
+        "bad utf-8 byte " + Hex.u1(value) + " at offset " + Hex.u4(offset));
+  }
+
+  /**
+   * Constructs an instance from a {@code String}.
+   *
+   * @param string {@code non-null;} the UTF-8 value as a string
+   */
+  public CstString(String string) {
+    if (string == null) {
+      throw new NullPointerException("string == null");
+    }
+
+    this.string = string.intern();
+    this.bytes = new ByteArray(stringToUtf8Bytes(string));
+  }
+
+  /**
+   * Constructs an instance from some UTF-8 bytes.
+   *
+   * @param bytes {@code non-null;} array of the UTF-8 bytes
+   */
+  public CstString(ByteArray bytes) {
+    if (bytes == null) {
+      throw new NullPointerException("bytes == null");
+    }
+
+    this.bytes = bytes;
+    this.string = utf8BytesToString(bytes).intern();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof CstString)) {
+      return false;
+    }
+
+    return string.equals(((CstString) other).string);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return string.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    return string.compareTo(((CstString) other).string);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "string{\"" + toHuman() + "\"}";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "utf8";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    int len = string.length();
+    StringBuilder sb = new StringBuilder(len * 3 / 2);
+
+    for (int i = 0; i < len; i++) {
+      char c = string.charAt(i);
+      if ((c >= ' ') && (c < 0x7f)) {
+        if ((c == '\'') || (c == '\"') || (c == '\\')) {
+          sb.append('\\');
+        }
+        sb.append(c);
+      } else if (c <= 0x7f) {
+        switch (c) {
+          case '\n':
+            sb.append("\\n");
+            break;
+          case '\r':
+            sb.append("\\r");
+            break;
+          case '\t':
+            sb.append("\\t");
+            break;
+          default: {
+            /*
+             * Represent the character as an octal escape.
+             * If the next character is a valid octal
+             * digit, disambiguate by using the
+             * three-digit form.
+             */
+            char nextChar = (i < (len - 1)) ? string.charAt(i + 1) : 0;
+            boolean displayZero = (nextChar >= '0') && (nextChar <= '7');
+            sb.append('\\');
+            for (int shift = 6; shift >= 0; shift -= 3) {
+              char outChar = (char) (((c >> shift) & 7) + '0');
+              if ((outChar != '0') || displayZero) {
+                sb.append(outChar);
+                displayZero = true;
+              }
             }
-        }
-
-        byte[] result = new byte[outAt];
-        System.arraycopy(bytes, 0, result, 0, outAt);
-        return result;
-    }
-
-    /**
-     * Converts an array of UTF-8 bytes into a string.
-     *
-     * @param bytes {@code non-null;} the bytes to convert
-     * @return {@code non-null;} the converted string
-     */
-    public static String utf8BytesToString(ByteArray bytes) {
-        int length = bytes.size();
-        char[] chars = new char[length]; // This is sized to avoid a realloc.
-        int outAt = 0;
-
-        for (int at = 0; length > 0; /*at*/) {
-            int v0 = bytes.getUnsignedByte(at);
-            char out;
-            switch (v0 >> 4) {
-                case 0x00: case 0x01: case 0x02: case 0x03:
-                case 0x04: case 0x05: case 0x06: case 0x07: {
-                    // 0XXXXXXX -- single-byte encoding
-                    length--;
-                    if (v0 == 0) {
-                        // A single zero byte is illegal.
-                        return throwBadUtf8(v0, at);
-                    }
-                    out = (char) v0;
-                    at++;
-                    break;
-                }
-                case 0x0c: case 0x0d: {
-                    // 110XXXXX -- two-byte encoding
-                    length -= 2;
-                    if (length < 0) {
-                        return throwBadUtf8(v0, at);
-                    }
-                    int v1 = bytes.getUnsignedByte(at + 1);
-                    if ((v1 & 0xc0) != 0x80) {
-                        return throwBadUtf8(v1, at + 1);
-                    }
-                    int value = ((v0 & 0x1f) << 6) | (v1 & 0x3f);
-                    if ((value != 0) && (value < 0x80)) {
-                        /*
-                         * This should have been represented with
-                         * one-byte encoding.
-                         */
-                        return throwBadUtf8(v1, at + 1);
-                    }
-                    out = (char) value;
-                    at += 2;
-                    break;
-                }
-                case 0x0e: {
-                    // 1110XXXX -- three-byte encoding
-                    length -= 3;
-                    if (length < 0) {
-                        return throwBadUtf8(v0, at);
-                    }
-                    int v1 = bytes.getUnsignedByte(at + 1);
-                    if ((v1 & 0xc0) != 0x80) {
-                        return throwBadUtf8(v1, at + 1);
-                    }
-                    int v2 = bytes.getUnsignedByte(at + 2);
-                    if ((v1 & 0xc0) != 0x80) {
-                        return throwBadUtf8(v2, at + 2);
-                    }
-                    int value = ((v0 & 0x0f) << 12) | ((v1 & 0x3f) << 6) |
-                        (v2 & 0x3f);
-                    if (value < 0x800) {
-                        /*
-                         * This should have been represented with one- or
-                         * two-byte encoding.
-                         */
-                        return throwBadUtf8(v2, at + 2);
-                    }
-                    out = (char) value;
-                    at += 3;
-                    break;
-                }
-                default: {
-                    // 10XXXXXX, 1111XXXX -- illegal
-                    return throwBadUtf8(v0, at);
-                }
+            if (!displayZero) {
+              // Ironic edge case: The original value was 0.
+              sb.append('0');
             }
-            chars[outAt] = out;
-            outAt++;
+            break;
+          }
         }
-
-        return new String(chars, 0, outAt);
+      } else {
+        sb.append("\\u");
+        sb.append(Character.forDigit(c >> 12, 16));
+        sb.append(Character.forDigit((c >> 8) & 0x0f, 16));
+        sb.append(Character.forDigit((c >> 4) & 0x0f, 16));
+        sb.append(Character.forDigit(c & 0x0f, 16));
+      }
     }
 
-    /**
-     * Helper for {@link #utf8BytesToString}, which throws the right
-     * exception for a bogus utf-8 byte.
-     *
-     * @param value the byte value
-     * @param offset the file offset
-     * @return never
-     * @throws IllegalArgumentException always thrown
-     */
-    private static String throwBadUtf8(int value, int offset) {
-        throw new IllegalArgumentException("bad utf-8 byte " + Hex.u1(value) +
-                                           " at offset " + Hex.u4(offset));
+    return sb.toString();
+  }
+
+  /**
+   * Gets the value as a human-oriented string, surrounded by double
+   * quotes.
+   *
+   * @return {@code non-null;} the quoted string
+   */
+  public String toQuoted() {
+    return '\"' + toHuman() + '\"';
+  }
+
+  /**
+   * Gets the value as a human-oriented string, surrounded by double
+   * quotes, but ellipsizes the result if it is longer than the given
+   * maximum length
+   *
+   * @param maxLength {@code >= 5;} the maximum length of the string to return
+   * @return {@code non-null;} the quoted string
+   */
+  public String toQuoted(int maxLength) {
+    String string = toHuman();
+    int length = string.length();
+    String ellipses;
+
+    if (length <= (maxLength - 2)) {
+      ellipses = "";
+    } else {
+      string = string.substring(0, maxLength - 5);
+      ellipses = "...";
     }
 
-    /**
-     * Constructs an instance from a {@code String}.
-     *
-     * @param string {@code non-null;} the UTF-8 value as a string
-     */
-    public CstString(String string) {
-        if (string == null) {
-            throw new NullPointerException("string == null");
-        }
+    return '\"' + string + ellipses + '\"';
+  }
 
-        this.string = string.intern();
-        this.bytes = new ByteArray(stringToUtf8Bytes(string));
-    }
+  /**
+   * Gets the UTF-8 value as a string.
+   * The returned string is always already interned.
+   *
+   * @return {@code non-null;} the UTF-8 value as a string
+   */
+  public String getString() {
+    return string;
+  }
 
-    /**
-     * Constructs an instance from some UTF-8 bytes.
-     *
-     * @param bytes {@code non-null;} array of the UTF-8 bytes
-     */
-    public CstString(ByteArray bytes) {
-        if (bytes == null) {
-            throw new NullPointerException("bytes == null");
-        }
+  /**
+   * Gets the UTF-8 value as UTF-8 encoded bytes.
+   *
+   * @return {@code non-null;} an array of the UTF-8 bytes
+   */
+  public ByteArray getBytes() {
+    return bytes;
+  }
 
-        this.bytes = bytes;
-        this.string = utf8BytesToString(bytes).intern();
-    }
+  /**
+   * Gets the size of this instance as UTF-8 code points. That is,
+   * get the number of bytes in the UTF-8 encoding of this instance.
+   *
+   * @return {@code >= 0;} the UTF-8 size
+   */
+  public int getUtf8Size() {
+    return bytes.size();
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof CstString)) {
-            return false;
-        }
+  /**
+   * Gets the size of this instance as UTF-16 code points. That is,
+   * get the number of 16-bit chars in the UTF-16 encoding of this
+   * instance. This is the same as the {@code length} of the
+   * Java {@code String} representation of this instance.
+   *
+   * @return {@code >= 0;} the UTF-16 size
+   */
+  public int getUtf16Size() {
+    return string.length();
+  }
 
-        return string.equals(((CstString) other).string);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return string.hashCode();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        return string.compareTo(((CstString) other).string);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return "string{\"" + toHuman() + "\"}";
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "utf8";
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        int len = string.length();
-        StringBuilder sb = new StringBuilder(len * 3 / 2);
-
-        for (int i = 0; i < len; i++) {
-            char c = string.charAt(i);
-            if ((c >= ' ') && (c < 0x7f)) {
-                if ((c == '\'') || (c == '\"') || (c == '\\')) {
-                    sb.append('\\');
-                }
-                sb.append(c);
-            } else if (c <= 0x7f) {
-                switch (c) {
-                    case '\n': sb.append("\\n"); break;
-                    case '\r': sb.append("\\r"); break;
-                    case '\t': sb.append("\\t"); break;
-                    default: {
-                        /*
-                         * Represent the character as an octal escape.
-                         * If the next character is a valid octal
-                         * digit, disambiguate by using the
-                         * three-digit form.
-                         */
-                        char nextChar =
-                            (i < (len - 1)) ? string.charAt(i + 1) : 0;
-                        boolean displayZero =
-                            (nextChar >= '0') && (nextChar <= '7');
-                        sb.append('\\');
-                        for (int shift = 6; shift >= 0; shift -= 3) {
-                            char outChar = (char) (((c >> shift) & 7) + '0');
-                            if ((outChar != '0') || displayZero) {
-                                sb.append(outChar);
-                                displayZero = true;
-                            }
-                        }
-                        if (! displayZero) {
-                            // Ironic edge case: The original value was 0.
-                            sb.append('0');
-                        }
-                        break;
-                    }
-                }
-            } else {
-                sb.append("\\u");
-                sb.append(Character.forDigit(c >> 12, 16));
-                sb.append(Character.forDigit((c >> 8) & 0x0f, 16));
-                sb.append(Character.forDigit((c >> 4) & 0x0f, 16));
-                sb.append(Character.forDigit(c & 0x0f, 16));
-            }
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * Gets the value as a human-oriented string, surrounded by double
-     * quotes.
-     *
-     * @return {@code non-null;} the quoted string
-     */
-    public String toQuoted() {
-        return '\"' + toHuman() + '\"';
-    }
-
-    /**
-     * Gets the value as a human-oriented string, surrounded by double
-     * quotes, but ellipsizes the result if it is longer than the given
-     * maximum length
-     *
-     * @param maxLength {@code >= 5;} the maximum length of the string to return
-     * @return {@code non-null;} the quoted string
-     */
-    public String toQuoted(int maxLength) {
-        String string = toHuman();
-        int length = string.length();
-        String ellipses;
-
-        if (length <= (maxLength - 2)) {
-            ellipses = "";
-        } else {
-            string = string.substring(0, maxLength - 5);
-            ellipses = "...";
-        }
-
-        return '\"' + string + ellipses + '\"';
-    }
-
-    /**
-     * Gets the UTF-8 value as a string.
-     * The returned string is always already interned.
-     *
-     * @return {@code non-null;} the UTF-8 value as a string
-     */
-    public String getString() {
-        return string;
-    }
-
-    /**
-     * Gets the UTF-8 value as UTF-8 encoded bytes.
-     *
-     * @return {@code non-null;} an array of the UTF-8 bytes
-     */
-    public ByteArray getBytes() {
-        return bytes;
-    }
-
-    /**
-     * Gets the size of this instance as UTF-8 code points. That is,
-     * get the number of bytes in the UTF-8 encoding of this instance.
-     *
-     * @return {@code >= 0;} the UTF-8 size
-     */
-    public int getUtf8Size() {
-        return bytes.size();
-    }
-
-    /**
-     * Gets the size of this instance as UTF-16 code points. That is,
-     * get the number of 16-bit chars in the UTF-16 encoding of this
-     * instance. This is the same as the {@code length} of the
-     * Java {@code String} representation of this instance.
-     *
-     * @return {@code >= 0;} the UTF-16 size
-     */
-    public int getUtf16Size() {
-        return string.length();
-    }
-
-    public Type getType() {
-        return Type.STRING;
-    }
+  @Override
+  public Type getType() {
+    return Type.STRING;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstType.java b/dx/src/com/android/jack/dx/rop/cst/CstType.java
index 26d5a07..4ef8ad5 100644
--- a/dx/src/com/android/jack/dx/rop/cst/CstType.java
+++ b/dx/src/com/android/jack/dx/rop/cst/CstType.java
@@ -24,227 +24,236 @@
  * Constants that represent an arbitrary type (reference or primitive).
  */
 public final class CstType extends TypedConstant {
-    /** {@code non-null;} map of interned types */
-    private static final HashMap<Type, CstType> interns =
-        new HashMap<Type, CstType>(100);
+  /** {@code non-null;} map of interned types */
+  private static final HashMap<Type, CstType> interns = new HashMap<Type, CstType>(100);
 
-    /** {@code non-null;} instance corresponding to the class {@code Object} */
-    public static final CstType OBJECT = intern(Type.OBJECT);
+  /** {@code non-null;} instance corresponding to the class {@code Object} */
+  public static final CstType OBJECT = intern(Type.OBJECT);
 
-    /** {@code non-null;} instance corresponding to the class {@code Boolean} */
-    public static final CstType BOOLEAN = intern(Type.BOOLEAN_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Boolean} */
+  public static final CstType BOOLEAN = intern(Type.BOOLEAN_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Byte} */
-    public static final CstType BYTE = intern(Type.BYTE_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Byte} */
+  public static final CstType BYTE = intern(Type.BYTE_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Character} */
-    public static final CstType CHARACTER = intern(Type.CHARACTER_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Character} */
+  public static final CstType CHARACTER = intern(Type.CHARACTER_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Double} */
-    public static final CstType DOUBLE = intern(Type.DOUBLE_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Double} */
+  public static final CstType DOUBLE = intern(Type.DOUBLE_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Float} */
-    public static final CstType FLOAT = intern(Type.FLOAT_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Float} */
+  public static final CstType FLOAT = intern(Type.FLOAT_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Long} */
-    public static final CstType LONG = intern(Type.LONG_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Long} */
+  public static final CstType LONG = intern(Type.LONG_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Integer} */
-    public static final CstType INTEGER = intern(Type.INTEGER_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Integer} */
+  public static final CstType INTEGER = intern(Type.INTEGER_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Short} */
-    public static final CstType SHORT = intern(Type.SHORT_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Short} */
+  public static final CstType SHORT = intern(Type.SHORT_CLASS);
 
-    /** {@code non-null;} instance corresponding to the class {@code Void} */
-    public static final CstType VOID = intern(Type.VOID_CLASS);
+  /** {@code non-null;} instance corresponding to the class {@code Void} */
+  public static final CstType VOID = intern(Type.VOID_CLASS);
 
-    /** {@code non-null;} instance corresponding to the type {@code boolean[]} */
-    public static final CstType BOOLEAN_ARRAY = intern(Type.BOOLEAN_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code boolean[]} */
+  public static final CstType BOOLEAN_ARRAY = intern(Type.BOOLEAN_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code byte[]} */
-    public static final CstType BYTE_ARRAY = intern(Type.BYTE_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code byte[]} */
+  public static final CstType BYTE_ARRAY = intern(Type.BYTE_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code char[]} */
-    public static final CstType CHAR_ARRAY = intern(Type.CHAR_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code char[]} */
+  public static final CstType CHAR_ARRAY = intern(Type.CHAR_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code double[]} */
-    public static final CstType DOUBLE_ARRAY = intern(Type.DOUBLE_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code double[]} */
+  public static final CstType DOUBLE_ARRAY = intern(Type.DOUBLE_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code float[]} */
-    public static final CstType FLOAT_ARRAY = intern(Type.FLOAT_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code float[]} */
+  public static final CstType FLOAT_ARRAY = intern(Type.FLOAT_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code long[]} */
-    public static final CstType LONG_ARRAY = intern(Type.LONG_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code long[]} */
+  public static final CstType LONG_ARRAY = intern(Type.LONG_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code int[]} */
-    public static final CstType INT_ARRAY = intern(Type.INT_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code int[]} */
+  public static final CstType INT_ARRAY = intern(Type.INT_ARRAY);
 
-    /** {@code non-null;} instance corresponding to the type {@code short[]} */
-    public static final CstType SHORT_ARRAY = intern(Type.SHORT_ARRAY);
+  /** {@code non-null;} instance corresponding to the type {@code short[]} */
+  public static final CstType SHORT_ARRAY = intern(Type.SHORT_ARRAY);
 
-    /** {@code non-null;} the underlying type */
-    private final Type type;
+  /** {@code non-null;} the underlying type */
+  private final Type type;
 
-    /**
-     * {@code null-ok;} the type descriptor corresponding to this instance, if
-     * calculated
-     */
-    private CstString descriptor;
+  /**
+   * {@code null-ok;} the type descriptor corresponding to this instance, if
+   * calculated
+   */
+  private CstString descriptor;
 
-    /**
-     * Returns an instance of this class that represents the wrapper
-     * class corresponding to a given primitive type. For example, if
-     * given {@link Type#INT}, this method returns the class reference
-     * {@code java.lang.Integer}.
-     *
-     * @param primitiveType {@code non-null;} the primitive type
-     * @return {@code non-null;} the corresponding wrapper class
-     */
-    public static CstType forBoxedPrimitiveType(Type primitiveType) {
-        switch (primitiveType.getBasicType()) {
-            case Type.BT_BOOLEAN: return BOOLEAN;
-            case Type.BT_BYTE:    return BYTE;
-            case Type.BT_CHAR:    return CHARACTER;
-            case Type.BT_DOUBLE:  return DOUBLE;
-            case Type.BT_FLOAT:   return FLOAT;
-            case Type.BT_INT:     return INTEGER;
-            case Type.BT_LONG:    return LONG;
-            case Type.BT_SHORT:   return SHORT;
-            case Type.BT_VOID:    return VOID;
-        }
-
-        throw new IllegalArgumentException("not primitive: " + primitiveType);
+  /**
+   * Returns an instance of this class that represents the wrapper
+   * class corresponding to a given primitive type. For example, if
+   * given {@link Type#INT}, this method returns the class reference
+   * {@code java.lang.Integer}.
+   *
+   * @param primitiveType {@code non-null;} the primitive type
+   * @return {@code non-null;} the corresponding wrapper class
+   */
+  public static CstType forBoxedPrimitiveType(Type primitiveType) {
+    switch (primitiveType.getBasicType()) {
+      case Type.BT_BOOLEAN:
+        return BOOLEAN;
+      case Type.BT_BYTE:
+        return BYTE;
+      case Type.BT_CHAR:
+        return CHARACTER;
+      case Type.BT_DOUBLE:
+        return DOUBLE;
+      case Type.BT_FLOAT:
+        return FLOAT;
+      case Type.BT_INT:
+        return INTEGER;
+      case Type.BT_LONG:
+        return LONG;
+      case Type.BT_SHORT:
+        return SHORT;
+      case Type.BT_VOID:
+        return VOID;
     }
 
-    /**
-     * Returns an interned instance of this class for the given type.
-     *
-     * @param type {@code non-null;} the underlying type
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static CstType intern(Type type) {
-        synchronized (interns) {
-            CstType cst = interns.get(type);
+    throw new IllegalArgumentException("not primitive: " + primitiveType);
+  }
 
-            if (cst == null) {
-                cst = new CstType(type);
-                interns.put(type, cst);
-            }
+  /**
+   * Returns an interned instance of this class for the given type.
+   *
+   * @param type {@code non-null;} the underlying type
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static CstType intern(Type type) {
+    synchronized (interns) {
+      CstType cst = interns.get(type);
 
-            return cst;
-        }
+      if (cst == null) {
+        cst = new CstType(type);
+        interns.put(type, cst);
+      }
+
+      return cst;
+    }
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param type {@code non-null;} the underlying type
+   */
+  public CstType(Type type) {
+    if (type == null) {
+      throw new NullPointerException("type == null");
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param type {@code non-null;} the underlying type
-     */
-    public CstType(Type type) {
-        if (type == null) {
-            throw new NullPointerException("type == null");
-        }
-
-        if (type == type.KNOWN_NULL) {
-            throw new UnsupportedOperationException(
-                    "KNOWN_NULL is not representable");
-        }
-
-        this.type = type;
-        this.descriptor = null;
+    if (type == Type.KNOWN_NULL) {
+      throw new UnsupportedOperationException("KNOWN_NULL is not representable");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (!(other instanceof CstType)) {
-            return false;
-        }
+    this.type = type;
+    this.descriptor = null;
+  }
 
-        return type == ((CstType) other).type;
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (!(other instanceof CstType)) {
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return type.hashCode();
+    return type == ((CstType) other).type;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return type.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(Constant other) {
+    String thisDescriptor = type.getDescriptor();
+    String otherDescriptor = ((CstType) other).type.getDescriptor();
+    return thisDescriptor.compareTo(otherDescriptor);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "type{" + toHuman() + '}';
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return Type.CLASS;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String typeName() {
+    return "type";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return type.toHuman();
+  }
+
+  /**
+   * Gets the underlying type (as opposed to the type corresponding
+   * to this instance as a constant, which is always
+   * {@code Class}).
+   *
+   * @return {@code non-null;} the type corresponding to the name
+   */
+  public Type getClassType() {
+    return type;
+  }
+
+  /**
+   * Gets the type descriptor for this instance.
+   *
+   * @return {@code non-null;} the descriptor
+   */
+  public CstString getDescriptor() {
+    if (descriptor == null) {
+      descriptor = new CstString(type.getDescriptor());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    protected int compareTo0(Constant other) {
-        String thisDescriptor = type.getDescriptor();
-        String otherDescriptor = ((CstType) other).type.getDescriptor();
-        return thisDescriptor.compareTo(otherDescriptor);
-    }
+    return descriptor;
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return "type{" + toHuman() + '}';
+  /**
+   * Returns a human readable package name for this type, like "java.util".
+   * If this is an array type, this returns the package name of the array's
+   * component type. If this is a primitive type, this returns "default".
+   */
+  public String getPackageName() {
+    // descriptor is a string like "[[Ljava/util/String;"
+    String descriptor = getDescriptor().getString();
+    int lastSlash = descriptor.lastIndexOf('/');
+    int lastLeftSquare = descriptor.lastIndexOf('['); // -1 unless this is an array
+    if (lastSlash == -1) {
+      return "default";
+    } else {
+      // +2 to skip the '[' and the 'L' prefix
+      return descriptor.substring(lastLeftSquare + 2, lastSlash).replace('/', '.');
     }
-
-    /** {@inheritDoc} */
-    public Type getType() {
-        return Type.CLASS;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String typeName() {
-        return "type";
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isCategory2() {
-        return false;
-    }
-
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return type.toHuman();
-    }
-
-    /**
-     * Gets the underlying type (as opposed to the type corresponding
-     * to this instance as a constant, which is always
-     * {@code Class}).
-     *
-     * @return {@code non-null;} the type corresponding to the name
-     */
-    public Type getClassType() {
-        return type;
-    }
-
-    /**
-     * Gets the type descriptor for this instance.
-     *
-     * @return {@code non-null;} the descriptor
-     */
-    public CstString getDescriptor() {
-        if (descriptor == null) {
-            descriptor = new CstString(type.getDescriptor());
-        }
-
-        return descriptor;
-    }
-
-    /**
-     * Returns a human readable package name for this type, like "java.util".
-     * If this is an array type, this returns the package name of the array's
-     * component type. If this is a primitive type, this returns "default".
-     */
-    public String getPackageName() {
-        // descriptor is a string like "[[Ljava/util/String;"
-        String descriptor = getDescriptor().getString();
-        int lastSlash = descriptor.lastIndexOf('/');
-        int lastLeftSquare = descriptor.lastIndexOf('['); // -1 unless this is an array
-        if (lastSlash == -1) {
-            return "default";
-        } else {
-            // +2 to skip the '[' and the 'L' prefix
-            return descriptor.substring(lastLeftSquare + 2, lastSlash).replace('/', '.');
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/StdConstantPool.java b/dx/src/com/android/jack/dx/rop/cst/StdConstantPool.java
index ab16a2e..3036484 100644
--- a/dx/src/com/android/jack/dx/rop/cst/StdConstantPool.java
+++ b/dx/src/com/android/jack/dx/rop/cst/StdConstantPool.java
@@ -24,116 +24,117 @@
  * Standard implementation of {@link ConstantPool}, which directly stores
  * an array of {@link Constant} objects and can be made immutable.
  */
-public final class StdConstantPool
-        extends MutabilityControl implements ConstantPool {
-    /** {@code non-null;} array of entries */
-    private final Constant[] entries;
+public final class StdConstantPool extends MutabilityControl implements ConstantPool {
+  /** {@code non-null;} array of entries */
+  private final Constant[] entries;
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the pool; this corresponds to the
-     * class file field {@code constant_pool_count}, and is in fact
-     * always at least one more than the actual size of the constant pool,
-     * as element {@code 0} is always invalid.
-     */
-    public StdConstantPool(int size) {
-        super(size > 1);
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the pool; this corresponds to the
+   * class file field {@code constant_pool_count}, and is in fact
+   * always at least one more than the actual size of the constant pool,
+   * as element {@code 0} is always invalid.
+   */
+  public StdConstantPool(int size) {
+    super(size > 1);
 
-        if (size < 1) {
-            throw new IllegalArgumentException("size < 1");
-        }
-
-        entries = new Constant[size];
+    if (size < 1) {
+      throw new IllegalArgumentException("size < 1");
     }
 
-    /** {@inheritDoc} */
-    public int size() {
-        return entries.length;
+    entries = new Constant[size];
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int size() {
+    return entries.length;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Constant getOrNull(int n) {
+    try {
+      return entries[n];
+    } catch (IndexOutOfBoundsException ex) {
+      // Translate the exception.
+      return throwInvalid(n);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Constant get0Ok(int n) {
+    if (n == 0) {
+      return null;
     }
 
-    /** {@inheritDoc} */
-    public Constant getOrNull(int n) {
-        try {
-            return entries[n];
-        } catch (IndexOutOfBoundsException ex) {
-            // Translate the exception.
-            return throwInvalid(n);
-        }
+    return get(n);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Constant get(int n) {
+    try {
+      Constant result = entries[n];
+
+      if (result == null) {
+        throwInvalid(n);
+      }
+
+      return result;
+    } catch (IndexOutOfBoundsException ex) {
+      // Translate the exception.
+      return throwInvalid(n);
+    }
+  }
+
+  /**
+   * Sets the entry at the given index.
+   *
+   * @param n {@code >= 1, < size();} which entry
+   * @param cst {@code null-ok;} the constant to store
+   */
+  public void set(int n, Constant cst) {
+    throwIfImmutable();
+
+    boolean cat2 = (cst != null) && cst.isCategory2();
+
+    if (n < 1) {
+      throw new IllegalArgumentException("n < 1");
     }
 
-    /** {@inheritDoc} */
-    public Constant get0Ok(int n) {
-        if (n == 0) {
-            return null;
-        }
-
-        return get(n);
+    if (cat2) {
+      // Storing a category-2 entry nulls out the next index.
+      if (n == (entries.length - 1)) {
+        throw new IllegalArgumentException("(n == size - 1) && " + "cst.isCategory2()");
+      }
+      entries[n + 1] = null;
     }
 
-    /** {@inheritDoc} */
-    public Constant get(int n) {
-        try {
-            Constant result = entries[n];
-
-            if (result == null) {
-                throwInvalid(n);
-            }
-
-            return result;
-        } catch (IndexOutOfBoundsException ex) {
-            // Translate the exception.
-            return throwInvalid(n);
-        }
+    if ((cst != null) && (entries[n] == null)) {
+      /*
+       * Overwriting the second half of a category-2 entry nulls out
+       * the first half.
+       */
+      Constant prev = entries[n - 1];
+      if ((prev != null) && prev.isCategory2()) {
+        entries[n - 1] = null;
+      }
     }
 
-    /**
-     * Sets the entry at the given index.
-     *
-     * @param n {@code >= 1, < size();} which entry
-     * @param cst {@code null-ok;} the constant to store
-     */
-    public void set(int n, Constant cst) {
-        throwIfImmutable();
+    entries[n] = cst;
+  }
 
-        boolean cat2 = (cst != null) && cst.isCategory2();
-
-        if (n < 1) {
-            throw new IllegalArgumentException("n < 1");
-        }
-
-        if (cat2) {
-            // Storing a category-2 entry nulls out the next index.
-            if (n == (entries.length - 1)) {
-                throw new IllegalArgumentException("(n == size - 1) && " +
-                                                   "cst.isCategory2()");
-            }
-            entries[n + 1] = null;
-        }
-
-        if ((cst != null) && (entries[n] == null)) {
-            /*
-             * Overwriting the second half of a category-2 entry nulls out
-             * the first half.
-             */
-            Constant prev = entries[n - 1];
-            if ((prev != null) && prev.isCategory2()) {
-                entries[n - 1] = null;
-            }
-        }
-
-        entries[n] = cst;
-    }
-
-    /**
-     * Throws the right exception for an invalid cpi.
-     *
-     * @param idx the bad cpi
-     * @return never
-     * @throws ExceptionWithContext always thrown
-     */
-    private static Constant throwInvalid(int idx) {
-        throw new ExceptionWithContext("invalid constant pool index " +
-                                       Hex.u2(idx));
-    }
+  /**
+   * Throws the right exception for an invalid cpi.
+   *
+   * @param idx the bad cpi
+   * @return never
+   * @throws ExceptionWithContext always thrown
+   */
+  private static Constant throwInvalid(int idx) {
+    throw new ExceptionWithContext("invalid constant pool index " + Hex.u2(idx));
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/TypedConstant.java b/dx/src/com/android/jack/dx/rop/cst/TypedConstant.java
index b7b236e..2e44b28 100644
--- a/dx/src/com/android/jack/dx/rop/cst/TypedConstant.java
+++ b/dx/src/com/android/jack/dx/rop/cst/TypedConstant.java
@@ -21,29 +21,32 @@
 /**
  * Base class for constants which implement {@link TypeBearer}.
  */
-public abstract class TypedConstant
-        extends Constant implements TypeBearer {
-    /**
-     * {@inheritDoc}
-     *
-     * This implementation always returns {@code this}.
-     */
-    public final TypeBearer getFrameType() {
-        return this;
-    }
+public abstract class TypedConstant extends Constant implements TypeBearer {
+  /**
+   * {@inheritDoc}
+   *
+   * This implementation always returns {@code this}.
+   */
+  @Override
+  public final TypeBearer getFrameType() {
+    return this;
+  }
 
-    /** {@inheritDoc} */
-    public final int getBasicType() {
-        return getType().getBasicType();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final int getBasicType() {
+    return getType().getBasicType();
+  }
 
-    /** {@inheritDoc} */
-    public final int getBasicFrameType() {
-        return getType().getBasicFrameType();
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final int getBasicFrameType() {
+    return getType().getBasicFrameType();
+  }
 
-    /** {@inheritDoc} */
-    public final boolean isConstant() {
-        return true;
-    }
+  /** {@inheritDoc} */
+  @Override
+  public final boolean isConstant() {
+    return true;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/cst/Zeroes.java b/dx/src/com/android/jack/dx/rop/cst/Zeroes.java
index 00842cb..2550ec0 100644
--- a/dx/src/com/android/jack/dx/rop/cst/Zeroes.java
+++ b/dx/src/com/android/jack/dx/rop/cst/Zeroes.java
@@ -22,34 +22,42 @@
  * Utility for turning types into zeroes.
  */
 public final class Zeroes {
-    /**
-     * This class is uninstantiable.
-     */
-    private Zeroes() {
-        // This space intentionally left blank.
-    }
+  /**
+   * This class is uninstantiable.
+   */
+  private Zeroes() {
+    // This space intentionally left blank.
+  }
 
-    /**
-     * Gets the "zero" (or {@code null}) value for the given type.
-     *
-     * @param type {@code non-null;} the type in question
-     * @return {@code non-null;} its "zero" value
-     */
-    public static Constant zeroFor(Type type) {
-        switch (type.getBasicType()) {
-            case Type.BT_BOOLEAN: return CstBoolean.VALUE_FALSE;
-            case Type.BT_BYTE:    return CstByte.VALUE_0;
-            case Type.BT_CHAR:    return CstChar.VALUE_0;
-            case Type.BT_DOUBLE:  return CstDouble.VALUE_0;
-            case Type.BT_FLOAT:   return CstFloat.VALUE_0;
-            case Type.BT_INT:     return CstInteger.VALUE_0;
-            case Type.BT_LONG:    return CstLong.VALUE_0;
-            case Type.BT_SHORT:   return CstShort.VALUE_0;
-            case Type.BT_OBJECT:  return CstKnownNull.THE_ONE;
-            default: {
-                throw new UnsupportedOperationException("no zero for type: " +
-                        type.toHuman());
-            }
-        }
+  /**
+   * Gets the "zero" (or {@code null}) value for the given type.
+   *
+   * @param type {@code non-null;} the type in question
+   * @return {@code non-null;} its "zero" value
+   */
+  public static Constant zeroFor(Type type) {
+    switch (type.getBasicType()) {
+      case Type.BT_BOOLEAN:
+        return CstBoolean.VALUE_FALSE;
+      case Type.BT_BYTE:
+        return CstByte.VALUE_0;
+      case Type.BT_CHAR:
+        return CstChar.VALUE_0;
+      case Type.BT_DOUBLE:
+        return CstDouble.VALUE_0;
+      case Type.BT_FLOAT:
+        return CstFloat.VALUE_0;
+      case Type.BT_INT:
+        return CstInteger.VALUE_0;
+      case Type.BT_LONG:
+        return CstLong.VALUE_0;
+      case Type.BT_SHORT:
+        return CstShort.VALUE_0;
+      case Type.BT_OBJECT:
+        return CstKnownNull.THE_ONE;
+      default: {
+        throw new UnsupportedOperationException("no zero for type: " + type.toHuman());
+      }
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/type/Prototype.java b/dx/src/com/android/jack/dx/rop/type/Prototype.java
index 547f1ca..ed4e46c 100644
--- a/dx/src/com/android/jack/dx/rop/type/Prototype.java
+++ b/dx/src/com/android/jack/dx/rop/type/Prototype.java
@@ -24,377 +24,374 @@
  * using {@code ==}.
  */
 public final class Prototype implements Comparable<Prototype> {
-    /** {@code non-null;} intern table mapping string descriptors to instances */
-    private static final HashMap<String, Prototype> internTable =
-        new HashMap<String, Prototype>(500);
+  /** {@code non-null;} intern table mapping string descriptors to instances */
+  private static final HashMap<String, Prototype> internTable = new HashMap<String, Prototype>(500);
 
-    /** {@code non-null;} method descriptor */
-    private final String descriptor;
+  /** {@code non-null;} method descriptor */
+  private final String descriptor;
 
-    /** {@code non-null;} return type */
-    private final Type returnType;
+  /** {@code non-null;} return type */
+  private final Type returnType;
 
-    /** {@code non-null;} list of parameter types */
-    private final StdTypeList parameterTypes;
+  /** {@code non-null;} list of parameter types */
+  private final StdTypeList parameterTypes;
 
-    /** {@code null-ok;} list of parameter frame types, if calculated */
-    private StdTypeList parameterFrameTypes;
+  /** {@code null-ok;} list of parameter frame types, if calculated */
+  private StdTypeList parameterFrameTypes;
 
-    /**
-     * Returns the unique instance corresponding to the
-     * given method descriptor. See vmspec-2 sec4.3.3 for details on the
-     * field descriptor syntax.
-     *
-     * @param descriptor {@code non-null;} the descriptor
-     * @return {@code non-null;} the corresponding instance
-     * @throws IllegalArgumentException thrown if the descriptor has
-     * invalid syntax
+  /**
+   * Returns the unique instance corresponding to the
+   * given method descriptor. See vmspec-2 sec4.3.3 for details on the
+   * field descriptor syntax.
+   *
+   * @param descriptor {@code non-null;} the descriptor
+   * @return {@code non-null;} the corresponding instance
+   * @throws IllegalArgumentException thrown if the descriptor has
+   * invalid syntax
+   */
+  public static Prototype intern(String descriptor) {
+    if (descriptor == null) {
+      throw new NullPointerException("descriptor == null");
+    }
+
+    Prototype result;
+    synchronized (internTable) {
+      result = internTable.get(descriptor);
+    }
+    if (result != null) {
+      return result;
+    }
+
+    Type[] params = makeParameterArray(descriptor);
+    int paramCount = 0;
+    int at = 1;
+
+    for (;;) {
+      int startAt = at;
+      char c = descriptor.charAt(at);
+      if (c == ')') {
+        at++;
+        break;
+      }
+
+      // Skip array markers.
+      while (c == '[') {
+        at++;
+        c = descriptor.charAt(at);
+      }
+
+      if (c == 'L') {
+        // It looks like the start of a class name; find the end.
+        int endAt = descriptor.indexOf(';', at);
+        if (endAt == -1) {
+          throw new IllegalArgumentException("bad descriptor");
+        }
+        at = endAt + 1;
+      } else {
+        at++;
+      }
+
+      params[paramCount] = Type.intern(descriptor.substring(startAt, at));
+      paramCount++;
+    }
+
+    Type returnType = Type.internReturnType(descriptor.substring(at));
+    StdTypeList parameterTypes = new StdTypeList(paramCount);
+
+    for (int i = 0; i < paramCount; i++) {
+      parameterTypes.set(i, params[i]);
+    }
+
+    result = new Prototype(descriptor, returnType, parameterTypes);
+    return putIntern(result);
+  }
+
+  /**
+   * Helper for {@link #intern} which returns an empty array to
+   * populate with parsed parameter types, and which also ensures
+   * that there is a '(' at the start of the descriptor and a
+   * single ')' somewhere before the end.
+   *
+   * @param descriptor {@code non-null;} the descriptor string
+   * @return {@code non-null;} array large enough to hold all parsed parameter
+   * types, but which is likely actually larger than needed
+   */
+  private static Type[] makeParameterArray(String descriptor) {
+    int length = descriptor.length();
+
+    if (descriptor.charAt(0) != '(') {
+      throw new IllegalArgumentException("bad descriptor");
+    }
+
+    /*
+     * This is a cheesy way to establish an upper bound on the
+     * number of parameters: Just count capital letters.
      */
-    public static Prototype intern(String descriptor) {
-        if (descriptor == null) {
-            throw new NullPointerException("descriptor == null");
-        }
-
-        Prototype result;
-        synchronized (internTable) {
-            result = internTable.get(descriptor);
-        }
-        if (result != null) {
-            return result;
-        }
-
-        Type[] params = makeParameterArray(descriptor);
-        int paramCount = 0;
-        int at = 1;
-
-        for (;;) {
-            int startAt = at;
-            char c = descriptor.charAt(at);
-            if (c == ')') {
-                at++;
-                break;
-            }
-
-            // Skip array markers.
-            while (c == '[') {
-                at++;
-                c = descriptor.charAt(at);
-            }
-
-            if (c == 'L') {
-                // It looks like the start of a class name; find the end.
-                int endAt = descriptor.indexOf(';', at);
-                if (endAt == -1) {
-                    throw new IllegalArgumentException("bad descriptor");
-                }
-                at = endAt + 1;
-            } else {
-                at++;
-            }
-
-            params[paramCount] =
-                Type.intern(descriptor.substring(startAt, at));
-            paramCount++;
-        }
-
-        Type returnType = Type.internReturnType(descriptor.substring(at));
-        StdTypeList parameterTypes = new StdTypeList(paramCount);
-
-        for (int i = 0; i < paramCount; i++) {
-            parameterTypes.set(i, params[i]);
-        }
-
-        result = new Prototype(descriptor, returnType, parameterTypes);
-        return putIntern(result);
+    int closeAt = 0;
+    int maxParams = 0;
+    for (int i = 1; i < length; i++) {
+      char c = descriptor.charAt(i);
+      if (c == ')') {
+        closeAt = i;
+        break;
+      }
+      if ((c >= 'A') && (c <= 'Z')) {
+        maxParams++;
+      }
     }
 
-    /**
-     * Helper for {@link #intern} which returns an empty array to
-     * populate with parsed parameter types, and which also ensures
-     * that there is a '(' at the start of the descriptor and a
-     * single ')' somewhere before the end.
-     *
-     * @param descriptor {@code non-null;} the descriptor string
-     * @return {@code non-null;} array large enough to hold all parsed parameter
-     * types, but which is likely actually larger than needed
+    if ((closeAt == 0) || (closeAt == (length - 1))) {
+      throw new IllegalArgumentException("bad descriptor");
+    }
+
+    if (descriptor.indexOf(')', closeAt + 1) != -1) {
+      throw new IllegalArgumentException("bad descriptor");
+    }
+
+    return new Type[maxParams];
+  }
+
+  /**
+   * Interns an instance, adding to the descriptor as necessary based
+   * on the given definer, name, and flags. For example, an init
+   * method has an uninitialized object of type {@code definer}
+   * as its first argument.
+   *
+   * @param descriptor {@code non-null;} the descriptor string
+   * @param definer {@code non-null;} class the method is defined on
+   * @param isStatic whether this is a static method
+   * @param isInit whether this is an init method
+   * @return {@code non-null;} the interned instance
+   */
+  public static Prototype intern(String descriptor, Type definer, boolean isStatic,
+      boolean isInit) {
+    Prototype base = intern(descriptor);
+
+    if (isStatic) {
+      return base;
+    }
+
+    if (isInit) {
+      definer = definer.asUninitialized(Integer.MAX_VALUE);
+    }
+
+    return base.withFirstParameter(definer);
+  }
+
+  /**
+   * Interns an instance which consists of the given number of
+   * {@code int}s along with the given return type
+   *
+   * @param returnType {@code non-null;} the return type
+   * @param count {@code > 0;} the number of elements in the prototype
+   * @return {@code non-null;} the interned instance
+   */
+  public static Prototype internInts(Type returnType, int count) {
+    // Make the descriptor...
+
+    StringBuffer sb = new StringBuffer(100);
+
+    sb.append('(');
+
+    for (int i = 0; i < count; i++) {
+      sb.append('I');
+    }
+
+    sb.append(')');
+    sb.append(returnType.getDescriptor());
+
+    // ...and intern it.
+    return intern(sb.toString());
+  }
+
+  /**
+   * Constructs an instance. This is a private constructor; use one
+   * of the public static methods to get instances.
+   *
+   * @param descriptor {@code non-null;} the descriptor string
+   */
+  private Prototype(String descriptor, Type returnType, StdTypeList parameterTypes) {
+    if (descriptor == null) {
+      throw new NullPointerException("descriptor == null");
+    }
+
+    if (returnType == null) {
+      throw new NullPointerException("returnType == null");
+    }
+
+    if (parameterTypes == null) {
+      throw new NullPointerException("parameterTypes == null");
+    }
+
+    this.descriptor = descriptor;
+    this.returnType = returnType;
+    this.parameterTypes = parameterTypes;
+    this.parameterFrameTypes = null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (this == other) {
+      /*
+       * Since externally-visible instances are interned, this
+       * check helps weed out some easy cases.
+       */
+      return true;
+    }
+
+    if (!(other instanceof Prototype)) {
+      return false;
+    }
+
+    return descriptor.equals(((Prototype) other).descriptor);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return descriptor.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(Prototype other) {
+    if (this == other) {
+      return 0;
+    }
+
+    /*
+     * The return type is the major order, and then args in order,
+     * and then the shorter list comes first (similar to string
+     * sorting).
      */
-    private static Type[] makeParameterArray(String descriptor) {
-        int length = descriptor.length();
 
-        if (descriptor.charAt(0) != '(') {
-            throw new IllegalArgumentException("bad descriptor");
-        }
+int result = returnType.compareTo(other.returnType);
 
-        /*
-         * This is a cheesy way to establish an upper bound on the
-         * number of parameters: Just count capital letters.
-         */
-        int closeAt = 0;
-        int maxParams = 0;
-        for (int i = 1; i < length; i++) {
-            char c = descriptor.charAt(i);
-            if (c == ')') {
-                closeAt = i;
-                break;
-            }
-            if ((c >= 'A') && (c <= 'Z')) {
-                maxParams++;
-            }
-        }
-
-        if ((closeAt == 0) || (closeAt == (length - 1))) {
-            throw new IllegalArgumentException("bad descriptor");
-        }
-
-        if (descriptor.indexOf(')', closeAt + 1) != -1) {
-            throw new IllegalArgumentException("bad descriptor");
-        }
-
-        return new Type[maxParams];
+    if (result != 0) {
+      return result;
     }
 
-    /**
-     * Interns an instance, adding to the descriptor as necessary based
-     * on the given definer, name, and flags. For example, an init
-     * method has an uninitialized object of type {@code definer}
-     * as its first argument.
-     *
-     * @param descriptor {@code non-null;} the descriptor string
-     * @param definer {@code non-null;} class the method is defined on
-     * @param isStatic whether this is a static method
-     * @param isInit whether this is an init method
-     * @return {@code non-null;} the interned instance
-     */
-    public static Prototype intern(String descriptor, Type definer,
-            boolean isStatic, boolean isInit) {
-        Prototype base = intern(descriptor);
+    int thisSize = parameterTypes.size();
+    int otherSize = other.parameterTypes.size();
+    int size = Math.min(thisSize, otherSize);
 
-        if (isStatic) {
-            return base;
-        }
+    for (int i = 0; i < size; i++) {
+      Type thisType = parameterTypes.get(i);
+      Type otherType = other.parameterTypes.get(i);
 
-        if (isInit) {
-            definer = definer.asUninitialized(Integer.MAX_VALUE);
-        }
+      result = thisType.compareTo(otherType);
 
-        return base.withFirstParameter(definer);
+      if (result != 0) {
+        return result;
+      }
     }
 
-    /**
-     * Interns an instance which consists of the given number of
-     * {@code int}s along with the given return type
-     *
-     * @param returnType {@code non-null;} the return type
-     * @param count {@code > 0;} the number of elements in the prototype
-     * @return {@code non-null;} the interned instance
-     */
-    public static Prototype internInts(Type returnType, int count) {
-        // Make the descriptor...
+    if (thisSize < otherSize) {
+      return -1;
+    } else if (thisSize > otherSize) {
+      return 1;
+    } else {
+      return 0;
+    }
+  }
 
-        StringBuffer sb = new StringBuffer(100);
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return descriptor;
+  }
 
-        sb.append('(');
+  /**
+   * Gets the descriptor string.
+   *
+   * @return {@code non-null;} the descriptor
+   */
+  public String getDescriptor() {
+    return descriptor;
+  }
 
-        for (int i = 0; i < count; i++) {
-            sb.append('I');
+  /**
+   * Gets the return type.
+   *
+   * @return {@code non-null;} the return type
+   */
+  public Type getReturnType() {
+    return returnType;
+  }
+
+  /**
+   * Gets the list of parameter types.
+   *
+   * @return {@code non-null;} the list of parameter types
+   */
+  public StdTypeList getParameterTypes() {
+    return parameterTypes;
+  }
+
+  /**
+   * Gets the list of frame types corresponding to the list of parameter
+   * types. The difference between the two lists (if any) is that all
+   * "intlike" types (see {@link Type#isIntlike}) are replaced by
+   * {@link Type#INT}.
+   *
+   * @return {@code non-null;} the list of parameter frame types
+   */
+  public StdTypeList getParameterFrameTypes() {
+    if (parameterFrameTypes == null) {
+      int sz = parameterTypes.size();
+      StdTypeList list = new StdTypeList(sz);
+      boolean any = false;
+      for (int i = 0; i < sz; i++) {
+        Type one = parameterTypes.get(i);
+        if (one.isIntlike()) {
+          any = true;
+          one = Type.INT;
         }
-
-        sb.append(')');
-        sb.append(returnType.getDescriptor());
-
-        // ...and intern it.
-        return intern(sb.toString());
+        list.set(i, one);
+      }
+      parameterFrameTypes = any ? list : parameterTypes;
     }
 
-    /**
-     * Constructs an instance. This is a private constructor; use one
-     * of the public static methods to get instances.
-     *
-     * @param descriptor {@code non-null;} the descriptor string
-     */
-    private Prototype(String descriptor, Type returnType,
-            StdTypeList parameterTypes) {
-        if (descriptor == null) {
-            throw new NullPointerException("descriptor == null");
-        }
+    return parameterFrameTypes;
+  }
 
-        if (returnType == null) {
-            throw new NullPointerException("returnType == null");
-        }
+  /**
+   * Returns a new interned instance, which is the same as this instance,
+   * except that it has an additional parameter prepended to the original's
+   * argument list.
+   *
+   * @param param {@code non-null;} the new first parameter
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public Prototype withFirstParameter(Type param) {
+    String newDesc = "(" + param.getDescriptor() + descriptor.substring(1);
+    StdTypeList newParams = parameterTypes.withFirst(param);
 
-        if (parameterTypes == null) {
-            throw new NullPointerException("parameterTypes == null");
-        }
+    newParams.setImmutable();
 
-        this.descriptor = descriptor;
-        this.returnType = returnType;
-        this.parameterTypes = parameterTypes;
-        this.parameterFrameTypes = null;
+    Prototype result = new Prototype(newDesc, returnType, newParams);
+
+    return putIntern(result);
+  }
+
+  /**
+   * Puts the given instance in the intern table if it's not already
+   * there. If a conflicting value is already in the table, then leave it.
+   * Return the interned value.
+   *
+   * @param desc {@code non-null;} instance to make interned
+   * @return {@code non-null;} the actual interned object
+   */
+  private static Prototype putIntern(Prototype desc) {
+    synchronized (internTable) {
+      String descriptor = desc.getDescriptor();
+      Prototype already = internTable.get(descriptor);
+      if (already != null) {
+        return already;
+      }
+      internTable.put(descriptor, desc);
+      return desc;
     }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (this == other) {
-            /*
-             * Since externally-visible instances are interned, this
-             * check helps weed out some easy cases.
-             */
-            return true;
-        }
-
-        if (!(other instanceof Prototype)) {
-            return false;
-        }
-
-        return descriptor.equals(((Prototype) other).descriptor);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return descriptor.hashCode();
-    }
-
-    /** {@inheritDoc} */
-    public int compareTo(Prototype other) {
-        if (this == other) {
-            return 0;
-        }
-
-        /*
-         * The return type is the major order, and then args in order,
-         * and then the shorter list comes first (similar to string
-         * sorting).
-         */
-
-        int result = returnType.compareTo(other.returnType);
-
-        if (result != 0) {
-            return result;
-        }
-
-        int thisSize = parameterTypes.size();
-        int otherSize = other.parameterTypes.size();
-        int size = Math.min(thisSize, otherSize);
-
-        for (int i = 0; i < size; i++) {
-            Type thisType = parameterTypes.get(i);
-            Type otherType = other.parameterTypes.get(i);
-
-            result = thisType.compareTo(otherType);
-
-            if (result != 0) {
-                return result;
-            }
-        }
-
-        if (thisSize < otherSize) {
-            return -1;
-        } else if (thisSize > otherSize) {
-            return 1;
-        } else {
-            return 0;
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        return descriptor;
-    }
-
-    /**
-     * Gets the descriptor string.
-     *
-     * @return {@code non-null;} the descriptor
-     */
-    public String getDescriptor() {
-        return descriptor;
-    }
-
-    /**
-     * Gets the return type.
-     *
-     * @return {@code non-null;} the return type
-     */
-    public Type getReturnType() {
-        return returnType;
-    }
-
-    /**
-     * Gets the list of parameter types.
-     *
-     * @return {@code non-null;} the list of parameter types
-     */
-    public StdTypeList getParameterTypes() {
-        return parameterTypes;
-    }
-
-    /**
-     * Gets the list of frame types corresponding to the list of parameter
-     * types. The difference between the two lists (if any) is that all
-     * "intlike" types (see {@link Type#isIntlike}) are replaced by
-     * {@link Type#INT}.
-     *
-     * @return {@code non-null;} the list of parameter frame types
-     */
-    public StdTypeList getParameterFrameTypes() {
-        if (parameterFrameTypes == null) {
-            int sz = parameterTypes.size();
-            StdTypeList list = new StdTypeList(sz);
-            boolean any = false;
-            for (int i = 0; i < sz; i++) {
-                Type one = parameterTypes.get(i);
-                if (one.isIntlike()) {
-                    any = true;
-                    one = Type.INT;
-                }
-                list.set(i, one);
-            }
-            parameterFrameTypes = any ? list : parameterTypes;
-        }
-
-        return parameterFrameTypes;
-    }
-
-    /**
-     * Returns a new interned instance, which is the same as this instance,
-     * except that it has an additional parameter prepended to the original's
-     * argument list.
-     *
-     * @param param {@code non-null;} the new first parameter
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public Prototype withFirstParameter(Type param) {
-        String newDesc = "(" + param.getDescriptor() + descriptor.substring(1);
-        StdTypeList newParams = parameterTypes.withFirst(param);
-
-        newParams.setImmutable();
-
-        Prototype result =
-            new Prototype(newDesc, returnType, newParams);
-
-        return putIntern(result);
-    }
-
-    /**
-     * Puts the given instance in the intern table if it's not already
-     * there. If a conflicting value is already in the table, then leave it.
-     * Return the interned value.
-     *
-     * @param desc {@code non-null;} instance to make interned
-     * @return {@code non-null;} the actual interned object
-     */
-    private static Prototype putIntern(Prototype desc) {
-        synchronized (internTable) {
-            String descriptor = desc.getDescriptor();
-            Prototype already = internTable.get(descriptor);
-            if (already != null) {
-                return already;
-            }
-            internTable.put(descriptor, desc);
-            return desc;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/type/StdTypeList.java b/dx/src/com/android/jack/dx/rop/type/StdTypeList.java
index fe8242e..c4b5c4a 100644
--- a/dx/src/com/android/jack/dx/rop/type/StdTypeList.java
+++ b/dx/src/com/android/jack/dx/rop/type/StdTypeList.java
@@ -21,387 +21,367 @@
 /**
  * Standard implementation of {@link TypeList}.
  */
-public final class StdTypeList
-        extends FixedSizeList implements TypeList {
-    /** {@code non-null;} no-element instance */
-    public static final StdTypeList EMPTY = new StdTypeList(0);
+public final class StdTypeList extends FixedSizeList implements TypeList {
+  /** {@code non-null;} no-element instance */
+  public static final StdTypeList EMPTY = new StdTypeList(0);
 
-    /** {@code non-null;} the list {@code [int]} */
-    public static final StdTypeList INT = StdTypeList.make(Type.INT);
+  /** {@code non-null;} the list {@code [int]} */
+  public static final StdTypeList INT = StdTypeList.make(Type.INT);
 
-    /** {@code non-null;} the list {@code [long]} */
-    public static final StdTypeList LONG = StdTypeList.make(Type.LONG);
+  /** {@code non-null;} the list {@code [long]} */
+  public static final StdTypeList LONG = StdTypeList.make(Type.LONG);
 
-    /** {@code non-null;} the list {@code [float]} */
-    public static final StdTypeList FLOAT = StdTypeList.make(Type.FLOAT);
+  /** {@code non-null;} the list {@code [float]} */
+  public static final StdTypeList FLOAT = StdTypeList.make(Type.FLOAT);
 
-    /** {@code non-null;} the list {@code [double]} */
-    public static final StdTypeList DOUBLE = StdTypeList.make(Type.DOUBLE);
+  /** {@code non-null;} the list {@code [double]} */
+  public static final StdTypeList DOUBLE = StdTypeList.make(Type.DOUBLE);
 
-    /** {@code non-null;} the list {@code [Object]} */
-    public static final StdTypeList OBJECT = StdTypeList.make(Type.OBJECT);
+  /** {@code non-null;} the list {@code [Object]} */
+  public static final StdTypeList OBJECT = StdTypeList.make(Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [ReturnAddress]} */
-    public static final StdTypeList RETURN_ADDRESS
-            = StdTypeList.make(Type.RETURN_ADDRESS);
+  /** {@code non-null;} the list {@code [ReturnAddress]} */
+  public static final StdTypeList RETURN_ADDRESS = StdTypeList.make(Type.RETURN_ADDRESS);
 
-    /** {@code non-null;} the list {@code [Throwable]} */
-    public static final StdTypeList THROWABLE =
-        StdTypeList.make(Type.THROWABLE);
+  /** {@code non-null;} the list {@code [Throwable]} */
+  public static final StdTypeList THROWABLE = StdTypeList.make(Type.THROWABLE);
 
-    /** {@code non-null;} the list {@code [int, int]} */
-    public static final StdTypeList INT_INT =
-        StdTypeList.make(Type.INT, Type.INT);
+  /** {@code non-null;} the list {@code [int, int]} */
+  public static final StdTypeList INT_INT = StdTypeList.make(Type.INT, Type.INT);
 
-    /** {@code non-null;} the list {@code [long, long]} */
-    public static final StdTypeList LONG_LONG =
-        StdTypeList.make(Type.LONG, Type.LONG);
+  /** {@code non-null;} the list {@code [long, long]} */
+  public static final StdTypeList LONG_LONG = StdTypeList.make(Type.LONG, Type.LONG);
 
-    /** {@code non-null;} the list {@code [float, float]} */
-    public static final StdTypeList FLOAT_FLOAT =
-        StdTypeList.make(Type.FLOAT, Type.FLOAT);
+  /** {@code non-null;} the list {@code [float, float]} */
+  public static final StdTypeList FLOAT_FLOAT = StdTypeList.make(Type.FLOAT, Type.FLOAT);
 
-    /** {@code non-null;} the list {@code [double, double]} */
-    public static final StdTypeList DOUBLE_DOUBLE =
-        StdTypeList.make(Type.DOUBLE, Type.DOUBLE);
+  /** {@code non-null;} the list {@code [double, double]} */
+  public static final StdTypeList DOUBLE_DOUBLE = StdTypeList.make(Type.DOUBLE, Type.DOUBLE);
 
-    /** {@code non-null;} the list {@code [Object, Object]} */
-    public static final StdTypeList OBJECT_OBJECT =
-        StdTypeList.make(Type.OBJECT, Type.OBJECT);
+  /** {@code non-null;} the list {@code [Object, Object]} */
+  public static final StdTypeList OBJECT_OBJECT = StdTypeList.make(Type.OBJECT, Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [int, Object]} */
-    public static final StdTypeList INT_OBJECT =
-        StdTypeList.make(Type.INT, Type.OBJECT);
+  /** {@code non-null;} the list {@code [int, Object]} */
+  public static final StdTypeList INT_OBJECT = StdTypeList.make(Type.INT, Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [long, Object]} */
-    public static final StdTypeList LONG_OBJECT =
-        StdTypeList.make(Type.LONG, Type.OBJECT);
+  /** {@code non-null;} the list {@code [long, Object]} */
+  public static final StdTypeList LONG_OBJECT = StdTypeList.make(Type.LONG, Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [float, Object]} */
-    public static final StdTypeList FLOAT_OBJECT =
-        StdTypeList.make(Type.FLOAT, Type.OBJECT);
+  /** {@code non-null;} the list {@code [float, Object]} */
+  public static final StdTypeList FLOAT_OBJECT = StdTypeList.make(Type.FLOAT, Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [double, Object]} */
-    public static final StdTypeList DOUBLE_OBJECT =
-        StdTypeList.make(Type.DOUBLE, Type.OBJECT);
+  /** {@code non-null;} the list {@code [double, Object]} */
+  public static final StdTypeList DOUBLE_OBJECT = StdTypeList.make(Type.DOUBLE, Type.OBJECT);
 
-    /** {@code non-null;} the list {@code [long, int]} */
-    public static final StdTypeList LONG_INT =
-        StdTypeList.make(Type.LONG, Type.INT);
+  /** {@code non-null;} the list {@code [long, int]} */
+  public static final StdTypeList LONG_INT = StdTypeList.make(Type.LONG, Type.INT);
 
-    /** {@code non-null;} the list {@code [int[], int]} */
-    public static final StdTypeList INTARR_INT =
-        StdTypeList.make(Type.INT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int[], int]} */
+  public static final StdTypeList INTARR_INT = StdTypeList.make(Type.INT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [long[], int]} */
-    public static final StdTypeList LONGARR_INT =
-        StdTypeList.make(Type.LONG_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [long[], int]} */
+  public static final StdTypeList LONGARR_INT = StdTypeList.make(Type.LONG_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [float[], int]} */
-    public static final StdTypeList FLOATARR_INT =
-        StdTypeList.make(Type.FLOAT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [float[], int]} */
+  public static final StdTypeList FLOATARR_INT = StdTypeList.make(Type.FLOAT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [double[], int]} */
-    public static final StdTypeList DOUBLEARR_INT =
-        StdTypeList.make(Type.DOUBLE_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [double[], int]} */
+  public static final StdTypeList DOUBLEARR_INT = StdTypeList.make(Type.DOUBLE_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [Object[], int]} */
-    public static final StdTypeList OBJECTARR_INT =
-        StdTypeList.make(Type.OBJECT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [Object[], int]} */
+  public static final StdTypeList OBJECTARR_INT = StdTypeList.make(Type.OBJECT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [boolean[], int]} */
-    public static final StdTypeList BOOLEANARR_INT =
-        StdTypeList.make(Type.BOOLEAN_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [boolean[], int]} */
+  public static final StdTypeList BOOLEANARR_INT = StdTypeList.make(Type.BOOLEAN_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [byte[], int]} */
-    public static final StdTypeList BYTEARR_INT =
-        StdTypeList.make(Type.BYTE_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [byte[], int]} */
+  public static final StdTypeList BYTEARR_INT = StdTypeList.make(Type.BYTE_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [char[], int]} */
-    public static final StdTypeList CHARARR_INT =
-        StdTypeList.make(Type.CHAR_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [char[], int]} */
+  public static final StdTypeList CHARARR_INT = StdTypeList.make(Type.CHAR_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [short[], int]} */
-    public static final StdTypeList SHORTARR_INT =
-        StdTypeList.make(Type.SHORT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [short[], int]} */
+  public static final StdTypeList SHORTARR_INT = StdTypeList.make(Type.SHORT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [int, int[], int]} */
-    public static final StdTypeList INT_INTARR_INT =
-        StdTypeList.make(Type.INT, Type.INT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int, int[], int]} */
+  public static final StdTypeList INT_INTARR_INT =
+      StdTypeList.make(Type.INT, Type.INT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [long, long[], int]} */
-    public static final StdTypeList LONG_LONGARR_INT =
-        StdTypeList.make(Type.LONG, Type.LONG_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [long, long[], int]} */
+  public static final StdTypeList LONG_LONGARR_INT =
+      StdTypeList.make(Type.LONG, Type.LONG_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [float, float[], int]} */
-    public static final StdTypeList FLOAT_FLOATARR_INT =
-        StdTypeList.make(Type.FLOAT, Type.FLOAT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [float, float[], int]} */
+  public static final StdTypeList FLOAT_FLOATARR_INT =
+      StdTypeList.make(Type.FLOAT, Type.FLOAT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [double, double[], int]} */
-    public static final StdTypeList DOUBLE_DOUBLEARR_INT =
-        StdTypeList.make(Type.DOUBLE, Type.DOUBLE_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [double, double[], int]} */
+  public static final StdTypeList DOUBLE_DOUBLEARR_INT =
+      StdTypeList.make(Type.DOUBLE, Type.DOUBLE_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [Object, Object[], int]} */
-    public static final StdTypeList OBJECT_OBJECTARR_INT =
-        StdTypeList.make(Type.OBJECT, Type.OBJECT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [Object, Object[], int]} */
+  public static final StdTypeList OBJECT_OBJECTARR_INT =
+      StdTypeList.make(Type.OBJECT, Type.OBJECT_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [int, boolean[], int]} */
-    public static final StdTypeList INT_BOOLEANARR_INT =
-        StdTypeList.make(Type.INT, Type.BOOLEAN_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int, boolean[], int]} */
+  public static final StdTypeList INT_BOOLEANARR_INT =
+      StdTypeList.make(Type.INT, Type.BOOLEAN_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [int, byte[], int]} */
-    public static final StdTypeList INT_BYTEARR_INT =
-        StdTypeList.make(Type.INT, Type.BYTE_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int, byte[], int]} */
+  public static final StdTypeList INT_BYTEARR_INT =
+      StdTypeList.make(Type.INT, Type.BYTE_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [int, char[], int]} */
-    public static final StdTypeList INT_CHARARR_INT =
-        StdTypeList.make(Type.INT, Type.CHAR_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int, char[], int]} */
+  public static final StdTypeList INT_CHARARR_INT =
+      StdTypeList.make(Type.INT, Type.CHAR_ARRAY, Type.INT);
 
-    /** {@code non-null;} the list {@code [int, short[], int]} */
-    public static final StdTypeList INT_SHORTARR_INT =
-        StdTypeList.make(Type.INT, Type.SHORT_ARRAY, Type.INT);
+  /** {@code non-null;} the list {@code [int, short[], int]} */
+  public static final StdTypeList INT_SHORTARR_INT =
+      StdTypeList.make(Type.INT, Type.SHORT_ARRAY, Type.INT);
 
-    /**
-     * Makes a single-element instance.
-     *
-     * @param type {@code non-null;} the element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static StdTypeList make(Type type) {
-        StdTypeList result = new StdTypeList(1);
-        result.set(0, type);
-        return result;
+  /**
+   * Makes a single-element instance.
+   *
+   * @param type {@code non-null;} the element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static StdTypeList make(Type type) {
+    StdTypeList result = new StdTypeList(1);
+    result.set(0, type);
+    return result;
+  }
+
+  /**
+   * Makes a two-element instance.
+   *
+   * @param type0 {@code non-null;} the first element
+   * @param type1 {@code non-null;} the second element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static StdTypeList make(Type type0, Type type1) {
+    StdTypeList result = new StdTypeList(2);
+    result.set(0, type0);
+    result.set(1, type1);
+    return result;
+  }
+
+  /**
+   * Makes a three-element instance.
+   *
+   * @param type0 {@code non-null;} the first element
+   * @param type1 {@code non-null;} the second element
+   * @param type2 {@code non-null;} the third element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static StdTypeList make(Type type0, Type type1, Type type2) {
+    StdTypeList result = new StdTypeList(3);
+    result.set(0, type0);
+    result.set(1, type1);
+    result.set(2, type2);
+    return result;
+  }
+
+  /**
+   * Makes a four-element instance.
+   *
+   * @param type0 {@code non-null;} the first element
+   * @param type1 {@code non-null;} the second element
+   * @param type2 {@code non-null;} the third element
+   * @param type3 {@code non-null;} the fourth element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static StdTypeList make(Type type0, Type type1, Type type2, Type type3) {
+    StdTypeList result = new StdTypeList(4);
+    result.set(0, type0);
+    result.set(1, type1);
+    result.set(2, type2);
+    result.set(3, type3);
+    return result;
+  }
+
+  /**
+   * Returns the given list as a comma-separated list of human forms. This
+   * is a static method so as to work on arbitrary {@link TypeList}
+   * instances.
+   *
+   * @param list {@code non-null;} the list to convert
+   * @return {@code non-null;} the human form
+   */
+  public static String toHuman(TypeList list) {
+    int size = list.size();
+
+    if (size == 0) {
+      return "<empty>";
     }
 
-    /**
-     * Makes a two-element instance.
-     *
-     * @param type0 {@code non-null;} the first element
-     * @param type1 {@code non-null;} the second element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static StdTypeList make(Type type0, Type type1) {
-        StdTypeList result = new StdTypeList(2);
-        result.set(0, type0);
-        result.set(1, type1);
-        return result;
+    StringBuffer sb = new StringBuffer(100);
+
+    for (int i = 0; i < size; i++) {
+      if (i != 0) {
+        sb.append(", ");
+      }
+      sb.append(list.getType(i).toHuman());
     }
 
-    /**
-     * Makes a three-element instance.
-     *
-     * @param type0 {@code non-null;} the first element
-     * @param type1 {@code non-null;} the second element
-     * @param type2 {@code non-null;} the third element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static StdTypeList make(Type type0, Type type1, Type type2) {
-        StdTypeList result = new StdTypeList(3);
-        result.set(0, type0);
-        result.set(1, type1);
-        result.set(2, type2);
-        return result;
+    return sb.toString();
+  }
+
+  /**
+   * Returns a hashcode of the contents of the given list. This
+   * is a static method so as to work on arbitrary {@link TypeList}
+   * instances.
+   *
+   * @param list {@code non-null;} the list to inspect
+   * @return {@code non-null;} the hash code
+   */
+  public static int hashContents(TypeList list) {
+    int size = list.size();
+    int hash = 0;
+
+    for (int i = 0; i < size; i++) {
+      hash = (hash * 31) + list.getType(i).hashCode();
     }
 
-    /**
-     * Makes a four-element instance.
-     *
-     * @param type0 {@code non-null;} the first element
-     * @param type1 {@code non-null;} the second element
-     * @param type2 {@code non-null;} the third element
-     * @param type3 {@code non-null;} the fourth element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static StdTypeList make(Type type0, Type type1, Type type2,
-                                   Type type3) {
-        StdTypeList result = new StdTypeList(4);
-        result.set(0, type0);
-        result.set(1, type1);
-        result.set(2, type2);
-        result.set(3, type3);
-        return result;
+    return hash;
+  }
+
+  /**
+   * Compares the contents of the given two instances for equality. This
+   * is a static method so as to work on arbitrary {@link TypeList}
+   * instances.
+   *
+   * @param list1 {@code non-null;} one list to compare
+   * @param list2 {@code non-null;} another list to compare
+   * @return whether the two lists contain corresponding equal elements
+   */
+  public static boolean equalContents(TypeList list1, TypeList list2) {
+    int size = list1.size();
+
+    if (list2.size() != size) {
+      return false;
     }
 
-    /**
-     * Returns the given list as a comma-separated list of human forms. This
-     * is a static method so as to work on arbitrary {@link TypeList}
-     * instances.
-     *
-     * @param list {@code non-null;} the list to convert
-     * @return {@code non-null;} the human form
-     */
-    public static String toHuman(TypeList list) {
-        int size = list.size();
-
-        if (size == 0) {
-            return "<empty>";
-        }
-
-        StringBuffer sb = new StringBuffer(100);
-
-        for (int i = 0; i < size; i++) {
-            if (i != 0) {
-                sb.append(", ");
-            }
-            sb.append(list.getType(i).toHuman());
-        }
-
-        return sb.toString();
+    for (int i = 0; i < size; i++) {
+      if (!list1.getType(i).equals(list2.getType(i))) {
+        return false;
+      }
     }
 
-    /**
-     * Returns a hashcode of the contents of the given list. This
-     * is a static method so as to work on arbitrary {@link TypeList}
-     * instances.
-     *
-     * @param list {@code non-null;} the list to inspect
-     * @return {@code non-null;} the hash code
-     */
-    public static int hashContents(TypeList list) {
-        int size = list.size();
-        int hash = 0;
+    return true;
+  }
 
-        for (int i = 0; i < size; i++) {
-            hash = (hash * 31) + list.getType(i).hashCode();
-        }
+  /**
+   * Compares the contents of the given two instances for ordering. This
+   * is a static method so as to work on arbitrary {@link TypeList}
+   * instances.
+   *
+   * @param list1 {@code non-null;} one list to compare
+   * @param list2 {@code non-null;} another list to compare
+   * @return the order of the two lists
+   */
+  public static int compareContents(TypeList list1, TypeList list2) {
+    int size1 = list1.size();
+    int size2 = list2.size();
+    int size = Math.min(size1, size2);
 
-        return hash;
+    for (int i = 0; i < size; i++) {
+      int comparison = list1.getType(i).compareTo(list2.getType(i));
+      if (comparison != 0) {
+        return comparison;
+      }
     }
 
-    /**
-     * Compares the contents of the given two instances for equality. This
-     * is a static method so as to work on arbitrary {@link TypeList}
-     * instances.
-     *
-     * @param list1 {@code non-null;} one list to compare
-     * @param list2 {@code non-null;} another list to compare
-     * @return whether the two lists contain corresponding equal elements
-     */
-    public static boolean equalContents(TypeList list1, TypeList list2) {
-        int size = list1.size();
+    if (size1 == size2) {
+      return 0;
+    } else if (size1 < size2) {
+      return -1;
+    } else {
+      return 1;
+    }
+  }
 
-        if (list2.size() != size) {
-            return false;
-        }
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public StdTypeList(int size) {
+    super(size);
+  }
 
-        for (int i = 0; i < size; i++) {
-            if (! list1.getType(i).equals(list2.getType(i))) {
-                return false;
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public Type getType(int n) {
+    return get(n);
+  }
 
-        return true;
+  /** {@inheritDoc} */
+  @Override
+  public int getWordCount() {
+    int sz = size();
+    int result = 0;
+
+    for (int i = 0; i < sz; i++) {
+      result += get(i).getCategory();
     }
 
-    /**
-     * Compares the contents of the given two instances for ordering. This
-     * is a static method so as to work on arbitrary {@link TypeList}
-     * instances.
-     *
-     * @param list1 {@code non-null;} one list to compare
-     * @param list2 {@code non-null;} another list to compare
-     * @return the order of the two lists
-     */
-    public static int compareContents(TypeList list1, TypeList list2) {
-        int size1 = list1.size();
-        int size2 = list2.size();
-        int size = Math.min(size1, size2);
+    return result;
+  }
 
-        for (int i = 0; i < size; i++) {
-            int comparison = list1.getType(i).compareTo(list2.getType(i));
-            if (comparison != 0) {
-                return comparison;
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public TypeList withAddedType(Type type) {
+    int sz = size();
+    StdTypeList result = new StdTypeList(sz + 1);
 
-        if (size1 == size2) {
-            return 0;
-        } else if (size1 < size2) {
-            return -1;
-        } else {
-            return 1;
-        }
+    for (int i = 0; i < sz; i++) {
+      result.set0(i, get0(i));
     }
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public StdTypeList(int size) {
-        super(size);
+    result.set(sz, type);
+    result.setImmutable();
+    return result;
+  }
+
+  /**
+   * Gets the indicated element. It is an error to call this with the
+   * index for an element which was never set; if you do that, this
+   * will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return {@code non-null;} the indicated element
+   */
+  public Type get(int n) {
+    return (Type) get0(n);
+  }
+
+  /**
+   * Sets the type at the given index.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @param type {@code non-null;} the type to store
+   */
+  public void set(int n, Type type) {
+    set0(n, type);
+  }
+
+  /**
+   * Returns a new instance, which is the same as this instance,
+   * except that it has an additional type prepended to the
+   * original.
+   *
+   * @param type {@code non-null;} the new first element
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public StdTypeList withFirst(Type type) {
+    int sz = size();
+    StdTypeList result = new StdTypeList(sz + 1);
+
+    result.set0(0, type);
+    for (int i = 0; i < sz; i++) {
+      result.set0(i + 1, getOrNull0(i));
     }
 
-    /** {@inheritDoc} */
-    public Type getType(int n) {
-        return get(n);
-    }
-
-    /** {@inheritDoc} */
-    public int getWordCount() {
-        int sz = size();
-        int result = 0;
-
-        for (int i = 0; i < sz; i++) {
-            result += get(i).getCategory();
-        }
-
-        return result;
-    }
-
-    /** {@inheritDoc} */
-    public TypeList withAddedType(Type type) {
-        int sz = size();
-        StdTypeList result = new StdTypeList(sz + 1);
-
-        for (int i = 0; i < sz; i++) {
-            result.set0(i, get0(i));
-        }
-
-        result.set(sz, type);
-        result.setImmutable();
-        return result;
-    }
-
-    /**
-     * Gets the indicated element. It is an error to call this with the
-     * index for an element which was never set; if you do that, this
-     * will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return {@code non-null;} the indicated element
-     */
-    public Type get(int n) {
-        return (Type) get0(n);
-    }
-
-    /**
-     * Sets the type at the given index.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @param type {@code non-null;} the type to store
-     */
-    public void set(int n, Type type) {
-        set0(n, type);
-    }
-
-    /**
-     * Returns a new instance, which is the same as this instance,
-     * except that it has an additional type prepended to the
-     * original.
-     *
-     * @param type {@code non-null;} the new first element
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public StdTypeList withFirst(Type type) {
-        int sz = size();
-        StdTypeList result = new StdTypeList(sz + 1);
-
-        result.set0(0, type);
-        for (int i = 0; i < sz; i++) {
-            result.set0(i + 1, getOrNull0(i));
-        }
-
-        return result;
-    }
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/type/Type.java b/dx/src/com/android/jack/dx/rop/type/Type.java
index 2b8d0a8..c6ea1fd 100644
--- a/dx/src/com/android/jack/dx/rop/type/Type.java
+++ b/dx/src/com/android/jack/dx/rop/type/Type.java
@@ -27,836 +27,844 @@
  * other using {@code ==}.
  */
 public final class Type implements TypeBearer, Comparable<Type> {
-    /**
-     * {@code non-null;} intern table mapping string descriptors to
-     * instances
+  /**
+   * {@code non-null;} intern table mapping string descriptors to
+   * instances
+   */
+  private static final HashMap<String, Type> internTable = new HashMap<String, Type>(500);
+
+  /** basic type constant for {@code void} */
+  public static final int BT_VOID = 0;
+
+  /** basic type constant for {@code boolean} */
+  public static final int BT_BOOLEAN = 1;
+
+  /** basic type constant for {@code byte} */
+  public static final int BT_BYTE = 2;
+
+  /** basic type constant for {@code char} */
+  public static final int BT_CHAR = 3;
+
+  /** basic type constant for {@code double} */
+  public static final int BT_DOUBLE = 4;
+
+  /** basic type constant for {@code float} */
+  public static final int BT_FLOAT = 5;
+
+  /** basic type constant for {@code int} */
+  public static final int BT_INT = 6;
+
+  /** basic type constant for {@code long} */
+  public static final int BT_LONG = 7;
+
+  /** basic type constant for {@code short} */
+  public static final int BT_SHORT = 8;
+
+  /** basic type constant for {@code Object} */
+  public static final int BT_OBJECT = 9;
+
+  /** basic type constant for a return address */
+  public static final int BT_ADDR = 10;
+
+  /** count of basic type constants */
+  public static final int BT_COUNT = 11;
+
+  /** {@code non-null;} instance representing {@code boolean} */
+  public static final Type BOOLEAN = new Type("Z", BT_BOOLEAN);
+
+  /** {@code non-null;} instance representing {@code byte} */
+  public static final Type BYTE = new Type("B", BT_BYTE);
+
+  /** {@code non-null;} instance representing {@code char} */
+  public static final Type CHAR = new Type("C", BT_CHAR);
+
+  /** {@code non-null;} instance representing {@code double} */
+  public static final Type DOUBLE = new Type("D", BT_DOUBLE);
+
+  /** {@code non-null;} instance representing {@code float} */
+  public static final Type FLOAT = new Type("F", BT_FLOAT);
+
+  /** {@code non-null;} instance representing {@code int} */
+  public static final Type INT = new Type("I", BT_INT);
+
+  /** {@code non-null;} instance representing {@code long} */
+  public static final Type LONG = new Type("J", BT_LONG);
+
+  /** {@code non-null;} instance representing {@code short} */
+  public static final Type SHORT = new Type("S", BT_SHORT);
+
+  /** {@code non-null;} instance representing {@code void} */
+  public static final Type VOID = new Type("V", BT_VOID);
+
+  /** {@code non-null;} instance representing a known-{@code null} */
+  public static final Type KNOWN_NULL = new Type("<null>", BT_OBJECT);
+
+  /** {@code non-null;} instance representing a subroutine return address */
+  public static final Type RETURN_ADDRESS = new Type("<addr>", BT_ADDR);
+
+  static {
+    /*
+     * Put all the primitive types into the intern table. This needs
+     * to happen before the array types below get interned.
      */
-    private static final HashMap<String, Type> internTable =
-        new HashMap<String, Type>(500);
+    putIntern(BOOLEAN);
+    putIntern(BYTE);
+    putIntern(CHAR);
+    putIntern(DOUBLE);
+    putIntern(FLOAT);
+    putIntern(INT);
+    putIntern(LONG);
+    putIntern(SHORT);
+    /*
+     * Note: VOID isn't put in the intern table, since it's special and
+     * shouldn't be found by a normal call to intern().
+     */
+  }
 
-    /** basic type constant for {@code void} */
-    public static final int BT_VOID = 0;
+  /**
+   * {@code non-null;} instance representing
+   * {@code java.lang.annotation.Annotation}
+   */
+  public static final Type ANNOTATION = intern("Ljava/lang/annotation/Annotation;");
 
-    /** basic type constant for {@code boolean} */
-    public static final int BT_BOOLEAN = 1;
+  /** {@code non-null;} instance representing {@code java.lang.Class} */
+  public static final Type CLASS = intern("Ljava/lang/Class;");
 
-    /** basic type constant for {@code byte} */
-    public static final int BT_BYTE = 2;
+  /** {@code non-null;} instance representing {@code java.lang.Cloneable} */
+  public static final Type CLONEABLE = intern("Ljava/lang/Cloneable;");
 
-    /** basic type constant for {@code char} */
-    public static final int BT_CHAR = 3;
+  /** {@code non-null;} instance representing {@code java.lang.Object} */
+  public static final Type OBJECT = intern("Ljava/lang/Object;");
 
-    /** basic type constant for {@code double} */
-    public static final int BT_DOUBLE = 4;
+  /** {@code non-null;} instance representing {@code java.io.Serializable} */
+  public static final Type SERIALIZABLE = intern("Ljava/io/Serializable;");
 
-    /** basic type constant for {@code float} */
-    public static final int BT_FLOAT = 5;
+  /** {@code non-null;} instance representing {@code java.lang.String} */
+  public static final Type STRING = intern("Ljava/lang/String;");
 
-    /** basic type constant for {@code int} */
-    public static final int BT_INT = 6;
+  /** {@code non-null;} instance representing {@code java.lang.Throwable} */
+  public static final Type THROWABLE = intern("Ljava/lang/Throwable;");
 
-    /** basic type constant for {@code long} */
-    public static final int BT_LONG = 7;
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Boolean}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type BOOLEAN_CLASS = intern("Ljava/lang/Boolean;");
 
-    /** basic type constant for {@code short} */
-    public static final int BT_SHORT = 8;
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Byte}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type BYTE_CLASS = intern("Ljava/lang/Byte;");
 
-    /** basic type constant for {@code Object} */
-    public static final int BT_OBJECT = 9;
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Character}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type CHARACTER_CLASS = intern("Ljava/lang/Character;");
 
-    /** basic type constant for a return address */
-    public static final int BT_ADDR = 10;
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Double}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type DOUBLE_CLASS = intern("Ljava/lang/Double;");
 
-    /** count of basic type constants */
-    public static final int BT_COUNT = 11;
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Float}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type FLOAT_CLASS = intern("Ljava/lang/Float;");
 
-    /** {@code non-null;} instance representing {@code boolean} */
-    public static final Type BOOLEAN = new Type("Z", BT_BOOLEAN);
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Integer}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type INTEGER_CLASS = intern("Ljava/lang/Integer;");
 
-    /** {@code non-null;} instance representing {@code byte} */
-    public static final Type BYTE = new Type("B", BT_BYTE);
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Long}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type LONG_CLASS = intern("Ljava/lang/Long;");
 
-    /** {@code non-null;} instance representing {@code char} */
-    public static final Type CHAR = new Type("C", BT_CHAR);
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Short}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type SHORT_CLASS = intern("Ljava/lang/Short;");
 
-    /** {@code non-null;} instance representing {@code double} */
-    public static final Type DOUBLE = new Type("D", BT_DOUBLE);
+  /**
+   * {@code non-null;} instance representing {@code java.lang.Void}; the
+   * suffix on the name helps disambiguate this from the instance
+   * representing a primitive type
+   */
+  public static final Type VOID_CLASS = intern("Ljava/lang/Void;");
 
-    /** {@code non-null;} instance representing {@code float} */
-    public static final Type FLOAT = new Type("F", BT_FLOAT);
+  /** {@code non-null;} instance representing {@code boolean[]} */
+  public static final Type BOOLEAN_ARRAY = BOOLEAN.getArrayType();
 
-    /** {@code non-null;} instance representing {@code int} */
-    public static final Type INT = new Type("I", BT_INT);
+  /** {@code non-null;} instance representing {@code byte[]} */
+  public static final Type BYTE_ARRAY = BYTE.getArrayType();
 
-    /** {@code non-null;} instance representing {@code long} */
-    public static final Type LONG = new Type("J", BT_LONG);
+  /** {@code non-null;} instance representing {@code char[]} */
+  public static final Type CHAR_ARRAY = CHAR.getArrayType();
 
-    /** {@code non-null;} instance representing {@code short} */
-    public static final Type SHORT = new Type("S", BT_SHORT);
+  /** {@code non-null;} instance representing {@code double[]} */
+  public static final Type DOUBLE_ARRAY = DOUBLE.getArrayType();
 
-    /** {@code non-null;} instance representing {@code void} */
-    public static final Type VOID = new Type("V", BT_VOID);
+  /** {@code non-null;} instance representing {@code float[]} */
+  public static final Type FLOAT_ARRAY = FLOAT.getArrayType();
 
-    /** {@code non-null;} instance representing a known-{@code null} */
-    public static final Type KNOWN_NULL = new Type("<null>", BT_OBJECT);
+  /** {@code non-null;} instance representing {@code int[]} */
+  public static final Type INT_ARRAY = INT.getArrayType();
 
-    /** {@code non-null;} instance representing a subroutine return address */
-    public static final Type RETURN_ADDRESS = new Type("<addr>", BT_ADDR);
+  /** {@code non-null;} instance representing {@code long[]} */
+  public static final Type LONG_ARRAY = LONG.getArrayType();
 
-    static {
-        /*
-         * Put all the primitive types into the intern table. This needs
-         * to happen before the array types below get interned.
-         */
-        putIntern(BOOLEAN);
-        putIntern(BYTE);
-        putIntern(CHAR);
-        putIntern(DOUBLE);
-        putIntern(FLOAT);
-        putIntern(INT);
-        putIntern(LONG);
-        putIntern(SHORT);
-        /*
-         * Note: VOID isn't put in the intern table, since it's special and
-         * shouldn't be found by a normal call to intern().
-         */
+  /** {@code non-null;} instance representing {@code Object[]} */
+  public static final Type OBJECT_ARRAY = OBJECT.getArrayType();
+
+  /** {@code non-null;} instance representing {@code short[]} */
+  public static final Type SHORT_ARRAY = SHORT.getArrayType();
+
+  /** {@code non-null;} field descriptor for the type */
+  private final String descriptor;
+
+  /**
+   * basic type corresponding to this type; one of the
+   * {@code BT_*} constants
+   */
+  private final int basicType;
+
+  /**
+   * {@code >= -1;} for an uninitialized type, bytecode index that this
+   * instance was allocated at; {@code Integer.MAX_VALUE} if it
+   * was an incoming uninitialized instance; {@code -1} if this
+   * is an <i>inititialized</i> instance
+   */
+  private final int newAt;
+
+  /**
+   * {@code null-ok;} the internal-form class name corresponding to
+   * this type, if calculated; only valid if {@code this} is a
+   * reference type and additionally not a return address
+   */
+  private String className;
+
+  /**
+   * {@code null-ok;} the type corresponding to an array of this type, if
+   * calculated
+   */
+  private Type arrayType;
+
+  /**
+   * {@code null-ok;} the type corresponding to elements of this type, if
+   * calculated; only valid if {@code this} is an array type
+   */
+  private Type componentType;
+
+  /**
+   * {@code null-ok;} the type corresponding to the initialized version of
+   * this type, if this instance is in fact an uninitialized type
+   */
+  private Type initializedType;
+
+  /**
+   * Returns the unique instance corresponding to the type with the
+   * given descriptor. See vmspec-2 sec4.3.2 for details on the
+   * field descriptor syntax. This method does <i>not</i> allow
+   * {@code "V"} (that is, type {@code void}) as a valid
+   * descriptor.
+   *
+   * @param descriptor {@code non-null;} the descriptor
+   * @return {@code non-null;} the corresponding instance
+   * @throws IllegalArgumentException thrown if the descriptor has
+   * invalid syntax
+   */
+  public static Type intern(String descriptor) {
+    Type result;
+    synchronized (internTable) {
+      result = internTable.get(descriptor);
+    }
+    if (result != null) {
+      return result;
     }
 
-    /**
-     * {@code non-null;} instance representing
-     * {@code java.lang.annotation.Annotation}
+    char firstChar;
+    try {
+      firstChar = descriptor.charAt(0);
+    } catch (IndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("descriptor is empty");
+    } catch (NullPointerException ex) {
+      // Elucidate the exception.
+      throw new NullPointerException("descriptor == null");
+    }
+
+    if (firstChar == '[') {
+      /*
+       * Recursively strip away array markers to get at the underlying
+       * type, and build back on to form the result.
+       */
+      result = intern(descriptor.substring(1));
+      return result.getArrayType();
+    }
+
+    /*
+     * If the first character isn't '[' and it wasn't found in the
+     * intern cache, then it had better be the descriptor for a class.
      */
-    public static final Type ANNOTATION =
-        intern("Ljava/lang/annotation/Annotation;");
 
-    /** {@code non-null;} instance representing {@code java.lang.Class} */
-    public static final Type CLASS = intern("Ljava/lang/Class;");
+int length = descriptor.length();
+    if ((firstChar != 'L') || (descriptor.charAt(length - 1) != ';')) {
+      throw new IllegalArgumentException("bad descriptor: " + descriptor);
+    }
 
-    /** {@code non-null;} instance representing {@code java.lang.Cloneable} */
-    public static final Type CLONEABLE = intern("Ljava/lang/Cloneable;");
-
-    /** {@code non-null;} instance representing {@code java.lang.Object} */
-    public static final Type OBJECT = intern("Ljava/lang/Object;");
-
-    /** {@code non-null;} instance representing {@code java.io.Serializable} */
-    public static final Type SERIALIZABLE = intern("Ljava/io/Serializable;");
-
-    /** {@code non-null;} instance representing {@code java.lang.String} */
-    public static final Type STRING = intern("Ljava/lang/String;");
-
-    /** {@code non-null;} instance representing {@code java.lang.Throwable} */
-    public static final Type THROWABLE = intern("Ljava/lang/Throwable;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Boolean}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
+    /*
+     * Validate the characters of the class name itself. Note that
+     * vmspec-2 does not have a coherent definition for valid
+     * internal-form class names, and the definition here is fairly
+     * liberal: A name is considered valid as long as it doesn't
+     * contain any of '[' ';' '.' '(' ')', and it has no more than one
+     * '/' in a row, and no '/' at either end.
      */
-    public static final Type BOOLEAN_CLASS = intern("Ljava/lang/Boolean;");
 
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Byte}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type BYTE_CLASS = intern("Ljava/lang/Byte;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Character}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type CHARACTER_CLASS = intern("Ljava/lang/Character;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Double}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type DOUBLE_CLASS = intern("Ljava/lang/Double;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Float}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type FLOAT_CLASS = intern("Ljava/lang/Float;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Integer}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type INTEGER_CLASS = intern("Ljava/lang/Integer;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Long}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type LONG_CLASS = intern("Ljava/lang/Long;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Short}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type SHORT_CLASS = intern("Ljava/lang/Short;");
-
-    /**
-     * {@code non-null;} instance representing {@code java.lang.Void}; the
-     * suffix on the name helps disambiguate this from the instance
-     * representing a primitive type
-     */
-    public static final Type VOID_CLASS = intern("Ljava/lang/Void;");
-
-    /** {@code non-null;} instance representing {@code boolean[]} */
-    public static final Type BOOLEAN_ARRAY = BOOLEAN.getArrayType();
-
-    /** {@code non-null;} instance representing {@code byte[]} */
-    public static final Type BYTE_ARRAY = BYTE.getArrayType();
-
-    /** {@code non-null;} instance representing {@code char[]} */
-    public static final Type CHAR_ARRAY = CHAR.getArrayType();
-
-    /** {@code non-null;} instance representing {@code double[]} */
-    public static final Type DOUBLE_ARRAY = DOUBLE.getArrayType();
-
-    /** {@code non-null;} instance representing {@code float[]} */
-    public static final Type FLOAT_ARRAY = FLOAT.getArrayType();
-
-    /** {@code non-null;} instance representing {@code int[]} */
-    public static final Type INT_ARRAY = INT.getArrayType();
-
-    /** {@code non-null;} instance representing {@code long[]} */
-    public static final Type LONG_ARRAY = LONG.getArrayType();
-
-    /** {@code non-null;} instance representing {@code Object[]} */
-    public static final Type OBJECT_ARRAY = OBJECT.getArrayType();
-
-    /** {@code non-null;} instance representing {@code short[]} */
-    public static final Type SHORT_ARRAY = SHORT.getArrayType();
-
-    /** {@code non-null;} field descriptor for the type */
-    private final String descriptor;
-
-    /**
-     * basic type corresponding to this type; one of the
-     * {@code BT_*} constants
-     */
-    private final int basicType;
-
-    /**
-     * {@code >= -1;} for an uninitialized type, bytecode index that this
-     * instance was allocated at; {@code Integer.MAX_VALUE} if it
-     * was an incoming uninitialized instance; {@code -1} if this
-     * is an <i>inititialized</i> instance
-     */
-    private final int newAt;
-
-    /**
-     * {@code null-ok;} the internal-form class name corresponding to
-     * this type, if calculated; only valid if {@code this} is a
-     * reference type and additionally not a return address
-     */
-    private String className;
-
-    /**
-     * {@code null-ok;} the type corresponding to an array of this type, if
-     * calculated
-     */
-    private Type arrayType;
-
-    /**
-     * {@code null-ok;} the type corresponding to elements of this type, if
-     * calculated; only valid if {@code this} is an array type
-     */
-    private Type componentType;
-
-    /**
-     * {@code null-ok;} the type corresponding to the initialized version of
-     * this type, if this instance is in fact an uninitialized type
-     */
-    private Type initializedType;
-
-    /**
-     * Returns the unique instance corresponding to the type with the
-     * given descriptor. See vmspec-2 sec4.3.2 for details on the
-     * field descriptor syntax. This method does <i>not</i> allow
-     * {@code "V"} (that is, type {@code void}) as a valid
-     * descriptor.
-     *
-     * @param descriptor {@code non-null;} the descriptor
-     * @return {@code non-null;} the corresponding instance
-     * @throws IllegalArgumentException thrown if the descriptor has
-     * invalid syntax
-     */
-    public static Type intern(String descriptor) {
-        Type result;
-        synchronized (internTable) {
-            result = internTable.get(descriptor);
+int limit = (length - 1); // Skip the final ';'.
+    for (int i = 1; i < limit; i++) {
+      char c = descriptor.charAt(i);
+      switch (c) {
+        case '[':
+        case ';':
+        case '.':
+        case '(':
+        case ')': {
+          throw new IllegalArgumentException("bad descriptor: " + descriptor);
         }
-        if (result != null) {
-            return result;
-        }
-
-        char firstChar;
-        try {
-            firstChar = descriptor.charAt(0);
-        } catch (IndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("descriptor is empty");
-        } catch (NullPointerException ex) {
-            // Elucidate the exception.
-            throw new NullPointerException("descriptor == null");
-        }
-
-        if (firstChar == '[') {
-            /*
-             * Recursively strip away array markers to get at the underlying
-             * type, and build back on to form the result.
-             */
-            result = intern(descriptor.substring(1));
-            return result.getArrayType();
-        }
-
-        /*
-         * If the first character isn't '[' and it wasn't found in the
-         * intern cache, then it had better be the descriptor for a class.
-         */
-
-        int length = descriptor.length();
-        if ((firstChar != 'L') ||
-            (descriptor.charAt(length - 1) != ';')) {
+        case '/': {
+          if ((i == 1) || (i == (length - 1)) || (descriptor.charAt(i - 1) == '/')) {
             throw new IllegalArgumentException("bad descriptor: " + descriptor);
+          }
+          break;
         }
-
-        /*
-         * Validate the characters of the class name itself. Note that
-         * vmspec-2 does not have a coherent definition for valid
-         * internal-form class names, and the definition here is fairly
-         * liberal: A name is considered valid as long as it doesn't
-         * contain any of '[' ';' '.' '(' ')', and it has no more than one
-         * '/' in a row, and no '/' at either end.
-         */
-
-        int limit = (length - 1); // Skip the final ';'.
-        for (int i = 1; i < limit; i++) {
-            char c = descriptor.charAt(i);
-            switch (c) {
-                case '[':
-                case ';':
-                case '.':
-                case '(':
-                case ')': {
-                    throw new IllegalArgumentException("bad descriptor: " + descriptor);
-                }
-                case '/': {
-                    if ((i == 1) ||
-                        (i == (length - 1)) ||
-                        (descriptor.charAt(i - 1) == '/')) {
-                        throw new IllegalArgumentException("bad descriptor: " + descriptor);
-                    }
-                    break;
-                }
-            }
-        }
-
-        result = new Type(descriptor, BT_OBJECT);
-        return putIntern(result);
+      }
     }
 
-    /**
-     * Returns the unique instance corresponding to the type with the
-     * given descriptor, allowing {@code "V"} to return the type
-     * for {@code void}. Other than that one caveat, this method
-     * is identical to {@link #intern}.
-     *
-     * @param descriptor {@code non-null;} the descriptor
-     * @return {@code non-null;} the corresponding instance
-     * @throws IllegalArgumentException thrown if the descriptor has
-     * invalid syntax
-     */
-    public static Type internReturnType(String descriptor) {
-        try {
-            if (descriptor.equals("V")) {
-                // This is the one special case where void may be returned.
-                return VOID;
-            }
-        } catch (NullPointerException ex) {
-            // Elucidate the exception.
-            throw new NullPointerException("descriptor == null");
-        }
+    result = new Type(descriptor, BT_OBJECT);
+    return putIntern(result);
+  }
 
-        return intern(descriptor);
+  /**
+   * Returns the unique instance corresponding to the type with the
+   * given descriptor, allowing {@code "V"} to return the type
+   * for {@code void}. Other than that one caveat, this method
+   * is identical to {@link #intern}.
+   *
+   * @param descriptor {@code non-null;} the descriptor
+   * @return {@code non-null;} the corresponding instance
+   * @throws IllegalArgumentException thrown if the descriptor has
+   * invalid syntax
+   */
+  public static Type internReturnType(String descriptor) {
+    try {
+      if (descriptor.equals("V")) {
+        // This is the one special case where void may be returned.
+        return VOID;
+      }
+    } catch (NullPointerException ex) {
+      // Elucidate the exception.
+      throw new NullPointerException("descriptor == null");
     }
 
-    /**
-     * Returns the unique instance corresponding to the type of the
-     * class with the given name. Calling this method is equivalent to
-     * calling {@code intern(name)} if {@code name} begins
-     * with {@code "["} and calling {@code intern("L" + name + ";")}
-     * in all other cases.
-     *
-     * @param name {@code non-null;} the name of the class whose type
-     * is desired
-     * @return {@code non-null;} the corresponding type
-     * @throws IllegalArgumentException thrown if the name has
-     * invalid syntax
-     */
-    public static Type internClassName(String name) {
-        if (name == null) {
-            throw new NullPointerException("name == null");
-        }
+    return intern(descriptor);
+  }
 
-        if (name.startsWith("[")) {
-            return intern(name);
-        }
-
-        return intern('L' + name + ';');
+  /**
+   * Returns the unique instance corresponding to the type of the
+   * class with the given name. Calling this method is equivalent to
+   * calling {@code intern(name)} if {@code name} begins
+   * with {@code "["} and calling {@code intern("L" + name + ";")}
+   * in all other cases.
+   *
+   * @param name {@code non-null;} the name of the class whose type
+   * is desired
+   * @return {@code non-null;} the corresponding type
+   * @throws IllegalArgumentException thrown if the name has
+   * invalid syntax
+   */
+  public static Type internClassName(String name) {
+    if (name == null) {
+      throw new NullPointerException("name == null");
     }
 
-    /**
-     * Constructs an instance corresponding to an "uninitialized type."
-     * This is a private constructor; use one of the public static
-     * methods to get instances.
-     *
-     * @param descriptor {@code non-null;} the field descriptor for the type
-     * @param basicType basic type corresponding to this type; one of the
-     * {@code BT_*} constants
-     * @param newAt {@code >= -1;} allocation bytecode index
-     */
-    private Type(String descriptor, int basicType, int newAt) {
-        if (descriptor == null) {
-            throw new NullPointerException("descriptor == null");
-        }
-
-        if ((basicType < 0) || (basicType >= BT_COUNT)) {
-            throw new IllegalArgumentException("bad basicType");
-        }
-
-        if (newAt < -1) {
-            throw new IllegalArgumentException("newAt < -1");
-        }
-
-        this.descriptor = descriptor;
-        this.basicType = basicType;
-        this.newAt = newAt;
-        this.arrayType = null;
-        this.componentType = null;
-        this.initializedType = null;
+    if (name.startsWith("[")) {
+      return intern(name);
     }
 
-    /**
-     * Constructs an instance corresponding to an "initialized type."
-     * This is a private constructor; use one of the public static
-     * methods to get instances.
-     *
-     * @param descriptor {@code non-null;} the field descriptor for the type
-     * @param basicType basic type corresponding to this type; one of the
-     * {@code BT_*} constants
-     */
-    private Type(String descriptor, int basicType) {
-        this(descriptor, basicType, -1);
+    return intern('L' + name + ';');
+  }
+
+  /**
+   * Constructs an instance corresponding to an "uninitialized type."
+   * This is a private constructor; use one of the public static
+   * methods to get instances.
+   *
+   * @param descriptor {@code non-null;} the field descriptor for the type
+   * @param basicType basic type corresponding to this type; one of the
+   * {@code BT_*} constants
+   * @param newAt {@code >= -1;} allocation bytecode index
+   */
+  private Type(String descriptor, int basicType, int newAt) {
+    if (descriptor == null) {
+      throw new NullPointerException("descriptor == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (this == other) {
-            /*
-             * Since externally-visible types are interned, this check
-             * helps weed out some easy cases.
-             */
-            return true;
-        }
-
-        if (!(other instanceof Type)) {
-            return false;
-        }
-
-        return descriptor.equals(((Type) other).descriptor);
+    if ((basicType < 0) || (basicType >= BT_COUNT)) {
+      throw new IllegalArgumentException("bad basicType");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return descriptor.hashCode();
+    if (newAt < -1) {
+      throw new IllegalArgumentException("newAt < -1");
     }
 
-    /** {@inheritDoc} */
-    public int compareTo(Type other) {
-        return descriptor.compareTo(other.descriptor);
+    this.descriptor = descriptor;
+    this.basicType = basicType;
+    this.newAt = newAt;
+    this.arrayType = null;
+    this.componentType = null;
+    this.initializedType = null;
+  }
+
+  /**
+   * Constructs an instance corresponding to an "initialized type."
+   * This is a private constructor; use one of the public static
+   * methods to get instances.
+   *
+   * @param descriptor {@code non-null;} the field descriptor for the type
+   * @param basicType basic type corresponding to this type; one of the
+   * {@code BT_*} constants
+   */
+  private Type(String descriptor, int basicType) {
+    this(descriptor, basicType, -1);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (this == other) {
+      /*
+       * Since externally-visible types are interned, this check
+       * helps weed out some easy cases.
+       */
+      return true;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
+    if (!(other instanceof Type)) {
+      return false;
+    }
+
+    return descriptor.equals(((Type) other).descriptor);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return descriptor.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int compareTo(Type other) {
+    return descriptor.compareTo(other.descriptor);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return descriptor;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    switch (basicType) {
+      case BT_VOID:
+        return "void";
+      case BT_BOOLEAN:
+        return "boolean";
+      case BT_BYTE:
+        return "byte";
+      case BT_CHAR:
+        return "char";
+      case BT_DOUBLE:
+        return "double";
+      case BT_FLOAT:
+        return "float";
+      case BT_INT:
+        return "int";
+      case BT_LONG:
+        return "long";
+      case BT_SHORT:
+        return "short";
+      case BT_OBJECT:
+        break;
+      default:
         return descriptor;
     }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        switch (basicType) {
-            case BT_VOID:    return "void";
-            case BT_BOOLEAN: return "boolean";
-            case BT_BYTE:    return "byte";
-            case BT_CHAR:    return "char";
-            case BT_DOUBLE:  return "double";
-            case BT_FLOAT:   return "float";
-            case BT_INT:     return "int";
-            case BT_LONG:    return "long";
-            case BT_SHORT:   return "short";
-            case BT_OBJECT:  break;
-            default:         return descriptor;
-        }
-
-        if (isArray()) {
-            return getComponentType().toHuman() + "[]";
-        }
-
-        // Remove the "L...;" around the type and convert "/" to ".".
-        return getClassName().replace("/", ".");
+    if (isArray()) {
+      return getComponentType().toHuman() + "[]";
     }
 
-    /** {@inheritDoc} */
-    public Type getType() {
-        return this;
+    // Remove the "L...;" around the type and convert "/" to ".".
+    return getClassName().replace("/", ".");
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Type getType() {
+    return this;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Type getFrameType() {
+    switch (basicType) {
+      case BT_BOOLEAN:
+      case BT_BYTE:
+      case BT_CHAR:
+      case BT_INT:
+      case BT_SHORT: {
+        return INT;
+      }
     }
 
-    /** {@inheritDoc} */
-    public Type getFrameType() {
-        switch (basicType) {
-            case BT_BOOLEAN:
-            case BT_BYTE:
-            case BT_CHAR:
-            case BT_INT:
-            case BT_SHORT: {
-                return INT;
-            }
-        }
+    return this;
+  }
 
-        return this;
+  /** {@inheritDoc} */
+  @Override
+  public int getBasicType() {
+    return basicType;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getBasicFrameType() {
+    switch (basicType) {
+      case BT_BOOLEAN:
+      case BT_BYTE:
+      case BT_CHAR:
+      case BT_INT:
+      case BT_SHORT: {
+        return BT_INT;
+      }
     }
 
-    /** {@inheritDoc} */
-    public int getBasicType() {
-        return basicType;
+    return basicType;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isConstant() {
+    return false;
+  }
+
+  /**
+   * Gets the descriptor.
+   *
+   * @return {@code non-null;} the descriptor
+   */
+  public String getDescriptor() {
+    return descriptor;
+  }
+
+  /**
+   * Gets the name of the class this type corresponds to, in internal
+   * form. This method is only valid if this instance is for a
+   * normal reference type (that is, a reference type and
+   * additionally not a return address).
+   *
+   * @return {@code non-null;} the internal-form class name
+   */
+  public String getClassName() {
+    if (className == null) {
+      if (!isReference()) {
+        throw new IllegalArgumentException("not an object type: " + descriptor);
+      }
+
+      if (descriptor.charAt(0) == '[') {
+        className = descriptor;
+      } else {
+        className = descriptor.substring(1, descriptor.length() - 1);
+      }
     }
 
-    /** {@inheritDoc} */
-    public int getBasicFrameType() {
-        switch (basicType) {
-            case BT_BOOLEAN:
-            case BT_BYTE:
-            case BT_CHAR:
-            case BT_INT:
-            case BT_SHORT: {
-                return BT_INT;
-            }
-        }
+    return className;
+  }
 
-        return basicType;
+  /**
+   * Gets the category. Most instances are category 1. {@code long}
+   * and {@code double} are the only category 2 types.
+   *
+   * @see #isCategory1
+   * @see #isCategory2
+   * @return the category
+   */
+  public int getCategory() {
+    switch (basicType) {
+      case BT_LONG:
+      case BT_DOUBLE: {
+        return 2;
+      }
     }
 
-    /** {@inheritDoc} */
-    public boolean isConstant() {
+    return 1;
+  }
+
+  /**
+   * Returns whether or not this is a category 1 type.
+   *
+   * @see #getCategory
+   * @see #isCategory2
+   * @return whether or not this is a category 1 type
+   */
+  public boolean isCategory1() {
+    switch (basicType) {
+      case BT_LONG:
+      case BT_DOUBLE: {
         return false;
+      }
     }
 
-    /**
-     * Gets the descriptor.
-     *
-     * @return {@code non-null;} the descriptor
-     */
-    public String getDescriptor() {
-        return descriptor;
-    }
+    return true;
+  }
 
-    /**
-     * Gets the name of the class this type corresponds to, in internal
-     * form. This method is only valid if this instance is for a
-     * normal reference type (that is, a reference type and
-     * additionally not a return address).
-     *
-     * @return {@code non-null;} the internal-form class name
-     */
-    public String getClassName() {
-        if (className == null) {
-            if (!isReference()) {
-                throw new IllegalArgumentException("not an object type: " +
-                                                   descriptor);
-            }
-
-            if (descriptor.charAt(0) == '[') {
-                className = descriptor;
-            } else {
-                className = descriptor.substring(1, descriptor.length() - 1);
-            }
-        }
-
-        return className;
-    }
-
-    /**
-     * Gets the category. Most instances are category 1. {@code long}
-     * and {@code double} are the only category 2 types.
-     *
-     * @see #isCategory1
-     * @see #isCategory2
-     * @return the category
-     */
-    public int getCategory() {
-        switch (basicType) {
-            case BT_LONG:
-            case BT_DOUBLE: {
-                return 2;
-            }
-        }
-
-        return 1;
-    }
-
-    /**
-     * Returns whether or not this is a category 1 type.
-     *
-     * @see #getCategory
-     * @see #isCategory2
-     * @return whether or not this is a category 1 type
-     */
-    public boolean isCategory1() {
-        switch (basicType) {
-            case BT_LONG:
-            case BT_DOUBLE: {
-                return false;
-            }
-        }
-
+  /**
+   * Returns whether or not this is a category 2 type.
+   *
+   * @see #getCategory
+   * @see #isCategory1
+   * @return whether or not this is a category 2 type
+   */
+  public boolean isCategory2() {
+    switch (basicType) {
+      case BT_LONG:
+      case BT_DOUBLE: {
         return true;
+      }
     }
 
-    /**
-     * Returns whether or not this is a category 2 type.
-     *
-     * @see #getCategory
-     * @see #isCategory1
-     * @return whether or not this is a category 2 type
+    return false;
+  }
+
+  /**
+   * Gets whether this type is "intlike." An intlike type is one which, when
+   * placed on a stack or in a local, is automatically converted to an
+   * {@code int}.
+   *
+   * @return whether this type is "intlike"
+   */
+  public boolean isIntlike() {
+    switch (basicType) {
+      case BT_BOOLEAN:
+      case BT_BYTE:
+      case BT_CHAR:
+      case BT_INT:
+      case BT_SHORT: {
+        return true;
+      }
+    }
+
+    return false;
+  }
+
+  /**
+   * Gets whether this type is a primitive type. All types are either
+   * primitive or reference types.
+   *
+   * @return whether this type is primitive
+   */
+  public boolean isPrimitive() {
+    switch (basicType) {
+      case BT_BOOLEAN:
+      case BT_BYTE:
+      case BT_CHAR:
+      case BT_DOUBLE:
+      case BT_FLOAT:
+      case BT_INT:
+      case BT_LONG:
+      case BT_SHORT:
+      case BT_VOID: {
+        return true;
+      }
+    }
+
+    return false;
+  }
+
+  /**
+   * Gets whether this type is a normal reference type. A normal
+   * reference type is a reference type that is not a return
+   * address. This method is just convenient shorthand for
+   * {@code getBasicType() == Type.BT_OBJECT}.
+   *
+   * @return whether this type is a normal reference type
+   */
+  public boolean isReference() {
+    return (basicType == BT_OBJECT);
+  }
+
+  /**
+   * Gets whether this type is an array type. If this method returns
+   * {@code true}, then it is safe to use {@link #getComponentType}
+   * to determine the component type.
+   *
+   * @return whether this type is an array type
+   */
+  public boolean isArray() {
+    return (descriptor.charAt(0) == '[');
+  }
+
+  /**
+   * Gets whether this type is an array type or is a known-null, and
+   * hence is compatible with array types.
+   *
+   * @return whether this type is an array type
+   */
+  public boolean isArrayOrKnownNull() {
+    return isArray() || equals(KNOWN_NULL);
+  }
+
+  /**
+   * Gets whether this type represents an uninitialized instance. An
+   * uninitialized instance is what one gets back from the {@code new}
+   * opcode, and remains uninitialized until a valid constructor is
+   * invoked on it.
+   *
+   * @return whether this type is "uninitialized"
+   */
+  public boolean isUninitialized() {
+    return (newAt >= 0);
+  }
+
+  /**
+   * Gets the bytecode index at which this uninitialized type was
+   * allocated.  This returns {@code Integer.MAX_VALUE} if this
+   * type is an uninitialized incoming parameter (i.e., the
+   * {@code this} of an {@code <init>} method) or
+   * {@code -1} if this type is in fact <i>initialized</i>.
+   *
+   * @return {@code >= -1;} the allocation bytecode index
+   */
+  public int getNewAt() {
+    return newAt;
+  }
+
+  /**
+   * Gets the initialized type corresponding to this instance, but only
+   * if this instance is in fact an uninitialized object type.
+   *
+   * @return {@code non-null;} the initialized type
+   */
+  public Type getInitializedType() {
+    if (initializedType == null) {
+      throw new IllegalArgumentException("initialized type: " + descriptor);
+    }
+
+    return initializedType;
+  }
+
+  /**
+   * Gets the type corresponding to an array of this type.
+   *
+   * @return {@code non-null;} the array type
+   */
+  public Type getArrayType() {
+    if (arrayType == null) {
+      arrayType = putIntern(new Type('[' + descriptor, BT_OBJECT));
+    }
+
+    return arrayType;
+  }
+
+  /**
+   * Gets the component type of this type. This method is only valid on
+   * array types.
+   *
+   * @return {@code non-null;} the component type
+   */
+  public Type getComponentType() {
+    if (componentType == null) {
+      if (descriptor.charAt(0) != '[') {
+        throw new IllegalArgumentException("not an array type: " + descriptor);
+      }
+      componentType = intern(descriptor.substring(1));
+    }
+
+    return componentType;
+  }
+
+  /**
+   * Returns a new interned instance which is identical to this one, except
+   * it is indicated as uninitialized and allocated at the given bytecode
+   * index. This instance must be an initialized object type.
+   *
+   * @param newAt {@code >= 0;} the allocation bytecode index
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public Type asUninitialized(int newAt) {
+    if (newAt < 0) {
+      throw new IllegalArgumentException("newAt < 0");
+    }
+
+    if (!isReference()) {
+      throw new IllegalArgumentException("not a reference type: " + descriptor);
+    }
+
+    if (isUninitialized()) {
+      /*
+       * Dealing with uninitialized types as a starting point is
+       * a pain, and it's not clear that it'd ever be used, so
+       * just disallow it.
+       */
+      throw new IllegalArgumentException("already uninitialized: " + descriptor);
+    }
+
+    /*
+     * Create a new descriptor that is unique and shouldn't conflict
+     * with "normal" type descriptors
      */
-    public boolean isCategory2() {
-        switch (basicType) {
-            case BT_LONG:
-            case BT_DOUBLE: {
-                return true;
-            }
-        }
+    String newDesc = 'N' + Hex.u2(newAt) + descriptor;
+    Type result = new Type(newDesc, BT_OBJECT, newAt);
+    result.initializedType = this;
+    return putIntern(result);
+  }
 
-        return false;
+  /**
+   * Puts the given instance in the intern table if it's not already
+   * there. If a conflicting value is already in the table, then leave it.
+   * Return the interned value.
+   *
+   * @param type {@code non-null;} instance to make interned
+   * @return {@code non-null;} the actual interned object
+   */
+  private static Type putIntern(Type type) {
+    synchronized (internTable) {
+      String descriptor = type.getDescriptor();
+      Type already = internTable.get(descriptor);
+      if (already != null) {
+        return already;
+      }
+      internTable.put(descriptor, type);
+      return type;
     }
-
-    /**
-     * Gets whether this type is "intlike." An intlike type is one which, when
-     * placed on a stack or in a local, is automatically converted to an
-     * {@code int}.
-     *
-     * @return whether this type is "intlike"
-     */
-    public boolean isIntlike() {
-        switch (basicType) {
-            case BT_BOOLEAN:
-            case BT_BYTE:
-            case BT_CHAR:
-            case BT_INT:
-            case BT_SHORT: {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    /**
-     * Gets whether this type is a primitive type. All types are either
-     * primitive or reference types.
-     *
-     * @return whether this type is primitive
-     */
-    public boolean isPrimitive() {
-        switch (basicType) {
-            case BT_BOOLEAN:
-            case BT_BYTE:
-            case BT_CHAR:
-            case BT_DOUBLE:
-            case BT_FLOAT:
-            case BT_INT:
-            case BT_LONG:
-            case BT_SHORT:
-            case BT_VOID: {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    /**
-     * Gets whether this type is a normal reference type. A normal
-     * reference type is a reference type that is not a return
-     * address. This method is just convenient shorthand for
-     * {@code getBasicType() == Type.BT_OBJECT}.
-     *
-     * @return whether this type is a normal reference type
-     */
-    public boolean isReference() {
-        return (basicType == BT_OBJECT);
-    }
-
-    /**
-     * Gets whether this type is an array type. If this method returns
-     * {@code true}, then it is safe to use {@link #getComponentType}
-     * to determine the component type.
-     *
-     * @return whether this type is an array type
-     */
-    public boolean isArray() {
-        return (descriptor.charAt(0) == '[');
-    }
-
-    /**
-     * Gets whether this type is an array type or is a known-null, and
-     * hence is compatible with array types.
-     *
-     * @return whether this type is an array type
-     */
-    public boolean isArrayOrKnownNull() {
-        return isArray() || equals(KNOWN_NULL);
-    }
-
-    /**
-     * Gets whether this type represents an uninitialized instance. An
-     * uninitialized instance is what one gets back from the {@code new}
-     * opcode, and remains uninitialized until a valid constructor is
-     * invoked on it.
-     *
-     * @return whether this type is "uninitialized"
-     */
-    public boolean isUninitialized() {
-        return (newAt >= 0);
-    }
-
-    /**
-     * Gets the bytecode index at which this uninitialized type was
-     * allocated.  This returns {@code Integer.MAX_VALUE} if this
-     * type is an uninitialized incoming parameter (i.e., the
-     * {@code this} of an {@code <init>} method) or
-     * {@code -1} if this type is in fact <i>initialized</i>.
-     *
-     * @return {@code >= -1;} the allocation bytecode index
-     */
-    public int getNewAt() {
-        return newAt;
-    }
-
-    /**
-     * Gets the initialized type corresponding to this instance, but only
-     * if this instance is in fact an uninitialized object type.
-     *
-     * @return {@code non-null;} the initialized type
-     */
-    public Type getInitializedType() {
-        if (initializedType == null) {
-            throw new IllegalArgumentException("initialized type: " +
-                                               descriptor);
-        }
-
-        return initializedType;
-    }
-
-    /**
-     * Gets the type corresponding to an array of this type.
-     *
-     * @return {@code non-null;} the array type
-     */
-    public Type getArrayType() {
-        if (arrayType == null) {
-            arrayType = putIntern(new Type('[' + descriptor, BT_OBJECT));
-        }
-
-        return arrayType;
-    }
-
-    /**
-     * Gets the component type of this type. This method is only valid on
-     * array types.
-     *
-     * @return {@code non-null;} the component type
-     */
-    public Type getComponentType() {
-        if (componentType == null) {
-            if (descriptor.charAt(0) != '[') {
-                throw new IllegalArgumentException("not an array type: " +
-                                                   descriptor);
-            }
-            componentType = intern(descriptor.substring(1));
-        }
-
-        return componentType;
-    }
-
-    /**
-     * Returns a new interned instance which is identical to this one, except
-     * it is indicated as uninitialized and allocated at the given bytecode
-     * index. This instance must be an initialized object type.
-     *
-     * @param newAt {@code >= 0;} the allocation bytecode index
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public Type asUninitialized(int newAt) {
-        if (newAt < 0) {
-            throw new IllegalArgumentException("newAt < 0");
-        }
-
-        if (!isReference()) {
-            throw new IllegalArgumentException("not a reference type: " +
-                                               descriptor);
-        }
-
-        if (isUninitialized()) {
-            /*
-             * Dealing with uninitialized types as a starting point is
-             * a pain, and it's not clear that it'd ever be used, so
-             * just disallow it.
-             */
-            throw new IllegalArgumentException("already uninitialized: " +
-                                               descriptor);
-        }
-
-        /*
-         * Create a new descriptor that is unique and shouldn't conflict
-         * with "normal" type descriptors
-         */
-        String newDesc = 'N' + Hex.u2(newAt) + descriptor;
-        Type result = new Type(newDesc, BT_OBJECT, newAt);
-        result.initializedType = this;
-        return putIntern(result);
-    }
-
-    /**
-     * Puts the given instance in the intern table if it's not already
-     * there. If a conflicting value is already in the table, then leave it.
-     * Return the interned value.
-     *
-     * @param type {@code non-null;} instance to make interned
-     * @return {@code non-null;} the actual interned object
-     */
-    private static Type putIntern(Type type) {
-        synchronized (internTable) {
-            String descriptor = type.getDescriptor();
-            Type already = internTable.get(descriptor);
-            if (already != null) {
-                return already;
-            }
-            internTable.put(descriptor, type);
-            return type;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/rop/type/TypeBearer.java b/dx/src/com/android/jack/dx/rop/type/TypeBearer.java
index 012814e..448e0e9 100644
--- a/dx/src/com/android/jack/dx/rop/type/TypeBearer.java
+++ b/dx/src/com/android/jack/dx/rop/type/TypeBearer.java
@@ -21,54 +21,53 @@
 /**
  * Object which has an associated type, possibly itself.
  */
-public interface TypeBearer
-        extends ToHuman {
-    /**
-     * Gets the type associated with this instance.
-     *
-     * @return {@code non-null;} the type
-     */
-    public Type getType();
+public interface TypeBearer extends ToHuman {
+  /**
+   * Gets the type associated with this instance.
+   *
+   * @return {@code non-null;} the type
+   */
+  public Type getType();
 
-    /**
-     * Gets the frame type corresponding to this type. This method returns
-     * {@code this}, except if {@link Type#isIntlike} on the underlying
-     * type returns {@code true} but the underlying type is not in
-     * fact {@link Type#INT}, in which case this method returns an instance
-     * whose underlying type <i>is</i> {@code INT}.
-     *
-     * @return {@code non-null;} the frame type for this instance
-     */
-    public TypeBearer getFrameType();
+  /**
+   * Gets the frame type corresponding to this type. This method returns
+   * {@code this}, except if {@link Type#isIntlike} on the underlying
+   * type returns {@code true} but the underlying type is not in
+   * fact {@link Type#INT}, in which case this method returns an instance
+   * whose underlying type <i>is</i> {@code INT}.
+   *
+   * @return {@code non-null;} the frame type for this instance
+   */
+  public TypeBearer getFrameType();
 
-    /**
-     * Gets the basic type corresponding to this instance.
-     *
-     * @return the basic type; one of the {@code BT_*} constants
-     * defined by {@link Type}
-     */
-    public int getBasicType();
+  /**
+   * Gets the basic type corresponding to this instance.
+   *
+   * @return the basic type; one of the {@code BT_*} constants
+   * defined by {@link Type}
+   */
+  public int getBasicType();
 
-    /**
-     * Gets the basic type corresponding to this instance's frame type. This
-     * is equivalent to {@code getFrameType().getBasicType()}, and
-     * is the same as calling {@code getFrameType()} unless this
-     * instance is an int-like type, in which case this method returns
-     * {@code BT_INT}.
-     *
-     * @see #getBasicType
-     * @see #getFrameType
-     *
-     * @return the basic frame type; one of the {@code BT_*} constants
-     * defined by {@link Type}
-     */
-    public int getBasicFrameType();
+  /**
+   * Gets the basic type corresponding to this instance's frame type. This
+   * is equivalent to {@code getFrameType().getBasicType()}, and
+   * is the same as calling {@code getFrameType()} unless this
+   * instance is an int-like type, in which case this method returns
+   * {@code BT_INT}.
+   *
+   * @see #getBasicType
+   * @see #getFrameType
+   *
+   * @return the basic frame type; one of the {@code BT_*} constants
+   * defined by {@link Type}
+   */
+  public int getBasicFrameType();
 
-    /**
-     * Returns whether this instance represents a constant value.
-     *
-     * @return {@code true} if this instance represents a constant value
-     * and {@code false} if not
-     */
-    public boolean isConstant();
+  /**
+   * Returns whether this instance represents a constant value.
+   *
+   * @return {@code true} if this instance represents a constant value
+   * and {@code false} if not
+   */
+  public boolean isConstant();
 }
diff --git a/dx/src/com/android/jack/dx/rop/type/TypeList.java b/dx/src/com/android/jack/dx/rop/type/TypeList.java
index 825d881..48cc50a 100644
--- a/dx/src/com/android/jack/dx/rop/type/TypeList.java
+++ b/dx/src/com/android/jack/dx/rop/type/TypeList.java
@@ -20,50 +20,50 @@
  * List of {@link Type} instances (or of things that contain types).
  */
 public interface TypeList {
-    /**
-     * Returns whether this instance is mutable. Note that the
-     * {@code TypeList} interface itself doesn't provide any
-     * means of mutation, but that doesn't mean that there isn't an
-     * extra-interface way of mutating an instance.
-     *
-     * @return {@code true} if this instance is mutable or
-     * {@code false} if it is immutable
-     */
-    public boolean isMutable();
+  /**
+   * Returns whether this instance is mutable. Note that the
+   * {@code TypeList} interface itself doesn't provide any
+   * means of mutation, but that doesn't mean that there isn't an
+   * extra-interface way of mutating an instance.
+   *
+   * @return {@code true} if this instance is mutable or
+   * {@code false} if it is immutable
+   */
+  public boolean isMutable();
 
-    /**
-     * Gets the size of this list.
-     *
-     * @return {@code >= 0;} the size
-     */
-    public int size();
+  /**
+   * Gets the size of this list.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int size();
 
-    /**
-     * Gets the indicated element. It is an error to call this with the
-     * index for an element which was never set; if you do that, this
-     * will throw {@code NullPointerException}.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return {@code non-null;} the indicated element
-     */
-    public Type getType(int n);
+  /**
+   * Gets the indicated element. It is an error to call this with the
+   * index for an element which was never set; if you do that, this
+   * will throw {@code NullPointerException}.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return {@code non-null;} the indicated element
+   */
+  public Type getType(int n);
 
-    /**
-     * Gets the number of 32-bit words required to hold instances of
-     * all the elements of this list. This is a sum of the widths (categories)
-     * of all the elements.
-     *
-     * @return {@code >= 0;} the required number of words
-     */
-    public int getWordCount();
+  /**
+   * Gets the number of 32-bit words required to hold instances of
+   * all the elements of this list. This is a sum of the widths (categories)
+   * of all the elements.
+   *
+   * @return {@code >= 0;} the required number of words
+   */
+  public int getWordCount();
 
-    /**
-     * Returns a new instance which is identical to this one, except that
-     * the given item is appended to the end and it is guaranteed to be
-     * immutable.
-     *
-     * @param type {@code non-null;} item to append
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public TypeList withAddedType(Type type);
+  /**
+   * Returns a new instance which is identical to this one, except that
+   * the given item is appended to the end and it is guaranteed to be
+   * immutable.
+   *
+   * @param type {@code non-null;} item to append
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public TypeList withAddedType(Type type);
 }
diff --git a/dx/src/com/android/jack/dx/ssa/BasicRegisterMapper.java b/dx/src/com/android/jack/dx/ssa/BasicRegisterMapper.java
index f9bdb2f..7093355 100644
--- a/dx/src/com/android/jack/dx/ssa/BasicRegisterMapper.java
+++ b/dx/src/com/android/jack/dx/ssa/BasicRegisterMapper.java
@@ -17,7 +17,6 @@
 package com.android.jack.dx.ssa;
 
 import com.android.jack.dx.rop.code.RegisterSpec;
-import com.android.jack.dx.rop.code.RegisterSpecList;
 import com.android.jack.dx.util.IntList;
 
 /**
@@ -25,105 +24,105 @@
  * each mapping built up individually and added via addMapping()
  */
 public class BasicRegisterMapper extends RegisterMapper {
-    /** indexed by old register, containing new name */
-    private IntList oldToNew;
+  /** indexed by old register, containing new name */
+  private IntList oldToNew;
 
-    /** running count of used registers in new namespace */
-    private int runningCountNewRegisters;
+  /** running count of used registers in new namespace */
+  private int runningCountNewRegisters;
 
-    /**
-     * Creates a new OneToOneRegisterMapper.
-     *
-     * @param countOldRegisters the number of registers in the old name space
-     */
-    public BasicRegisterMapper(int countOldRegisters) {
-        oldToNew = new IntList(countOldRegisters);
+  /**
+   * Creates a new OneToOneRegisterMapper.
+   *
+   * @param countOldRegisters the number of registers in the old name space
+   */
+  public BasicRegisterMapper(int countOldRegisters) {
+    oldToNew = new IntList(countOldRegisters);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getNewRegisterCount() {
+    return runningCountNewRegisters;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public RegisterSpec map(RegisterSpec registerSpec) {
+    if (registerSpec == null) {
+      return null;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int getNewRegisterCount() {
-        return runningCountNewRegisters;
+    int newReg;
+    try {
+      newReg = oldToNew.get(registerSpec.getReg());
+    } catch (IndexOutOfBoundsException ex) {
+      newReg = -1;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public RegisterSpec map(RegisterSpec registerSpec) {
-        if (registerSpec == null) {
-            return null;
-        }
-
-        int newReg;
-        try {
-            newReg = oldToNew.get(registerSpec.getReg());
-        } catch (IndexOutOfBoundsException ex) {
-            newReg = -1;
-        }
-
-        if (newReg < 0) {
-            throw new RuntimeException("no mapping specified for register");
-        }
-
-        return registerSpec.withReg(newReg);
+    if (newReg < 0) {
+      throw new RuntimeException("no mapping specified for register");
     }
 
-    /**
-     * Returns the new-namespace mapping for the specified
-     * old-namespace register, or -1 if one exists.
-     *
-     * @param oldReg {@code >= 0;} old-namespace register
-     * @return new-namespace register or -1 if none
-     */
-    public int oldToNew(int oldReg) {
-        if (oldReg >= oldToNew.size()) {
-            return -1;
-        }
+    return registerSpec.withReg(newReg);
+  }
 
-        return oldToNew.get(oldReg);
+  /**
+   * Returns the new-namespace mapping for the specified
+   * old-namespace register, or -1 if one exists.
+   *
+   * @param oldReg {@code >= 0;} old-namespace register
+   * @return new-namespace register or -1 if none
+   */
+  public int oldToNew(int oldReg) {
+    if (oldReg >= oldToNew.size()) {
+      return -1;
     }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        StringBuilder sb = new StringBuilder();
+    return oldToNew.get(oldReg);
+  }
 
-        sb.append("Old\tNew\n");
-        int sz = oldToNew.size();
+  /** {@inheritDoc} */
+  public String toHuman() {
+    StringBuilder sb = new StringBuilder();
 
-        for (int i = 0; i < sz; i++) {
-            sb.append(i);
-            sb.append('\t');
-            sb.append(oldToNew.get(i));
-            sb.append('\n');
-        }
+    sb.append("Old\tNew\n");
+    int sz = oldToNew.size();
 
-        sb.append("new reg count:");
-
-        sb.append(runningCountNewRegisters);
-        sb.append('\n');
-
-        return sb.toString();
+    for (int i = 0; i < sz; i++) {
+      sb.append(i);
+      sb.append('\t');
+      sb.append(oldToNew.get(i));
+      sb.append('\n');
     }
 
-    /**
-     * Adds a mapping to the mapper. If oldReg has already been mapped,
-     * overwrites previous mapping with new mapping.
-     *
-     * @param oldReg {@code >= 0;} old register
-     * @param newReg {@code >= 0;} new register
-     * @param category {@code 1..2;} width of reg
-     */
-    public void addMapping(int oldReg, int newReg, int category) {
-        if (oldReg >= oldToNew.size()) {
-            // expand the array as necessary
-            for (int i = oldReg - oldToNew.size(); i >= 0; i--) {
-                oldToNew.add(-1);
-            }
-        }
+    sb.append("new reg count:");
 
-        oldToNew.set(oldReg, newReg);
+    sb.append(runningCountNewRegisters);
+    sb.append('\n');
 
-        if (runningCountNewRegisters < (newReg + category)) {
-            runningCountNewRegisters = newReg + category;
-        }
+    return sb.toString();
+  }
+
+  /**
+   * Adds a mapping to the mapper. If oldReg has already been mapped,
+   * overwrites previous mapping with new mapping.
+   *
+   * @param oldReg {@code >= 0;} old register
+   * @param newReg {@code >= 0;} new register
+   * @param category {@code 1..2;} width of reg
+   */
+  public void addMapping(int oldReg, int newReg, int category) {
+    if (oldReg >= oldToNew.size()) {
+      // expand the array as necessary
+      for (int i = oldReg - oldToNew.size(); i >= 0; i--) {
+        oldToNew.add(-1);
+      }
     }
+
+    oldToNew.set(oldReg, newReg);
+
+    if (runningCountNewRegisters < (newReg + category)) {
+      runningCountNewRegisters = newReg + category;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/ConstCollector.java b/dx/src/com/android/jack/dx/ssa/ConstCollector.java
index ee12cb4..aa73c2a 100644
--- a/dx/src/com/android/jack/dx/ssa/ConstCollector.java
+++ b/dx/src/com/android/jack/dx/ssa/ConstCollector.java
@@ -45,356 +45,340 @@
  * insn size by about 3%.
  */
 public class ConstCollector {
-    /** Maximum constants to collect per method. Puts cap on reg use */
-    private static final int MAX_COLLECTED_CONSTANTS = 5;
+  /** Maximum constants to collect per method. Puts cap on reg use */
+  private static final int MAX_COLLECTED_CONSTANTS = 5;
 
-    /**
-     * Also collect string consts, although they can throw exceptions.
-     * This is off now because it just doesn't seem to gain a whole lot.
-     * TODO if you turn this on, you must change SsaInsn.hasSideEffect()
-     * to return false for const-string insns whose exceptions are not
-     * caught in the current method.
-     */
-    private static boolean COLLECT_STRINGS = false;
+  /**
+   * Also collect string consts, although they can throw exceptions.
+   * This is off now because it just doesn't seem to gain a whole lot.
+   * TODO(dx team) if you turn this on, you must change SsaInsn.hasSideEffect()
+   * to return false for const-string insns whose exceptions are not
+   * caught in the current method.
+   */
+  private static boolean collectStrings = false;
 
-    /**
-     * If true, allow one local var to be involved with a collected const.
-     * Turned off because it mostly just inserts more moves.
-     */
-    private static boolean COLLECT_ONE_LOCAL = false;
+  /**
+   * If true, allow one local var to be involved with a collected const.
+   * Turned off because it mostly just inserts more moves.
+   */
+  private static final boolean COLLECT_ONE_LOCAL = false;
 
-    /** method we're processing */
-    private final SsaMethod ssaMeth;
+  /** method we're processing */
+  private final SsaMethod ssaMeth;
 
-    /**
-     * Processes a method.
-     *
-     * @param ssaMethod {@code non-null;} method to process
-     */
-    public static void process(SsaMethod ssaMethod) {
-        ConstCollector cc = new ConstCollector(ssaMethod);
-        cc.run();
+  /**
+   * Processes a method.
+   *
+   * @param ssaMethod {@code non-null;} method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    ConstCollector cc = new ConstCollector(ssaMethod);
+    cc.run();
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param ssaMethod {@code non-null;} method to process
+   */
+  private ConstCollector(SsaMethod ssaMethod) {
+    this.ssaMeth = ssaMethod;
+  }
+
+  /**
+   * Applies the optimization.
+   */
+  private void run() {
+    int regSz = ssaMeth.getRegCount();
+
+    ArrayList<TypedConstant> constantList = getConstsSortedByCountUse();
+
+    int toCollect = Math.min(constantList.size(), MAX_COLLECTED_CONSTANTS);
+
+    SsaBasicBlock start = ssaMeth.getEntryBlock();
+
+    // Constant to new register containing the constant
+    HashMap<TypedConstant, RegisterSpec> newRegs =
+        new HashMap<TypedConstant, RegisterSpec>(toCollect);
+
+    for (int i = 0; i < toCollect; i++) {
+      TypedConstant cst = constantList.get(i);
+      RegisterSpec result = RegisterSpec.make(ssaMeth.makeNewSsaReg(), cst);
+
+      Rop constRop = Rops.opConst(cst);
+
+      if (constRop.getBranchingness() == Rop.BRANCH_NONE) {
+        start.addInsnToHead(new PlainCstInsn(Rops.opConst(cst), SourcePosition.NO_INFO, result,
+            RegisterSpecList.EMPTY, cst));
+      } else {
+        // We need two new basic blocks along with the new insn
+        SsaBasicBlock entryBlock = ssaMeth.getEntryBlock();
+        SsaBasicBlock successorBlock = entryBlock.getPrimarySuccessor();
+
+        // Insert a block containing the const insn.
+        SsaBasicBlock constBlock = entryBlock.insertNewSuccessor(successorBlock);
+
+        constBlock.replaceLastInsn(new ThrowingCstInsn(constRop, SourcePosition.NO_INFO,
+            RegisterSpecList.EMPTY, StdTypeList.EMPTY, cst));
+
+        // Insert a block containing the move-result-pseudo insn.
+
+        SsaBasicBlock resultBlock = constBlock.insertNewSuccessor(successorBlock);
+        PlainInsn insn = new PlainInsn(Rops.opMoveResultPseudo(result.getTypeBearer()),
+            SourcePosition.NO_INFO, result, RegisterSpecList.EMPTY);
+
+        resultBlock.addInsnToHead(insn);
+      }
+
+      newRegs.put(cst, result);
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ssaMethod {@code non-null;} method to process
+    updateConstUses(newRegs, regSz);
+  }
+
+  /**
+   * Gets all of the collectable constant values used in this method,
+   * sorted by most used first. Skips non-collectable consts, such as
+   * non-string object constants
+   *
+   * @return {@code non-null;} list of constants in most-to-least used order
+   */
+  private ArrayList<TypedConstant> getConstsSortedByCountUse() {
+    int regSz = ssaMeth.getRegCount();
+
+    final HashMap<TypedConstant, Integer> countUses = new HashMap<TypedConstant, Integer>();
+
+    /*
+     * Each collected constant can be used by just one local
+     * (used only if COLLECT_ONE_LOCAL is true).
      */
-    private ConstCollector(SsaMethod ssaMethod) {
-        this.ssaMeth = ssaMethod;
-    }
+    final HashSet<TypedConstant> usedByLocal = new HashSet<TypedConstant>();
 
-    /**
-     * Applies the optimization.
-     */
-    private void run() {
-        int regSz = ssaMeth.getRegCount();
+    // Count how many times each const value is used.
+    for (int i = 0; i < regSz; i++) {
+      SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
 
-        ArrayList<TypedConstant> constantList
-                = getConstsSortedByCountUse();
+      if (insn == null || insn.getOpcode() == null) {
+        continue;
+      }
 
-        int toCollect = Math.min(constantList.size(), MAX_COLLECTED_CONSTANTS);
+      RegisterSpec result = insn.getResult();
+      TypeBearer typeBearer = result.getTypeBearer();
 
-        SsaBasicBlock start = ssaMeth.getEntryBlock();
+      if (!typeBearer.isConstant()) {
+        continue;
+      }
 
-        // Constant to new register containing the constant
-        HashMap<TypedConstant, RegisterSpec> newRegs
-                = new HashMap<TypedConstant, RegisterSpec> (toCollect);
+      TypedConstant cst = (TypedConstant) typeBearer;
 
-        for (int i = 0; i < toCollect; i++) {
-            TypedConstant cst = constantList.get(i);
-            RegisterSpec result
-                    = RegisterSpec.make(ssaMeth.makeNewSsaReg(), cst);
+      // Find defining instruction for move-result-pseudo instructions
+      if (insn.getOpcode().getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
+        int pred = insn.getBlock().getPredecessors().nextSetBit(0);
+        ArrayList<SsaInsn> predInsns;
+        predInsns = ssaMeth.getBlocks().get(pred).getInsns();
+        insn = predInsns.get(predInsns.size() - 1);
+      }
 
-            Rop constRop = Rops.opConst(cst);
-
-            if (constRop.getBranchingness() == Rop.BRANCH_NONE) {
-                start.addInsnToHead(
-                        new PlainCstInsn(Rops.opConst(cst),
-                                SourcePosition.NO_INFO, result,
-                                RegisterSpecList.EMPTY, cst));
-            } else {
-                // We need two new basic blocks along with the new insn
-                SsaBasicBlock entryBlock = ssaMeth.getEntryBlock();
-                SsaBasicBlock successorBlock
-                        = entryBlock.getPrimarySuccessor();
-
-                // Insert a block containing the const insn.
-                SsaBasicBlock constBlock
-                        = entryBlock.insertNewSuccessor(successorBlock);
-
-                constBlock.replaceLastInsn(
-                        new ThrowingCstInsn(constRop, SourcePosition.NO_INFO,
-                                RegisterSpecList.EMPTY,
-                                StdTypeList.EMPTY, cst));
-
-                // Insert a block containing the move-result-pseudo insn.
-
-                SsaBasicBlock resultBlock
-                        = constBlock.insertNewSuccessor(successorBlock);
-                PlainInsn insn
-                    = new PlainInsn(
-                            Rops.opMoveResultPseudo(result.getTypeBearer()),
-                            SourcePosition.NO_INFO,
-                            result, RegisterSpecList.EMPTY);
-
-                resultBlock.addInsnToHead(insn);
-            }
-
-            newRegs.put(cst, result);
-        }
-
-        updateConstUses(newRegs, regSz);
-    }
-
-    /**
-     * Gets all of the collectable constant values used in this method,
-     * sorted by most used first. Skips non-collectable consts, such as
-     * non-string object constants
-     *
-     * @return {@code non-null;} list of constants in most-to-least used order
-     */
-    private ArrayList<TypedConstant> getConstsSortedByCountUse() {
-        int regSz = ssaMeth.getRegCount();
-
-        final HashMap<TypedConstant, Integer> countUses
-                = new HashMap<TypedConstant, Integer>();
-
+      if (insn.canThrow()) {
         /*
-         * Each collected constant can be used by just one local
-         * (used only if COLLECT_ONE_LOCAL is true).
+         * Don't move anything other than strings -- the risk
+         * of changing where an exception is thrown is too high.
          */
-        final HashSet<TypedConstant> usedByLocal
-                = new HashSet<TypedConstant>();
-
-        // Count how many times each const value is used.
-        for (int i = 0; i < regSz; i++) {
-            SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
-
-            if (insn == null || insn.getOpcode() == null) continue;
-
-            RegisterSpec result = insn.getResult();
-            TypeBearer typeBearer = result.getTypeBearer();
-
-            if (!typeBearer.isConstant()) continue;
-
-            TypedConstant cst = (TypedConstant) typeBearer;
-
-            // Find defining instruction for move-result-pseudo instructions
-            if (insn.getOpcode().getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
-                int pred = insn.getBlock().getPredecessors().nextSetBit(0);
-                ArrayList<SsaInsn> predInsns;
-                predInsns = ssaMeth.getBlocks().get(pred).getInsns();
-                insn = predInsns.get(predInsns.size()-1);
-            }
-
-            if (insn.canThrow()) {
-                /*
-                 * Don't move anything other than strings -- the risk
-                 * of changing where an exception is thrown is too high.
-                 */
-                if (!(cst instanceof CstString) || !COLLECT_STRINGS) {
-                    continue;
-                }
-                /*
-                 * We can't move any throwable const whose throw will be
-                 * caught, so don't count them.
-                 */
-                if (insn.getBlock().getSuccessors().cardinality() > 1) {
-                    continue;
-                }
-            }
-
-            /*
-             * TODO: Might be nice to try and figure out which local
-             * wins most when collected.
-             */
-            if (ssaMeth.isRegALocal(result)) {
-                if (!COLLECT_ONE_LOCAL) {
-                    continue;
-                } else {
-                    if (usedByLocal.contains(cst)) {
-                        // Count one local usage only.
-                        continue;
-                    } else {
-                        usedByLocal.add(cst);
-                    }
-                }
-            }
-
-            Integer has = countUses.get(cst);
-            if (has == null) {
-                countUses.put(cst, 1);
-            } else {
-                countUses.put(cst, has + 1);
-            }
+        if (!(cst instanceof CstString) || !collectStrings) {
+          continue;
         }
-
-        // Collect constants that have been reused.
-        ArrayList<TypedConstant> constantList = new ArrayList<TypedConstant>();
-        for (Map.Entry<TypedConstant, Integer> entry : countUses.entrySet()) {
-            if (entry.getValue() > 1) {
-                constantList.add(entry.getKey());
-            }
-        }
-
-        // Sort by use, with most used at the beginning of the list.
-        Collections.sort(constantList, new Comparator<Constant>() {
-            public int compare(Constant a, Constant b) {
-                int ret;
-                ret = countUses.get(b) - countUses.get(a);
-
-                if (ret == 0) {
-                    /*
-                     * Provide sorting determinisim for constants with same
-                     * usage count.
-                     */
-                    ret = a.compareTo(b);
-                }
-
-                return ret;
-            }
-
-            @Override
-            public boolean equals (Object obj) {
-                return obj == this;
-            }
-        });
-
-        return constantList;
-    }
-
-    /**
-     * Inserts mark-locals if necessary when changing a register. If
-     * the definition of {@code origReg} is associated with a local
-     * variable, then insert a mark-local for {@code newReg} just below
-     * it. We expect the definition of  {@code origReg} to ultimately
-     * be removed by the dead code eliminator
-     *
-     * @param origReg {@code non-null;} original register
-     * @param newReg {@code non-null;} new register that will replace
-     * {@code origReg}
-     */
-    private void fixLocalAssignment(RegisterSpec origReg,
-            RegisterSpec newReg) {
-        for (SsaInsn use : ssaMeth.getUseListForRegister(origReg.getReg())) {
-            RegisterSpec localAssignment = use.getLocalAssignment();
-            if (localAssignment == null) {
-                continue;
-            }
-
-            if (use.getResult() == null) {
-                /*
-                 * This is a mark-local. it will be updated when all uses
-                 * are updated.
-                 */
-                continue;
-            }
-
-            LocalItem local = localAssignment.getLocalItem();
-
-            // Un-associate original use.
-            use.setResultLocal(null);
-
-            // Now add a mark-local to the new reg immediately after.
-            newReg = newReg.withLocalItem(local);
-
-            SsaInsn newInsn
-                    = SsaInsn.makeFromRop(
-                        new PlainInsn(Rops.opMarkLocal(newReg),
-                        SourcePosition.NO_INFO, null,
-                                RegisterSpecList.make(newReg)),
-                    use.getBlock());
-
-            ArrayList<SsaInsn> insns = use.getBlock().getInsns();
-
-            insns.add(insns.indexOf(use) + 1, newInsn);
-        }
-    }
-
-    /**
-     * Updates all uses of various consts to use the values in the newly
-     * assigned registers.
-     *
-     * @param newRegs {@code non-null;} mapping between constant and new reg
-     * @param origRegCount {@code >=0;} original SSA reg count, not including
-     * newly added constant regs
-     */
-    private void updateConstUses(HashMap<TypedConstant, RegisterSpec> newRegs,
-            int origRegCount) {
-
         /*
-         * set of constants associated with a local variable; used
-         * only if COLLECT_ONE_LOCAL is true.
+         * We can't move any throwable const whose throw will be
+         * caught, so don't count them.
          */
-        final HashSet<TypedConstant> usedByLocal
-                = new HashSet<TypedConstant>();
-
-        final ArrayList<SsaInsn>[] useList = ssaMeth.getUseListCopy();
-
-        for (int i = 0; i < origRegCount; i++) {
-            SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
-
-            if (insn == null) {
-                continue;
-            }
-
-            final RegisterSpec origReg = insn.getResult();
-            TypeBearer typeBearer = insn.getResult().getTypeBearer();
-
-            if (!typeBearer.isConstant()) continue;
-
-            TypedConstant cst = (TypedConstant) typeBearer;
-            final RegisterSpec newReg = newRegs.get(cst);
-
-            if (newReg == null) {
-                continue;
-            }
-
-            if (ssaMeth.isRegALocal(origReg)) {
-                if (!COLLECT_ONE_LOCAL) {
-                    continue;
-                } else {
-                    /*
-                     * TODO: If the same local gets the same cst
-                     * multiple times, it would be nice to reuse the
-                     * register.
-                     */
-                    if (usedByLocal.contains(cst)) {
-                        continue;
-                    } else {
-                        usedByLocal.add(cst);
-                        fixLocalAssignment(origReg, newRegs.get(cst));
-                    }
-                }
-            }
-
-            // maps an original const register to the new collected register
-            RegisterMapper mapper = new RegisterMapper() {
-                @Override
-                public int getNewRegisterCount() {
-                    return ssaMeth.getRegCount();
-                }
-
-                @Override
-                public RegisterSpec map(RegisterSpec registerSpec) {
-                    if (registerSpec.getReg() == origReg.getReg()) {
-                        return newReg.withLocalItem(
-                                registerSpec.getLocalItem());
-                    }
-
-                    return registerSpec;
-                }
-            };
-
-            for (SsaInsn use : useList[origReg.getReg()]) {
-                if (use.canThrow()
-                        && use.getBlock().getSuccessors().cardinality() > 1) {
-                    continue;
-                }
-                use.mapSourceRegisters(mapper);
-            }
+        if (insn.getBlock().getSuccessors().cardinality() > 1) {
+          continue;
         }
+      }
+
+      /*
+       * TODO(dx team): Might be nice to try and figure out which local
+       * wins most when collected.
+       */
+      if (ssaMeth.isRegALocal(result)) {
+        if (!COLLECT_ONE_LOCAL) {
+          continue;
+        } else {
+          if (usedByLocal.contains(cst)) {
+            // Count one local usage only.
+            continue;
+          } else {
+            usedByLocal.add(cst);
+          }
+        }
+      }
+
+      Integer has = countUses.get(cst);
+      if (has == null) {
+        countUses.put(cst, 1);
+      } else {
+        countUses.put(cst, has + 1);
+      }
     }
+
+    // Collect constants that have been reused.
+    ArrayList<TypedConstant> constantList = new ArrayList<TypedConstant>();
+    for (Map.Entry<TypedConstant, Integer> entry : countUses.entrySet()) {
+      if (entry.getValue() > 1) {
+        constantList.add(entry.getKey());
+      }
+    }
+
+    // Sort by use, with most used at the beginning of the list.
+    Collections.sort(constantList, new Comparator<Constant>() {
+      @Override
+      public int compare(Constant a, Constant b) {
+        int ret;
+        ret = countUses.get(b) - countUses.get(a);
+
+        if (ret == 0) {
+          /*
+           * Provide sorting determinisim for constants with same
+           * usage count.
+           */
+          ret = a.compareTo(b);
+        }
+
+        return ret;
+      }
+
+      @Override
+      public boolean equals(Object obj) {
+        return obj == this;
+      }
+    });
+
+    return constantList;
+  }
+
+  /**
+   * Inserts mark-locals if necessary when changing a register. If
+   * the definition of {@code origReg} is associated with a local
+   * variable, then insert a mark-local for {@code newReg} just below
+   * it. We expect the definition of  {@code origReg} to ultimately
+   * be removed by the dead code eliminator
+   *
+   * @param origReg {@code non-null;} original register
+   * @param newReg {@code non-null;} new register that will replace
+   * {@code origReg}
+   */
+  private void fixLocalAssignment(RegisterSpec origReg, RegisterSpec newReg) {
+    for (SsaInsn use : ssaMeth.getUseListForRegister(origReg.getReg())) {
+      RegisterSpec localAssignment = use.getLocalAssignment();
+      if (localAssignment == null) {
+        continue;
+      }
+
+      if (use.getResult() == null) {
+        /*
+         * This is a mark-local. it will be updated when all uses
+         * are updated.
+         */
+        continue;
+      }
+
+      LocalItem local = localAssignment.getLocalItem();
+
+      // Un-associate original use.
+      use.setResultLocal(null);
+
+      // Now add a mark-local to the new reg immediately after.
+      newReg = newReg.withLocalItem(local);
+
+      SsaInsn newInsn = SsaInsn.makeFromRop(new PlainInsn(Rops.opMarkLocal(newReg),
+          SourcePosition.NO_INFO, null, RegisterSpecList.make(newReg)), use.getBlock());
+
+      ArrayList<SsaInsn> insns = use.getBlock().getInsns();
+
+      insns.add(insns.indexOf(use) + 1, newInsn);
+    }
+  }
+
+  /**
+   * Updates all uses of various consts to use the values in the newly
+   * assigned registers.
+   *
+   * @param newRegs {@code non-null;} mapping between constant and new reg
+   * @param origRegCount {@code >=0;} original SSA reg count, not including
+   * newly added constant regs
+   */
+  private void updateConstUses(HashMap<TypedConstant, RegisterSpec> newRegs, int origRegCount) {
+
+    /*
+     * set of constants associated with a local variable; used
+     * only if COLLECT_ONE_LOCAL is true.
+     */
+    final HashSet<TypedConstant> usedByLocal = new HashSet<TypedConstant>();
+
+    final ArrayList<SsaInsn>[] useList = ssaMeth.getUseListCopy();
+
+    for (int i = 0; i < origRegCount; i++) {
+      SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
+
+      if (insn == null) {
+        continue;
+      }
+
+      final RegisterSpec origReg = insn.getResult();
+      TypeBearer typeBearer = insn.getResult().getTypeBearer();
+
+      if (!typeBearer.isConstant()) {
+        continue;
+      }
+
+      TypedConstant cst = (TypedConstant) typeBearer;
+      final RegisterSpec newReg = newRegs.get(cst);
+
+      if (newReg == null) {
+        continue;
+      }
+
+      if (ssaMeth.isRegALocal(origReg)) {
+        if (!COLLECT_ONE_LOCAL) {
+          continue;
+        } else {
+          /*
+           * TODO(dx team): If the same local gets the same cst
+           * multiple times, it would be nice to reuse the
+           * register.
+           */
+          if (usedByLocal.contains(cst)) {
+            continue;
+          } else {
+            usedByLocal.add(cst);
+            fixLocalAssignment(origReg, newRegs.get(cst));
+          }
+        }
+      }
+
+      // maps an original const register to the new collected register
+      RegisterMapper mapper = new RegisterMapper() {
+        @Override
+        public int getNewRegisterCount() {
+          return ssaMeth.getRegCount();
+        }
+
+        @Override
+        public RegisterSpec map(RegisterSpec registerSpec) {
+          if (registerSpec.getReg() == origReg.getReg()) {
+            return newReg.withLocalItem(registerSpec.getLocalItem());
+          }
+
+          return registerSpec;
+        }
+      };
+
+      for (SsaInsn use : useList[origReg.getReg()]) {
+        if (use.canThrow() && use.getBlock().getSuccessors().cardinality() > 1) {
+          continue;
+        }
+        use.mapSourceRegisters(mapper);
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/DeadCodeRemover.java b/dx/src/com/android/jack/dx/ssa/DeadCodeRemover.java
index 70c0005..27040cf 100644
--- a/dx/src/com/android/jack/dx/ssa/DeadCodeRemover.java
+++ b/dx/src/com/android/jack/dx/ssa/DeadCodeRemover.java
@@ -16,14 +16,8 @@
 
 package com.android.jack.dx.ssa;
 
-import com.android.jack.dx.rop.code.Insn;
-import com.android.jack.dx.rop.code.PlainInsn;
-import com.android.jack.dx.rop.code.RegOps;
 import com.android.jack.dx.rop.code.RegisterSpec;
 import com.android.jack.dx.rop.code.RegisterSpecList;
-import com.android.jack.dx.rop.code.Rop;
-import com.android.jack.dx.rop.code.Rops;
-import com.android.jack.dx.rop.code.SourcePosition;
 
 import java.util.ArrayList;
 import java.util.BitSet;
@@ -32,241 +26,244 @@
 /**
  * A variation on Appel Algorithm 19.12 "Dead code elimination in SSA form".
  *
- * TODO this algorithm is more efficient if run in reverse from exit
+ * TODO(dx team) this algorithm is more efficient if run in reverse from exit
  * block to entry block.
  */
 public class DeadCodeRemover {
-    /** method we're processing */
-    private final SsaMethod ssaMeth;
+  /** method we're processing */
+  private final SsaMethod ssaMeth;
 
-    /** ssaMeth.getRegCount() */
-    private final int regCount;
+  /** ssaMeth.getRegCount() */
+  private final int regCount;
 
-    /**
-     * indexed by register: whether reg should be examined
-     * (does it correspond to a no-side-effect insn?)
-     */
-    private final BitSet worklist;
+  /**
+   * indexed by register: whether reg should be examined
+   * (does it correspond to a no-side-effect insn?)
+   */
+  private final BitSet worklist;
 
-    /** use list indexed by register; modified during operation */
-    private final ArrayList<SsaInsn>[] useList;
+  /** use list indexed by register; modified during operation */
+  private final ArrayList<SsaInsn>[] useList;
 
-    /**
-     * Process a method with the dead-code remver
-     *
-     * @param ssaMethod method to process
-     */
-    public static void process(SsaMethod ssaMethod) {
-        DeadCodeRemover dc = new DeadCodeRemover(ssaMethod);
-        dc.run();
-    }
+  /**
+   * Process a method with the dead-code remver
+   *
+   * @param ssaMethod method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    DeadCodeRemover dc = new DeadCodeRemover(ssaMethod);
+    dc.run();
+  }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ssaMethod method to process
-     */
-    private DeadCodeRemover(SsaMethod ssaMethod) {
-        this.ssaMeth = ssaMethod;
+  /**
+   * Constructs an instance.
+   *
+   * @param ssaMethod method to process
+   */
+  private DeadCodeRemover(SsaMethod ssaMethod) {
+    this.ssaMeth = ssaMethod;
 
-        regCount = ssaMethod.getRegCount();
-        worklist = new BitSet(regCount);
-        useList = ssaMeth.getUseListCopy();
-    }
+    regCount = ssaMethod.getRegCount();
+    worklist = new BitSet(regCount);
+    useList = ssaMeth.getUseListCopy();
+  }
 
-    /**
-     * Runs the dead code remover.
-     */
-    private void run() {
-        pruneDeadInstructions();
+  /**
+   * Runs the dead code remover.
+   */
+  private void run() {
+    pruneDeadInstructions();
 
-        HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
+    HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
 
-        ssaMeth.forEachInsn(new NoSideEffectVisitor(worklist));
+    ssaMeth.forEachInsn(new NoSideEffectVisitor(worklist));
 
-        int regV;
+    int regV;
 
-        while ( 0 <= (regV = worklist.nextSetBit(0)) ) {
-            worklist.clear(regV);
+    while (0 <= (regV = worklist.nextSetBit(0))) {
+      worklist.clear(regV);
 
-            if (useList[regV].size() == 0
-                    || isCircularNoSideEffect(regV, null)) {
+      if (useList[regV].size() == 0 || isCircularNoSideEffect(regV, null)) {
 
-                SsaInsn insnS = ssaMeth.getDefinitionForRegister(regV);
+        SsaInsn insnS = ssaMeth.getDefinitionForRegister(regV);
 
-                // This insn has already been deleted.
-                if (deletedInsns.contains(insnS)) {
-                    continue;
-                }
-
-                RegisterSpecList sources = insnS.getSources();
-
-                int sz = sources.size();
-                for (int i = 0; i < sz; i++) {
-                    // Delete this insn from all usage lists.
-                    RegisterSpec source = sources.get(i);
-                    useList[source.getReg()].remove(insnS);
-
-                    if (!hasSideEffect(
-                            ssaMeth.getDefinitionForRegister(
-                                    source.getReg()))) {
-                        /*
-                         * Only registers whose definition has no side effect
-                         * should be added back to the worklist.
-                         */
-                        worklist.set(source.getReg());
-                    }
-                }
-
-                // Schedule this insn for later deletion.
-                deletedInsns.add(insnS);
-            }
+        // This insn has already been deleted.
+        if (deletedInsns.contains(insnS)) {
+          continue;
         }
 
-        ssaMeth.deleteInsns(deletedInsns);
-    }
+        RegisterSpecList sources = insnS.getSources();
 
-    /**
-     * Removes all instructions from every unreachable block.
-     */
-    private void pruneDeadInstructions() {
-        HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
+        int sz = sources.size();
+        for (int i = 0; i < sz; i++) {
+          // Delete this insn from all usage lists.
+          RegisterSpec source = sources.get(i);
+          useList[source.getReg()].remove(insnS);
 
-        ssaMeth.computeReachability();
-
-        for (SsaBasicBlock block : ssaMeth.getBlocks()) {
-            if (block.isReachable()) continue;
-
-            // Prune instructions from unreachable blocks
-            for (int i = 0; i < block.getInsns().size(); i++) {
-                SsaInsn insn = block.getInsns().get(i);
-                RegisterSpecList sources = insn.getSources();
-                int sourcesSize = sources.size();
-
-                // Delete this instruction completely if it has sources
-                if (sourcesSize != 0) {
-                    deletedInsns.add(insn);
-                }
-
-                // Delete this instruction from all usage lists.
-                for (int j = 0; j < sourcesSize; j++) {
-                    RegisterSpec source = sources.get(j);
-                    useList[source.getReg()].remove(insn);
-                }
-
-                // Remove this instruction result from the sources of any phis
-                RegisterSpec result = insn.getResult();
-                if (result == null) continue;
-                for (SsaInsn use : useList[result.getReg()]) {
-                    if (use instanceof PhiInsn) {
-                        PhiInsn phiUse = (PhiInsn) use;
-                        phiUse.removePhiRegister(result);
-                    }
-                }
-            }
-        }
-
-        ssaMeth.deleteInsns(deletedInsns);
-    }
-
-    /**
-     * Returns true if the only uses of this register form a circle of
-     * operations with no side effects.
-     *
-     * @param regV register to examine
-     * @param set a set of registers that we've already determined
-     * are only used as sources in operations with no side effect or null
-     * if this is the first recursion
-     * @return true if usage is circular without side effect
-     */
-    private boolean isCircularNoSideEffect(int regV, BitSet set) {
-        if ((set != null) && set.get(regV)) {
-            return true;
-        }
-
-        for (SsaInsn use : useList[regV]) {
-            if (hasSideEffect(use)) {
-                return false;
-            }
-        }
-
-        if (set == null) {
-            set = new BitSet(regCount);
-        }
-
-        // This register is only used in operations that have no side effect.
-        set.set(regV);
-
-        for (SsaInsn use : useList[regV]) {
-            RegisterSpec result = use.getResult();
-
-            if (result == null
-                    || !isCircularNoSideEffect(result.getReg(), set)) {
-                return false;
-            }
-        }
-
-        return true;
-    }
-
-    /**
-     * Returns true if this insn has a side-effect. Returns true
-     * if the insn is null for reasons stated in the code block.
-     *
-     * @param insn {@code null-ok;} instruction in question
-     * @return true if it has a side-effect
-     */
-    private static boolean hasSideEffect(SsaInsn insn) {
-        if (insn == null) {
-            /* While false would seem to make more sense here, true
-             * prevents us from adding this back to a worklist unnecessarally.
+          if (!hasSideEffect(ssaMeth.getDefinitionForRegister(source.getReg()))) {
+            /*
+             * Only registers whose definition has no side effect
+             * should be added back to the worklist.
              */
-            return true;
+            worklist.set(source.getReg());
+          }
         }
 
-        return insn.hasSideEffect();
+        // Schedule this insn for later deletion.
+        deletedInsns.add(insnS);
+      }
     }
 
+    ssaMeth.deleteInsns(deletedInsns);
+  }
+
+  /**
+   * Removes all instructions from every unreachable block.
+   */
+  private void pruneDeadInstructions() {
+    HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
+
+    ssaMeth.computeReachability();
+
+    for (SsaBasicBlock block : ssaMeth.getBlocks()) {
+      if (block.isReachable()) {
+        continue;
+      }
+
+      // Prune instructions from unreachable blocks
+      for (int i = 0; i < block.getInsns().size(); i++) {
+        SsaInsn insn = block.getInsns().get(i);
+        RegisterSpecList sources = insn.getSources();
+        int sourcesSize = sources.size();
+
+        // Delete this instruction completely if it has sources
+        if (sourcesSize != 0) {
+          deletedInsns.add(insn);
+        }
+
+        // Delete this instruction from all usage lists.
+        for (int j = 0; j < sourcesSize; j++) {
+          RegisterSpec source = sources.get(j);
+          useList[source.getReg()].remove(insn);
+        }
+
+        // Remove this instruction result from the sources of any phis
+        RegisterSpec result = insn.getResult();
+        if (result == null) {
+          continue;
+        }
+        for (SsaInsn use : useList[result.getReg()]) {
+          if (use instanceof PhiInsn) {
+            PhiInsn phiUse = (PhiInsn) use;
+            phiUse.removePhiRegister(result);
+          }
+        }
+      }
+    }
+
+    ssaMeth.deleteInsns(deletedInsns);
+  }
+
+  /**
+   * Returns true if the only uses of this register form a circle of
+   * operations with no side effects.
+   *
+   * @param regV register to examine
+   * @param set a set of registers that we've already determined
+   * are only used as sources in operations with no side effect or null
+   * if this is the first recursion
+   * @return true if usage is circular without side effect
+   */
+  private boolean isCircularNoSideEffect(int regV, BitSet set) {
+    if ((set != null) && set.get(regV)) {
+      return true;
+    }
+
+    for (SsaInsn use : useList[regV]) {
+      if (hasSideEffect(use)) {
+        return false;
+      }
+    }
+
+    if (set == null) {
+      set = new BitSet(regCount);
+    }
+
+    // This register is only used in operations that have no side effect.
+    set.set(regV);
+
+    for (SsaInsn use : useList[regV]) {
+      RegisterSpec result = use.getResult();
+
+      if (result == null || !isCircularNoSideEffect(result.getReg(), set)) {
+        return false;
+      }
+    }
+
+    return true;
+  }
+
+  /**
+   * Returns true if this insn has a side-effect. Returns true
+   * if the insn is null for reasons stated in the code block.
+   *
+   * @param insn {@code null-ok;} instruction in question
+   * @return true if it has a side-effect
+   */
+  private static boolean hasSideEffect(SsaInsn insn) {
+    if (insn == null) {
+      /* While false would seem to make more sense here, true
+       * prevents us from adding this back to a worklist unnecessarally.
+       */
+      return true;
+    }
+
+    return insn.hasSideEffect();
+  }
+
+  /**
+   * A callback class used to build up the initial worklist of
+   * registers defined by an instruction with no side effect.
+   */
+  private static class NoSideEffectVisitor implements SsaInsn.Visitor {
+    BitSet noSideEffectRegs;
+
     /**
-     * A callback class used to build up the initial worklist of
-     * registers defined by an instruction with no side effect.
+     * Passes in data structures that will be filled out after
+     * ssaMeth.forEachInsn() is called with this instance.
+     *
+     * @param noSideEffectRegs to-build bitset of regs that are
+     * results of regs with no side effects
      */
-    static private class NoSideEffectVisitor implements SsaInsn.Visitor {
-        BitSet noSideEffectRegs;
-
-        /**
-         * Passes in data structures that will be filled out after
-         * ssaMeth.forEachInsn() is called with this instance.
-         *
-         * @param noSideEffectRegs to-build bitset of regs that are
-         * results of regs with no side effects
-         */
-        public NoSideEffectVisitor(BitSet noSideEffectRegs) {
-            this.noSideEffectRegs = noSideEffectRegs;
-        }
-
-        /** {@inheritDoc} */
-        public void visitMoveInsn (NormalSsaInsn insn) {
-            // If we're tracking local vars, some moves have side effects.
-            if (!hasSideEffect(insn)) {
-                noSideEffectRegs.set(insn.getResult().getReg());
-            }
-        }
-
-        /** {@inheritDoc} */
-        public void visitPhiInsn (PhiInsn phi) {
-            // If we're tracking local vars, then some phis have side effects.
-            if (!hasSideEffect(phi)) {
-                noSideEffectRegs.set(phi.getResult().getReg());
-            }
-        }
-
-        /** {@inheritDoc} */
-        public void visitNonMoveInsn (NormalSsaInsn insn) {
-            RegisterSpec result = insn.getResult();
-            if (!hasSideEffect(insn) && result != null) {
-                noSideEffectRegs.set(result.getReg());
-            }
-        }
+    public NoSideEffectVisitor(BitSet noSideEffectRegs) {
+      this.noSideEffectRegs = noSideEffectRegs;
     }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitMoveInsn(NormalSsaInsn insn) {
+      // If we're tracking local vars, some moves have side effects.
+      if (!hasSideEffect(insn)) {
+        noSideEffectRegs.set(insn.getResult().getReg());
+      }
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitPhiInsn(PhiInsn phi) {
+      // If we're tracking local vars, then some phis have side effects.
+      if (!hasSideEffect(phi)) {
+        noSideEffectRegs.set(phi.getResult().getReg());
+      }
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    public void visitNonMoveInsn(NormalSsaInsn insn) {
+      RegisterSpec result = insn.getResult();
+      if (!hasSideEffect(insn) && result != null) {
+        noSideEffectRegs.set(result.getReg());
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/DomFront.java b/dx/src/com/android/jack/dx/ssa/DomFront.java
index 9e67f46..5a599ff 100644
--- a/dx/src/com/android/jack/dx/ssa/DomFront.java
+++ b/dx/src/com/android/jack/dx/ssa/DomFront.java
@@ -16,12 +16,9 @@
 
 package com.android.jack.dx.ssa;
 
-import com.android.jack.dx.util.BitIntSet;
 import com.android.jack.dx.util.IntSet;
-import com.android.jack.dx.util.ListIntSet;
 
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.BitSet;
 
 /**
@@ -30,175 +27,172 @@
  * Harvey, and Kennedy; transliterated to Java.
  */
 public class DomFront {
-    /** local debug flag */
-    private static boolean DEBUG = false;
+  /** local debug flag */
+  private static final boolean DEBUG = false;
 
-    /** {@code non-null;} method being processed */
-    private final SsaMethod meth;
+  /** {@code non-null;} method being processed */
+  private final SsaMethod meth;
 
-    private final ArrayList<SsaBasicBlock> nodes;
+  private final ArrayList<SsaBasicBlock> nodes;
 
-    private final DomInfo[] domInfos;
+  private final DomInfo[] domInfos;
 
+  /**
+   * Dominance-frontier information for a single basic block.
+   */
+  public static class DomInfo {
     /**
-     * Dominance-frontier information for a single basic block.
+     * {@code null-ok;} the dominance frontier set indexed by
+     * block index
      */
-    public static class DomInfo {
-        /**
-         * {@code null-ok;} the dominance frontier set indexed by
-         * block index
-         */
-        public IntSet dominanceFrontiers;
+    public IntSet dominanceFrontiers;
 
-        /** {@code >= 0 after run();} the index of the immediate dominator */
-        public int idom = -1;
+    /** {@code >= 0 after run();} the index of the immediate dominator */
+    public int idom = -1;
+  }
+
+  /**
+   * Constructs instance. Call {@link DomFront#run} to process.
+   *
+   * @param meth {@code non-null;} method to process
+   */
+  public DomFront(SsaMethod meth) {
+    this.meth = meth;
+    nodes = meth.getBlocks();
+
+    int szNodes = nodes.size();
+    domInfos = new DomInfo[szNodes];
+
+    for (int i = 0; i < szNodes; i++) {
+      domInfos[i] = new DomInfo();
+    }
+  }
+
+  /**
+   * Calculates the dominance frontier information for the method.
+   *
+   * @return {@code non-null;} an array of DomInfo structures
+   */
+  public DomInfo[] run() {
+    int szNodes = nodes.size();
+
+    if (DEBUG) {
+      for (int i = 0; i < szNodes; i++) {
+        SsaBasicBlock node = nodes.get(i);
+        System.out.println("pred[" + i + "]: " + node.getPredecessors());
+      }
     }
 
-    /**
-     * Constructs instance. Call {@link DomFront#run} to process.
-     *
-     * @param meth {@code non-null;} method to process
-     */
-    public DomFront(SsaMethod meth) {
-        this.meth = meth;
-        nodes = meth.getBlocks();
+    Dominators.make(meth, domInfos, false);
 
-        int szNodes = nodes.size();
-        domInfos = new DomInfo[szNodes];
+    if (DEBUG) {
+      for (int i = 0; i < szNodes; i++) {
+        DomInfo info = domInfos[i];
+        System.out.println("idom[" + i + "]: " + info.idom);
+      }
+    }
 
-        for (int i = 0; i < szNodes; i++) {
-            domInfos[i] = new DomInfo();
+    buildDomTree();
+
+    if (DEBUG) {
+      debugPrintDomChildren();
+    }
+
+    for (int i = 0; i < szNodes; i++) {
+      domInfos[i].dominanceFrontiers = SetFactory.makeDomFrontSet(szNodes);
+    }
+
+    calcDomFronts();
+
+    if (DEBUG) {
+      for (int i = 0; i < szNodes; i++) {
+        System.out.println("df[" + i + "]: " + domInfos[i].dominanceFrontiers);
+      }
+    }
+
+    return domInfos;
+  }
+
+  private void debugPrintDomChildren() {
+    int szNodes = nodes.size();
+
+    for (int i = 0; i < szNodes; i++) {
+      SsaBasicBlock node = nodes.get(i);
+      StringBuffer sb = new StringBuffer();
+
+      sb.append('{');
+      boolean comma = false;
+      for (SsaBasicBlock child : node.getDomChildren()) {
+        if (comma) {
+          sb.append(',');
         }
+        sb.append(child);
+        comma = true;
+      }
+      sb.append('}');
+
+      System.out.println("domChildren[" + node + "]: " + sb);
     }
+  }
 
-    /**
-     * Calculates the dominance frontier information for the method.
-     *
-     * @return {@code non-null;} an array of DomInfo structures
-     */
-    public DomInfo[] run() {
-        int szNodes = nodes.size();
+  /**
+   * The dominators algorithm leaves us knowing who the immediate dominator
+   * is for each node. This sweeps the node list and builds the proper
+   * dominance tree.
+   */
+  private void buildDomTree() {
+    int szNodes = nodes.size();
 
-        if (DEBUG) {
-            for (int i = 0; i < szNodes; i++) {
-                SsaBasicBlock node = nodes.get(i);
-                System.out.println("pred[" + i + "]: "
-                        + node.getPredecessors());
+    for (int i = 0; i < szNodes; i++) {
+      DomInfo info = domInfos[i];
+
+      if (info.idom == -1) {
+        continue;
+      }
+
+      SsaBasicBlock domParent = nodes.get(info.idom);
+      domParent.addDomChild(nodes.get(i));
+    }
+  }
+
+  /**
+   * Calculates the dominance-frontier set.
+   * from "A Simple, Fast Dominance Algorithm" by Cooper,
+   * Harvey, and Kennedy; transliterated to Java.
+   */
+  private void calcDomFronts() {
+    int szNodes = nodes.size();
+
+    for (int b = 0; b < szNodes; b++) {
+      SsaBasicBlock nb = nodes.get(b);
+      DomInfo nbInfo = domInfos[b];
+      BitSet pred = nb.getPredecessors();
+
+      if (pred.cardinality() > 1) {
+        for (int i = pred.nextSetBit(0); i >= 0; i = pred.nextSetBit(i + 1)) {
+
+          for (int runnerIndex = i; runnerIndex != nbInfo.idom; /* empty */) {
+            /*
+             * We can stop if we hit a block we already
+             * added label to, since we must be at a part
+             * of the dom tree we have seen before.
+             */
+            if (runnerIndex == -1) {
+              break;
             }
-        }
 
-        Dominators methDom = Dominators.make(meth, domInfos, false);
+            DomInfo runnerInfo = domInfos[runnerIndex];
 
-        if (DEBUG) {
-            for (int i = 0; i < szNodes; i++) {
-                DomInfo info = domInfos[i];
-                System.out.println("idom[" + i + "]: "
-                        + info.idom);
+            if (runnerInfo.dominanceFrontiers.has(b)) {
+              break;
             }
+
+            // Add b to runner's dominance frontier set.
+            runnerInfo.dominanceFrontiers.add(b);
+            runnerIndex = runnerInfo.idom;
+          }
         }
-
-        buildDomTree();
-
-        if (DEBUG) {
-            debugPrintDomChildren();
-        }
-
-        for (int i = 0; i < szNodes; i++) {
-            domInfos[i].dominanceFrontiers
-                    = SetFactory.makeDomFrontSet(szNodes);
-        }
-
-        calcDomFronts();
-
-        if (DEBUG) {
-            for (int i = 0; i < szNodes; i++) {
-                System.out.println("df[" + i + "]: "
-                        + domInfos[i].dominanceFrontiers);
-            }
-        }
-
-        return domInfos;
+      }
     }
-
-    private void debugPrintDomChildren() {
-        int szNodes = nodes.size();
-
-        for (int i = 0; i < szNodes; i++) {
-            SsaBasicBlock node = nodes.get(i);
-            StringBuffer sb = new StringBuffer();
-
-            sb.append('{');
-            boolean comma = false;
-            for (SsaBasicBlock child : node.getDomChildren()) {
-                if (comma) {
-                    sb.append(',');
-                }
-                sb.append(child);
-                comma = true;
-            }
-            sb.append('}');
-
-            System.out.println("domChildren[" + node + "]: "
-                    + sb);
-        }
-    }
-
-    /**
-     * The dominators algorithm leaves us knowing who the immediate dominator
-     * is for each node. This sweeps the node list and builds the proper
-     * dominance tree.
-     */
-    private void buildDomTree() {
-        int szNodes = nodes.size();
-
-        for (int i = 0; i < szNodes; i++) {
-            DomInfo info = domInfos[i];
-
-            if (info.idom == -1) continue;
-
-            SsaBasicBlock domParent = nodes.get(info.idom);
-            domParent.addDomChild(nodes.get(i));
-        }
-    }
-
-    /**
-     * Calculates the dominance-frontier set.
-     * from "A Simple, Fast Dominance Algorithm" by Cooper,
-     * Harvey, and Kennedy; transliterated to Java.
-     */
-    private void calcDomFronts() {
-        int szNodes = nodes.size();
-
-        for (int b = 0; b < szNodes; b++) {
-            SsaBasicBlock nb = nodes.get(b);
-            DomInfo nbInfo = domInfos[b];
-            BitSet pred = nb.getPredecessors();
-
-            if (pred.cardinality() > 1) {
-                for (int i = pred.nextSetBit(0); i >= 0;
-                     i = pred.nextSetBit(i + 1)) {
-
-                    for (int runnerIndex = i;
-                         runnerIndex != nbInfo.idom; /* empty */) {
-                        /*
-                         * We can stop if we hit a block we already
-                         * added label to, since we must be at a part
-                         * of the dom tree we have seen before.
-                         */
-                        if (runnerIndex == -1) break;
-
-                        DomInfo runnerInfo = domInfos[runnerIndex];
-
-                        if (runnerInfo.dominanceFrontiers.has(b)) {
-                            break;
-                        }
-
-                        // Add b to runner's dominance frontier set.
-                        runnerInfo.dominanceFrontiers.add(b);
-                        runnerIndex = runnerInfo.idom;
-                    }
-                }
-            }
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/Dominators.java b/dx/src/com/android/jack/dx/ssa/Dominators.java
index b3b4c3f..3311efd 100644
--- a/dx/src/com/android/jack/dx/ssa/Dominators.java
+++ b/dx/src/com/android/jack/dx/ssa/Dominators.java
@@ -41,245 +41,229 @@
  * rank to keep the union-find tree balanced.
  */
 public final class Dominators {
-    /* postdom is true if we want post dominators */
-    private final boolean postdom;
+  /* postdom is true if we want post dominators */
+  private final boolean postdom;
 
-    /* {@code non-null;} method being processed */
-    private final SsaMethod meth;
+  /* {@code non-null;} method being processed */
+  private final SsaMethod meth;
 
-    /* Method's basic blocks. */
-    private final ArrayList<SsaBasicBlock> blocks;
+  /* Method's basic blocks. */
+  private final ArrayList<SsaBasicBlock> blocks;
 
-    /** indexed by basic block index */
-    private final DFSInfo[] info;
+  /** indexed by basic block index */
+  private final DFSInfo[] info;
 
-    private final ArrayList<SsaBasicBlock> vertex;
+  private final ArrayList<SsaBasicBlock> vertex;
 
-    /** {@code non-null;} the raw dominator info */
-    private final DomFront.DomInfo domInfos[];
+  /** {@code non-null;} the raw dominator info */
+  private final DomFront.DomInfo domInfos[];
 
-    /**
-     * Constructs an instance.
-     *
-     * @param meth {@code non-null;} method to process
-     * @param domInfos {@code non-null;} the raw dominator info
-     * @param postdom true for postdom information, false for normal dom info
+  /**
+   * Constructs an instance.
+   *
+   * @param meth {@code non-null;} method to process
+   * @param domInfos {@code non-null;} the raw dominator info
+   * @param postdom true for postdom information, false for normal dom info
+   */
+  private Dominators(SsaMethod meth, DomFront.DomInfo[] domInfos, boolean postdom) {
+    this.meth = meth;
+    this.domInfos = domInfos;
+    this.postdom = postdom;
+    this.blocks = meth.getBlocks();
+    this.info = new DFSInfo[blocks.size() + 2];
+    this.vertex = new ArrayList<SsaBasicBlock>();
+  }
+
+  /**
+   * Constructs a fully-initialized instance. (This method exists so as
+   * to avoid calling a large amount of code in the constructor.)
+   *
+   * @param meth {@code non-null;} method to process
+   * @param domInfos {@code non-null;} the raw dominator info
+   * @param postdom true for postdom information, false for normal dom info
+   */
+  public static Dominators make(SsaMethod meth, DomFront.DomInfo[] domInfos, boolean postdom) {
+    Dominators result = new Dominators(meth, domInfos, postdom);
+
+    result.run();
+    return result;
+  }
+
+  private BitSet getPreds(SsaBasicBlock block) {
+    if (postdom) {
+      return block.getSuccessors();
+    } else {
+      return block.getPredecessors();
+    }
+  }
+
+  /**
+   * Performs path compress on the DFS info.
+   *
+   * @param in Basic block whose DFS info we are path compressing.
+   */
+  private void compress(SsaBasicBlock in) {
+    DFSInfo bbInfo = info[in.getIndex()];
+    DFSInfo ancestorbbInfo = info[bbInfo.ancestor.getIndex()];
+
+    if (ancestorbbInfo.ancestor != null) {
+      ArrayList<SsaBasicBlock> worklist = new ArrayList<SsaBasicBlock>();
+      HashSet<SsaBasicBlock> visited = new HashSet<SsaBasicBlock>();
+      worklist.add(in);
+
+      while (!worklist.isEmpty()) {
+        int wsize = worklist.size();
+        SsaBasicBlock v = worklist.get(wsize - 1);
+        DFSInfo vbbInfo = info[v.getIndex()];
+        SsaBasicBlock vAncestor = vbbInfo.ancestor;
+        DFSInfo vabbInfo = info[vAncestor.getIndex()];
+
+        // Make sure we process our ancestor before ourselves.
+        if (visited.add(vAncestor) && vabbInfo.ancestor != null) {
+          worklist.add(vAncestor);
+          continue;
+        }
+        worklist.remove(wsize - 1);
+
+        // Update based on ancestor info.
+        if (vabbInfo.ancestor == null) {
+          continue;
+        }
+        SsaBasicBlock vAncestorRep = vabbInfo.rep;
+        SsaBasicBlock vRep = vbbInfo.rep;
+        if (info[vAncestorRep.getIndex()].semidom < info[vRep.getIndex()].semidom) {
+          vbbInfo.rep = vAncestorRep;
+        }
+        vbbInfo.ancestor = vabbInfo.ancestor;
+      }
+    }
+  }
+
+  private SsaBasicBlock eval(SsaBasicBlock v) {
+    DFSInfo bbInfo = info[v.getIndex()];
+
+    if (bbInfo.ancestor == null) {
+      return v;
+    }
+
+    compress(v);
+    return bbInfo.rep;
+  }
+
+  /**
+   * Performs dominator/post-dominator calculation for the control
+   * flow graph.
+   *
+   * @param meth {@code non-null;} method to analyze
+   */
+  private void run() {
+    SsaBasicBlock root = postdom ? meth.getExitBlock() : meth.getEntryBlock();
+
+    if (root != null) {
+      vertex.add(root);
+      domInfos[root.getIndex()].idom = root.getIndex();
+    }
+
+    /*
+     * First we perform a DFS numbering of the blocks, by
+     * numbering the dfs tree roots.
      */
-    private Dominators(SsaMethod meth, DomFront.DomInfo[] domInfos,
-            boolean postdom) {
-        this.meth = meth;
-        this.domInfos = domInfos;
-        this.postdom = postdom;
-        this.blocks = meth.getBlocks();
-        this.info = new DFSInfo[blocks.size() + 2];
-        this.vertex = new ArrayList<SsaBasicBlock>();
-    }
 
-    /**
-     * Constructs a fully-initialized instance. (This method exists so as
-     * to avoid calling a large amount of code in the constructor.)
-     *
-     * @param meth {@code non-null;} method to process
-     * @param domInfos {@code non-null;} the raw dominator info
-     * @param postdom true for postdom information, false for normal dom info
-     */
-    public static Dominators make(SsaMethod meth, DomFront.DomInfo[] domInfos,
-            boolean postdom) {
-        Dominators result = new Dominators(meth, domInfos, postdom);
+DfsWalker walker = new DfsWalker();
+    meth.forEachBlockDepthFirst(postdom, walker);
 
-        result.run();
-        return result;
-    }
+    // the largest semidom number assigned
+    int dfsMax = vertex.size() - 1;
 
-    private BitSet getSuccs(SsaBasicBlock block) {
-        if (postdom) {
-            return block.getPredecessors();
-        } else {
-            return block.getSuccessors();
-        }
-    }
+    // Now calculate semidominators.
+    for (int i = dfsMax; i >= 2; --i) {
+      SsaBasicBlock w = vertex.get(i);
+      DFSInfo wInfo = info[w.getIndex()];
 
-    private BitSet getPreds(SsaBasicBlock block) {
-        if (postdom) {
-            return block.getSuccessors();
-        } else {
-            return block.getPredecessors();
-        }
-    }
-
-    /**
-     * Performs path compress on the DFS info.
-     *
-     * @param in Basic block whose DFS info we are path compressing.
-     */
-    private void compress(SsaBasicBlock in) {
-        DFSInfo bbInfo = info[in.getIndex()];
-        DFSInfo ancestorbbInfo = info[bbInfo.ancestor.getIndex()];
-
-        if (ancestorbbInfo.ancestor != null) {
-            ArrayList<SsaBasicBlock> worklist = new ArrayList<SsaBasicBlock>();
-            HashSet<SsaBasicBlock> visited = new HashSet<SsaBasicBlock>();
-            worklist.add(in);
-
-            while (!worklist.isEmpty()) {
-                int wsize = worklist.size();
-                SsaBasicBlock v = worklist.get(wsize - 1);
-                DFSInfo vbbInfo = info[v.getIndex()];
-                SsaBasicBlock vAncestor = vbbInfo.ancestor;
-                DFSInfo vabbInfo = info[vAncestor.getIndex()];
-
-                // Make sure we process our ancestor before ourselves.
-                if (visited.add(vAncestor) && vabbInfo.ancestor != null) {
-                    worklist.add(vAncestor);
-                    continue;
-                }
-                worklist.remove(wsize - 1);
-
-                // Update based on ancestor info.
-                if (vabbInfo.ancestor == null) {
-                    continue;
-                }
-                SsaBasicBlock vAncestorRep = vabbInfo.rep;
-                SsaBasicBlock vRep = vbbInfo.rep;
-                if (info[vAncestorRep.getIndex()].semidom
-                        < info[vRep.getIndex()].semidom) {
-                    vbbInfo.rep = vAncestorRep;
-                }
-                vbbInfo.ancestor = vabbInfo.ancestor;
-            }
-        }
-    }
-
-    private SsaBasicBlock eval(SsaBasicBlock v) {
-        DFSInfo bbInfo = info[v.getIndex()];
-
-        if (bbInfo.ancestor == null) {
-            return v;
-        }
-
-        compress(v);
-        return bbInfo.rep;
-    }
-
-    /**
-     * Performs dominator/post-dominator calculation for the control
-     * flow graph.
-     *
-     * @param meth {@code non-null;} method to analyze
-     */
-    private void run() {
-        SsaBasicBlock root = postdom
-                ? meth.getExitBlock() : meth.getEntryBlock();
-
-        if (root != null) {
-            vertex.add(root);
-            domInfos[root.getIndex()].idom = root.getIndex();
-        }
+      BitSet preds = getPreds(w);
+      for (int j = preds.nextSetBit(0); j >= 0; j = preds.nextSetBit(j + 1)) {
+        SsaBasicBlock predBlock = blocks.get(j);
+        DFSInfo predInfo = info[predBlock.getIndex()];
 
         /*
-         * First we perform a DFS numbering of the blocks, by
-         * numbering the dfs tree roots.
+         * PredInfo may not exist in case the predecessor is
+         * not reachable.
          */
-
-        DfsWalker walker = new DfsWalker();
-        meth.forEachBlockDepthFirst(postdom, walker);
-
-        // the largest semidom number assigned
-        int dfsMax = vertex.size() - 1;
-
-        // Now calculate semidominators.
-        for (int i = dfsMax; i >= 2; --i) {
-            SsaBasicBlock w = vertex.get(i);
-            DFSInfo wInfo = info[w.getIndex()];
-
-            BitSet preds = getPreds(w);
-            for (int j = preds.nextSetBit(0);
-                 j >= 0;
-                 j = preds.nextSetBit(j + 1)) {
-                SsaBasicBlock predBlock = blocks.get(j);
-                DFSInfo predInfo = info[predBlock.getIndex()];
-
-                /*
-                 * PredInfo may not exist in case the predecessor is
-                 * not reachable.
-                 */
-                if (predInfo != null) {
-                    int predSemidom = info[eval(predBlock).getIndex()].semidom;
-                    if (predSemidom < wInfo.semidom) {
-                        wInfo.semidom = predSemidom;
-                    }
-                }
-            }
-            info[vertex.get(wInfo.semidom).getIndex()].bucket.add(w);
-
-            /*
-             * Normally we would call link here, but in our O(m log n)
-             * implementation this is equivalent to the following
-             * single line.
-             */
-            wInfo.ancestor = wInfo.parent;
-
-            // Implicity define idom for each vertex.
-            ArrayList<SsaBasicBlock> wParentBucket;
-            wParentBucket = info[wInfo.parent.getIndex()].bucket;
-
-            while (!wParentBucket.isEmpty()) {
-                int lastItem = wParentBucket.size() - 1;
-                SsaBasicBlock last = wParentBucket.remove(lastItem);
-                SsaBasicBlock U = eval(last);
-                if (info[U.getIndex()].semidom
-                        < info[last.getIndex()].semidom) {
-                    domInfos[last.getIndex()].idom = U.getIndex();
-                } else {
-                    domInfos[last.getIndex()].idom = wInfo.parent.getIndex();
-                }
-            }
+        if (predInfo != null) {
+          int predSemidom = info[eval(predBlock).getIndex()].semidom;
+          if (predSemidom < wInfo.semidom) {
+            wInfo.semidom = predSemidom;
+          }
         }
+      }
+      info[vertex.get(wInfo.semidom).getIndex()].bucket.add(w);
 
-        // Now explicitly define the immediate dominator of each vertex
-        for (int i =  2; i <= dfsMax; ++i) {
-            SsaBasicBlock w = vertex.get(i);
-            if (domInfos[w.getIndex()].idom
-                    != vertex.get(info[w.getIndex()].semidom).getIndex()) {
-                domInfos[w.getIndex()].idom
-                        = domInfos[domInfos[w.getIndex()].idom].idom;
-            }
+      /*
+       * Normally we would call link here, but in our O(m log n)
+       * implementation this is equivalent to the following
+       * single line.
+       */
+      wInfo.ancestor = wInfo.parent;
+
+      // Implicity define idom for each vertex.
+      ArrayList<SsaBasicBlock> wParentBucket;
+      wParentBucket = info[wInfo.parent.getIndex()].bucket;
+
+      while (!wParentBucket.isEmpty()) {
+        int lastItem = wParentBucket.size() - 1;
+        SsaBasicBlock last = wParentBucket.remove(lastItem);
+        SsaBasicBlock u = eval(last);
+        if (info[u.getIndex()].semidom < info[last.getIndex()].semidom) {
+          domInfos[last.getIndex()].idom = u.getIndex();
+        } else {
+          domInfos[last.getIndex()].idom = wInfo.parent.getIndex();
         }
+      }
     }
 
+    // Now explicitly define the immediate dominator of each vertex
+    for (int i = 2; i <= dfsMax; ++i) {
+      SsaBasicBlock w = vertex.get(i);
+      if (domInfos[w.getIndex()].idom != vertex.get(info[w.getIndex()].semidom).getIndex()) {
+        domInfos[w.getIndex()].idom = domInfos[domInfos[w.getIndex()].idom].idom;
+      }
+    }
+  }
+
+  /**
+   * Callback for depth-first walk through control flow graph (either
+   * from the entry block or the exit block). Records the traversal order
+   * in the {@code info}list.
+   */
+  private class DfsWalker implements SsaBasicBlock.Visitor {
+    private int dfsNum = 0;
+
+    @Override
+    public void visitBlock(SsaBasicBlock v, SsaBasicBlock parent) {
+      DFSInfo bbInfo = new DFSInfo();
+      bbInfo.semidom = ++dfsNum;
+      bbInfo.rep = v;
+      bbInfo.parent = parent;
+      vertex.add(v);
+      info[v.getIndex()] = bbInfo;
+    }
+  }
+
+  private static final class DFSInfo {
+    public int semidom;
+    public SsaBasicBlock parent;
+
     /**
-     * Callback for depth-first walk through control flow graph (either
-     * from the entry block or the exit block). Records the traversal order
-     * in the {@code info}list.
+     * rep(resentative) is known as "label" in the paper. It is the node
+     * that our block's DFS info has been unioned to.
      */
-    private class DfsWalker implements SsaBasicBlock.Visitor {
-        private int dfsNum = 0;
+    public SsaBasicBlock rep;
 
-        public void visitBlock(SsaBasicBlock v, SsaBasicBlock parent) {
-            DFSInfo bbInfo = new DFSInfo();
-            bbInfo.semidom = ++dfsNum;
-            bbInfo.rep = v;
-            bbInfo.parent = parent;
-            vertex.add(v);
-            info[v.getIndex()] = bbInfo;
-        }
+    public SsaBasicBlock ancestor;
+    public ArrayList<SsaBasicBlock> bucket;
+
+    public DFSInfo() {
+      bucket = new ArrayList<SsaBasicBlock>();
     }
-
-    private static final class DFSInfo {
-        public int semidom;
-        public SsaBasicBlock parent;
-
-        /**
-         * rep(resentative) is known as "label" in the paper. It is the node
-         * that our block's DFS info has been unioned to.
-         */
-        public SsaBasicBlock rep;
-
-        public SsaBasicBlock ancestor;
-        public ArrayList<SsaBasicBlock> bucket;
-
-        public DFSInfo() {
-            bucket = new ArrayList<SsaBasicBlock>();
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/EscapeAnalysis.java b/dx/src/com/android/jack/dx/ssa/EscapeAnalysis.java
index 791a3b5..6021941 100644
--- a/dx/src/com/android/jack/dx/ssa/EscapeAnalysis.java
+++ b/dx/src/com/android/jack/dx/ssa/EscapeAnalysis.java
@@ -50,794 +50,768 @@
  * the method they are created in and replaces the array values with registers.
  */
 public class EscapeAnalysis {
-    /**
-     * Struct used to generate and maintain escape analysis results.
-     */
-    static class EscapeSet {
-        /** set containing all registers related to an object */
-        BitSet regSet;
-        /** escape state of the object */
-        EscapeState escape;
-        /** list of objects that are put into this object */
-        ArrayList<EscapeSet> childSets;
-        /** list of objects that this object is put into */
-        ArrayList<EscapeSet> parentSets;
-        /** flag to indicate this object is a scalar replaceable array */
-        boolean replaceableArray;
-
-        /**
-         * Constructs an instance of an EscapeSet
-         *
-         * @param reg the SSA register that defines the object
-         * @param size the number of registers in the method
-         * @param escState the lattice value to initially set this to
-         */
-        EscapeSet(int reg, int size, EscapeState escState) {
-            regSet = new BitSet(size);
-            regSet.set(reg);
-            escape = escState;
-            childSets = new ArrayList<EscapeSet>();
-            parentSets = new ArrayList<EscapeSet>();
-            replaceableArray = false;
-        }
-    }
+  /**
+   * Struct used to generate and maintain escape analysis results.
+   */
+  static class EscapeSet {
+    /** set containing all registers related to an object */
+    BitSet regSet;
+    /** escape state of the object */
+    EscapeState escape;
+    /** list of objects that are put into this object */
+    ArrayList<EscapeSet> childSets;
+    /** list of objects that this object is put into */
+    ArrayList<EscapeSet> parentSets;
+    /** flag to indicate this object is a scalar replaceable array */
+    boolean replaceableArray;
 
     /**
-     * Lattice values used to indicate escape state for an object. Analysis can
-     * only raise escape state values, not lower them.
+     * Constructs an instance of an EscapeSet
      *
-     * TOP - Used for objects that haven't been analyzed yet
-     * NONE - Object does not escape, and is eligible for scalar replacement.
-     * METHOD - Object remains local to method, but can't be scalar replaced.
-     * INTER - Object is passed between methods. (treated as globally escaping
-     *         since this is an intraprocedural analysis)
-     * GLOBAL - Object escapes globally.
+     * @param reg the SSA register that defines the object
+     * @param size the number of registers in the method
+     * @param escState the lattice value to initially set this to
      */
-    public enum EscapeState {
-        TOP, NONE, METHOD, INTER, GLOBAL
+    EscapeSet(int reg, int size, EscapeState escState) {
+      regSet = new BitSet(size);
+      regSet.set(reg);
+      escape = escState;
+      childSets = new ArrayList<EscapeSet>();
+      parentSets = new ArrayList<EscapeSet>();
+      replaceableArray = false;
     }
+  }
 
-    /** method we're processing */
-    private SsaMethod ssaMeth;
-    /** ssaMeth.getRegCount() */
-    private int regCount;
-    /** Lattice values for each object register group */
-    private ArrayList<EscapeSet> latticeValues;
+  /**
+   * Lattice values used to indicate escape state for an object. Analysis can
+   * only raise escape state values, not lower them.
+   *
+   * TOP - Used for objects that haven't been analyzed yet
+   * NONE - Object does not escape, and is eligible for scalar replacement.
+   * METHOD - Object remains local to method, but can't be scalar replaced.
+   * INTER - Object is passed between methods. (treated as globally escaping
+   *         since this is an intraprocedural analysis)
+   * GLOBAL - Object escapes globally.
+   */
+  public enum EscapeState {
+    TOP, NONE, METHOD, INTER, GLOBAL
+  }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ssaMeth method to process
-     */
-    private EscapeAnalysis(SsaMethod ssaMeth) {
-        this.ssaMeth = ssaMeth;
-        this.regCount = ssaMeth.getRegCount();
-        this.latticeValues = new ArrayList<EscapeSet>();
-    }
+  /** method we're processing */
+  private SsaMethod ssaMeth;
+  /** ssaMeth.getRegCount() */
+  private int regCount;
+  /** Lattice values for each object register group */
+  private ArrayList<EscapeSet> latticeValues;
 
-    /**
-     * Finds the index in the lattice for a particular register.
-     * Returns the size of the lattice if the register wasn't found.
-     *
-     * @param reg {@code non-null;} register being looked up
-     * @return index of the register or size of the lattice if it wasn't found.
-     */
-    private int findSetIndex(RegisterSpec reg) {
-        int i;
-        for (i = 0; i < latticeValues.size(); i++) {
-            EscapeSet e = latticeValues.get(i);
-            if (e.regSet.get(reg.getReg())) {
-                return i;
-            }
-        }
+  /**
+   * Constructs an instance.
+   *
+   * @param ssaMeth method to process
+   */
+  private EscapeAnalysis(SsaMethod ssaMeth) {
+    this.ssaMeth = ssaMeth;
+    this.regCount = ssaMeth.getRegCount();
+    this.latticeValues = new ArrayList<EscapeSet>();
+  }
+
+  /**
+   * Finds the index in the lattice for a particular register.
+   * Returns the size of the lattice if the register wasn't found.
+   *
+   * @param reg {@code non-null;} register being looked up
+   * @return index of the register or size of the lattice if it wasn't found.
+   */
+  private int findSetIndex(RegisterSpec reg) {
+    int i;
+    for (i = 0; i < latticeValues.size(); i++) {
+      EscapeSet e = latticeValues.get(i);
+      if (e.regSet.get(reg.getReg())) {
         return i;
+      }
     }
+    return i;
+  }
 
-    /**
-     * Finds the corresponding instruction for a given move result
-     *
-     * @param moveInsn {@code non-null;} a move result instruction
-     * @return {@code non-null;} the instruction that produces the result for
-     * the move
-     */
-    private SsaInsn getInsnForMove(SsaInsn moveInsn) {
-        int pred = moveInsn.getBlock().getPredecessors().nextSetBit(0);
-        ArrayList<SsaInsn> predInsns = ssaMeth.getBlocks().get(pred).getInsns();
-        return predInsns.get(predInsns.size()-1);
+  /**
+   * Finds the corresponding instruction for a given move result
+   *
+   * @param moveInsn {@code non-null;} a move result instruction
+   * @return {@code non-null;} the instruction that produces the result for
+   * the move
+   */
+  private SsaInsn getInsnForMove(SsaInsn moveInsn) {
+    int pred = moveInsn.getBlock().getPredecessors().nextSetBit(0);
+    ArrayList<SsaInsn> predInsns = ssaMeth.getBlocks().get(pred).getInsns();
+    return predInsns.get(predInsns.size() - 1);
+  }
+
+  /**
+   * Finds the corresponding move result for a given instruction
+   *
+   * @param insn {@code non-null;} an instruction that must always be
+   * followed by a move result
+   * @return {@code non-null;} the move result for the given instruction
+   */
+  private SsaInsn getMoveForInsn(SsaInsn insn) {
+    int succ = insn.getBlock().getSuccessors().nextSetBit(0);
+    ArrayList<SsaInsn> succInsns = ssaMeth.getBlocks().get(succ).getInsns();
+    return succInsns.get(0);
+  }
+
+  /**
+   * Creates a link in the lattice between two EscapeSets due to a put
+   * instruction. The object being put is the child and the object being put
+   * into is the parent. A child set must always have an escape state at
+   * least as high as its parent.
+   *
+   * @param parentSet {@code non-null;} the EscapeSet for the object being put
+   * into
+   * @param childSet {@code non-null;} the EscapeSet for the object being put
+   */
+  private void addEdge(EscapeSet parentSet, EscapeSet childSet) {
+    if (!childSet.parentSets.contains(parentSet)) {
+      childSet.parentSets.add(parentSet);
     }
-
-    /**
-     * Finds the corresponding move result for a given instruction
-     *
-     * @param insn {@code non-null;} an instruction that must always be
-     * followed by a move result
-     * @return {@code non-null;} the move result for the given instruction
-     */
-    private SsaInsn getMoveForInsn(SsaInsn insn) {
-        int succ = insn.getBlock().getSuccessors().nextSetBit(0);
-        ArrayList<SsaInsn> succInsns = ssaMeth.getBlocks().get(succ).getInsns();
-        return succInsns.get(0);
+    if (!parentSet.childSets.contains(childSet)) {
+      parentSet.childSets.add(childSet);
     }
+  }
 
-    /**
-     * Creates a link in the lattice between two EscapeSets due to a put
-     * instruction. The object being put is the child and the object being put
-     * into is the parent. A child set must always have an escape state at
-     * least as high as its parent.
-     *
-     * @param parentSet {@code non-null;} the EscapeSet for the object being put
-     * into
-     * @param childSet {@code non-null;} the EscapeSet for the object being put
-     */
-    private void addEdge(EscapeSet parentSet, EscapeSet childSet) {
-        if (!childSet.parentSets.contains(parentSet)) {
-            childSet.parentSets.add(parentSet);
+  /**
+   * Merges all links in the lattice among two EscapeSets. On return, the
+   * newNode will have its old links as well as all links from the oldNode.
+   * The oldNode has all its links removed.
+   *
+   * @param newNode {@code non-null;} the EscapeSet to merge all links into
+   * @param oldNode {@code non-null;} the EscapeSet to remove all links from
+   */
+  private void replaceNode(EscapeSet newNode, EscapeSet oldNode) {
+    for (EscapeSet e : oldNode.parentSets) {
+      e.childSets.remove(oldNode);
+      e.childSets.add(newNode);
+      newNode.parentSets.add(e);
+    }
+    for (EscapeSet e : oldNode.childSets) {
+      e.parentSets.remove(oldNode);
+      e.parentSets.add(newNode);
+      newNode.childSets.add(e);
+    }
+  }
+
+  /**
+   * Performs escape analysis on a method. Finds scalar replaceable arrays and
+   * replaces them with equivalent registers.
+   *
+   * @param ssaMethod {@code non-null;} method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    new EscapeAnalysis(ssaMethod).run();
+  }
+
+  /**
+   * Process a single instruction, looking for new objects resulting from
+   * move result or move param.
+   *
+   * @param insn {@code non-null;} instruction to process
+   */
+  private void processInsn(SsaInsn insn) {
+    int op = insn.getOpcode().getOpcode();
+    RegisterSpec result = insn.getResult();
+    EscapeSet escSet;
+
+    // Identify new objects
+    if (op == RegOps.MOVE_RESULT_PSEUDO
+        && result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
+      // Handle objects generated through move_result_pseudo
+      escSet = processMoveResultPseudoInsn(insn);
+      processRegister(result, escSet);
+    } else if (op == RegOps.MOVE_PARAM && result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
+      // Track method arguments that are objects
+      escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
+      latticeValues.add(escSet);
+      processRegister(result, escSet);
+    } else if (op == RegOps.MOVE_RESULT
+        && result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
+      // Track method return values that are objects
+      escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
+      latticeValues.add(escSet);
+      processRegister(result, escSet);
+    }
+  }
+
+  /**
+   * Determine the origin of a move result pseudo instruction that generates
+   * an object. Creates a new EscapeSet for the new object accordingly.
+   *
+   * @param insn {@code non-null;} move result pseudo instruction to process
+   * @return {@code non-null;} an EscapeSet for the object referred to by the
+   * move result pseudo instruction
+   */
+  private EscapeSet processMoveResultPseudoInsn(SsaInsn insn) {
+    RegisterSpec result = insn.getResult();
+    SsaInsn prevSsaInsn = getInsnForMove(insn);
+    int prevOpcode = prevSsaInsn.getOpcode().getOpcode();
+    EscapeSet escSet;
+    RegisterSpec prevSource;
+
+    switch (prevOpcode) {
+    // New instance / Constant
+      case RegOps.NEW_INSTANCE:
+      case RegOps.CONST:
+        escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
+        break;
+      // New array
+      case RegOps.NEW_ARRAY:
+      case RegOps.FILLED_NEW_ARRAY:
+        prevSource = prevSsaInsn.getSources().get(0);
+        if (prevSource.getTypeBearer().isConstant()) {
+          // New fixed array
+          escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
+          escSet.replaceableArray = true;
+        } else {
+          // New variable array
+          escSet = new EscapeSet(result.getReg(), regCount, EscapeState.GLOBAL);
         }
-        if (!parentSet.childSets.contains(childSet)) {
-            parentSet.childSets.add(childSet);
-        }
-    }
+        break;
+      // Loading a static object
+      case RegOps.GET_STATIC:
+        escSet = new EscapeSet(result.getReg(), regCount, EscapeState.GLOBAL);
+        break;
+      // Type cast / load an object from a field or array
+      case RegOps.CHECK_CAST:
+      case RegOps.GET_FIELD:
+      case RegOps.AGET:
+        prevSource = prevSsaInsn.getSources().get(0);
+        int setIndex = findSetIndex(prevSource);
 
-    /**
-     * Merges all links in the lattice among two EscapeSets. On return, the
-     * newNode will have its old links as well as all links from the oldNode.
-     * The oldNode has all its links removed.
-     *
-     * @param newNode {@code non-null;} the EscapeSet to merge all links into
-     * @param oldNode {@code non-null;} the EscapeSet to remove all links from
-     */
-    private void replaceNode(EscapeSet newNode, EscapeSet oldNode) {
-        for (EscapeSet e : oldNode.parentSets) {
-            e.childSets.remove(oldNode);
-            e.childSets.add(newNode);
-            newNode.parentSets.add(e);
-        }
-        for (EscapeSet e : oldNode.childSets) {
-            e.parentSets.remove(oldNode);
-            e.parentSets.add(newNode);
-            newNode.childSets.add(e);
-        }
-    }
-
-    /**
-     * Performs escape analysis on a method. Finds scalar replaceable arrays and
-     * replaces them with equivalent registers.
-     *
-     * @param ssaMethod {@code non-null;} method to process
-     */
-    public static void process(SsaMethod ssaMethod) {
-        new EscapeAnalysis(ssaMethod).run();
-    }
-
-    /**
-     * Process a single instruction, looking for new objects resulting from
-     * move result or move param.
-     *
-     * @param insn {@code non-null;} instruction to process
-     */
-    private void processInsn(SsaInsn insn) {
-        int op = insn.getOpcode().getOpcode();
-        RegisterSpec result = insn.getResult();
-        EscapeSet escSet;
-
-        // Identify new objects
-        if (op == RegOps.MOVE_RESULT_PSEUDO &&
-                result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
-            // Handle objects generated through move_result_pseudo
-            escSet = processMoveResultPseudoInsn(insn);
-            processRegister(result, escSet);
-        } else if (op == RegOps.MOVE_PARAM &&
-                      result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
-            // Track method arguments that are objects
-            escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
-            latticeValues.add(escSet);
-            processRegister(result, escSet);
-        } else if (op == RegOps.MOVE_RESULT &&
-                result.getTypeBearer().getBasicType() == Type.BT_OBJECT) {
-            // Track method return values that are objects
-            escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
-            latticeValues.add(escSet);
-            processRegister(result, escSet);
-        }
-    }
-
-    /**
-     * Determine the origin of a move result pseudo instruction that generates
-     * an object. Creates a new EscapeSet for the new object accordingly.
-     *
-     * @param insn {@code non-null;} move result pseudo instruction to process
-     * @return {@code non-null;} an EscapeSet for the object referred to by the
-     * move result pseudo instruction
-     */
-    private EscapeSet processMoveResultPseudoInsn(SsaInsn insn) {
-        RegisterSpec result = insn.getResult();
-        SsaInsn prevSsaInsn = getInsnForMove(insn);
-        int prevOpcode = prevSsaInsn.getOpcode().getOpcode();
-        EscapeSet escSet;
-        RegisterSpec prevSource;
-
-        switch(prevOpcode) {
-           // New instance / Constant
-            case RegOps.NEW_INSTANCE:
-            case RegOps.CONST:
-                escSet = new EscapeSet(result.getReg(), regCount,
-                                           EscapeState.NONE);
-                break;
-            // New array
-            case RegOps.NEW_ARRAY:
-            case RegOps.FILLED_NEW_ARRAY:
-                prevSource = prevSsaInsn.getSources().get(0);
-                if (prevSource.getTypeBearer().isConstant()) {
-                    // New fixed array
-                    escSet = new EscapeSet(result.getReg(), regCount,
-                                               EscapeState.NONE);
-                    escSet.replaceableArray = true;
-                } else {
-                    // New variable array
-                    escSet = new EscapeSet(result.getReg(), regCount,
-                                               EscapeState.GLOBAL);
-                }
-                break;
-            // Loading a static object
-            case RegOps.GET_STATIC:
-                escSet = new EscapeSet(result.getReg(), regCount,
-                                           EscapeState.GLOBAL);
-                break;
-            // Type cast / load an object from a field or array
-            case RegOps.CHECK_CAST:
-            case RegOps.GET_FIELD:
-            case RegOps.AGET:
-                prevSource = prevSsaInsn.getSources().get(0);
-                int setIndex = findSetIndex(prevSource);
-
-                // Set should already exist, try to find it
-                if (setIndex != latticeValues.size()) {
-                    escSet = latticeValues.get(setIndex);
-                    escSet.regSet.set(result.getReg());
-                    return escSet;
-                }
-
-                // Set not found, must be either null or unknown
-                if (prevSource.getType() == Type.KNOWN_NULL) {
-                    escSet = new EscapeSet(result.getReg(), regCount,
-                                               EscapeState.NONE);
-               } else {
-                    escSet = new EscapeSet(result.getReg(), regCount,
-                                               EscapeState.GLOBAL);
-                }
-                break;
-            default:
-                return null;
-        }
-
-        // Add the newly created escSet to the lattice and return it
-        latticeValues.add(escSet);
-        return escSet;
-    }
-
-    /**
-     * Iterate through all the uses of a new object.
-     *
-     * @param result {@code non-null;} register where new object is stored
-     * @param escSet {@code non-null;} EscapeSet for the new object
-     */
-    private void processRegister(RegisterSpec result, EscapeSet escSet) {
-        ArrayList<RegisterSpec> regWorklist = new ArrayList<RegisterSpec>();
-        regWorklist.add(result);
-
-        // Go through the worklist
-        while (!regWorklist.isEmpty()) {
-            int listSize = regWorklist.size() - 1;
-            RegisterSpec def = regWorklist.remove(listSize);
-            List<SsaInsn> useList = ssaMeth.getUseListForRegister(def.getReg());
-
-            // Handle all the uses of this register
-            for (SsaInsn use : useList) {
-                Rop useOpcode = use.getOpcode();
-
-                if (useOpcode == null) {
-                    // Handle phis
-                    processPhiUse(use, escSet, regWorklist);
-                } else {
-                    // Handle other opcodes
-                    processUse(def, use, escSet, regWorklist);
-                }
-            }
-        }
-    }
-
-    /**
-     * Handles phi uses of new objects. Will merge together the sources of a phi
-     * into a single EscapeSet. Adds the result of the phi to the worklist so
-     * its uses can be followed.
-     *
-     * @param use {@code non-null;} phi use being processed
-     * @param escSet {@code non-null;} EscapeSet for the object
-     * @param regWorklist {@code non-null;} worklist of instructions left to
-     * process for this object
-     */
-    private void processPhiUse(SsaInsn use, EscapeSet escSet,
-                                   ArrayList<RegisterSpec> regWorklist) {
-        int setIndex = findSetIndex(use.getResult());
+        // Set should already exist, try to find it
         if (setIndex != latticeValues.size()) {
-            // Check if result is in a set already
-            EscapeSet mergeSet = latticeValues.get(setIndex);
-            if (mergeSet != escSet) {
-                // If it is, merge the sets and states, then delete the copy
-                escSet.replaceableArray = false;
-                escSet.regSet.or(mergeSet.regSet);
-                if (escSet.escape.compareTo(mergeSet.escape) < 0) {
-                    escSet.escape = mergeSet.escape;
-                }
-                replaceNode(escSet, mergeSet);
-                latticeValues.remove(setIndex);
-            }
+          escSet = latticeValues.get(setIndex);
+          escSet.regSet.set(result.getReg());
+          return escSet;
+        }
+
+        // Set not found, must be either null or unknown
+        if (prevSource.getType() == Type.KNOWN_NULL) {
+          escSet = new EscapeSet(result.getReg(), regCount, EscapeState.NONE);
         } else {
-            // If no set is found, add it to this escSet and the worklist
-            escSet.regSet.set(use.getResult().getReg());
-            regWorklist.add(use.getResult());
+          escSet = new EscapeSet(result.getReg(), regCount, EscapeState.GLOBAL);
         }
+        break;
+      default:
+        return null;
     }
 
-    /**
-     * Handles non-phi uses of new objects. Checks to see how instruction is
-     * used and updates the escape state accordingly.
-     *
-     * @param def {@code non-null;} register holding definition of new object
-     * @param use {@code non-null;} use of object being processed
-     * @param escSet {@code non-null;} EscapeSet for the object
-     * @param regWorklist {@code non-null;} worklist of instructions left to
-     * process for this object
-     */
-    private void processUse(RegisterSpec def, SsaInsn use, EscapeSet escSet,
-                                ArrayList<RegisterSpec> regWorklist) {
-        int useOpcode = use.getOpcode().getOpcode();
-        switch (useOpcode) {
-            case RegOps.MOVE:
-                // Follow uses of the move by adding it to the worklist
-                escSet.regSet.set(use.getResult().getReg());
-                regWorklist.add(use.getResult());
-                break;
-            case RegOps.IF_EQ:
-            case RegOps.IF_NE:
-            case RegOps.CHECK_CAST:
-                // Compared objects can't be replaced, so promote if necessary
-                if (escSet.escape.compareTo(EscapeState.METHOD) < 0) {
-                    escSet.escape = EscapeState.METHOD;
-                }
-                break;
-            case RegOps.APUT:
-                // For array puts, check for a constant array index
-                RegisterSpec putIndex = use.getSources().get(2);
-                if (!putIndex.getTypeBearer().isConstant()) {
-                    // If not constant, array can't be replaced
-                    escSet.replaceableArray = false;
-                }
-                // Intentional fallthrough
-            case RegOps.PUT_FIELD:
-                // Skip non-object puts
-                RegisterSpec putValue = use.getSources().get(0);
-                if (putValue.getTypeBearer().getBasicType() != Type.BT_OBJECT) {
-                    break;
-                }
-                escSet.replaceableArray = false;
+    // Add the newly created escSet to the lattice and return it
+    latticeValues.add(escSet);
+    return escSet;
+  }
 
-                // Raise 1st object's escape state to 2nd if 2nd is higher
-                RegisterSpecList sources = use.getSources();
-                if (sources.get(0).getReg() == def.getReg()) {
-                    int setIndex = findSetIndex(sources.get(1));
-                    if (setIndex != latticeValues.size()) {
-                        EscapeSet parentSet = latticeValues.get(setIndex);
-                        addEdge(parentSet, escSet);
-                        if (escSet.escape.compareTo(parentSet.escape) < 0) {
-                            escSet.escape = parentSet.escape;
-                        }
-                    }
-                } else {
-                    int setIndex = findSetIndex(sources.get(0));
-                    if (setIndex != latticeValues.size()) {
-                        EscapeSet childSet = latticeValues.get(setIndex);
-                        addEdge(escSet, childSet);
-                        if (childSet.escape.compareTo(escSet.escape) < 0) {
-                            childSet.escape = escSet.escape;
-                        }
-                    }
-                }
-                break;
-            case RegOps.AGET:
-                // For array gets, check for a constant array index
-                RegisterSpec getIndex = use.getSources().get(1);
-                if (!getIndex.getTypeBearer().isConstant()) {
-                    // If not constant, array can't be replaced
-                    escSet.replaceableArray = false;
-                }
-                break;
-            case RegOps.PUT_STATIC:
-                // Static puts cause an object to escape globally
-                escSet.escape = EscapeState.GLOBAL;
-                break;
-            case RegOps.INVOKE_STATIC:
-            case RegOps.INVOKE_VIRTUAL:
-            case RegOps.INVOKE_SUPER:
-            case RegOps.INVOKE_DIRECT:
-            case RegOps.INVOKE_INTERFACE:
-            case RegOps.RETURN:
-            case RegOps.THROW:
-                // These operations cause an object to escape interprocedurally
-                escSet.escape = EscapeState.INTER;
-                break;
-            default:
-                break;
+  /**
+   * Iterate through all the uses of a new object.
+   *
+   * @param result {@code non-null;} register where new object is stored
+   * @param escSet {@code non-null;} EscapeSet for the new object
+   */
+  private void processRegister(RegisterSpec result, EscapeSet escSet) {
+    ArrayList<RegisterSpec> regWorklist = new ArrayList<RegisterSpec>();
+    regWorklist.add(result);
+
+    // Go through the worklist
+    while (!regWorklist.isEmpty()) {
+      int listSize = regWorklist.size() - 1;
+      RegisterSpec def = regWorklist.remove(listSize);
+      List<SsaInsn> useList = ssaMeth.getUseListForRegister(def.getReg());
+
+      // Handle all the uses of this register
+      for (SsaInsn use : useList) {
+        Rop useOpcode = use.getOpcode();
+
+        if (useOpcode == null) {
+          // Handle phis
+          processPhiUse(use, escSet, regWorklist);
+        } else {
+          // Handle other opcodes
+          processUse(def, use, escSet, regWorklist);
         }
+      }
     }
+  }
 
-    /**
-     * Performs scalar replacement on all eligible arrays.
-     */
-    private void scalarReplacement() {
-        // Iterate through lattice, looking for non-escaping replaceable arrays
-        for (EscapeSet escSet : latticeValues) {
-            if (!escSet.replaceableArray || escSet.escape != EscapeState.NONE) {
-                continue;
+  /**
+   * Handles phi uses of new objects. Will merge together the sources of a phi
+   * into a single EscapeSet. Adds the result of the phi to the worklist so
+   * its uses can be followed.
+   *
+   * @param use {@code non-null;} phi use being processed
+   * @param escSet {@code non-null;} EscapeSet for the object
+   * @param regWorklist {@code non-null;} worklist of instructions left to
+   * process for this object
+   */
+  private void processPhiUse(SsaInsn use, EscapeSet escSet, ArrayList<RegisterSpec> regWorklist) {
+    int setIndex = findSetIndex(use.getResult());
+    if (setIndex != latticeValues.size()) {
+      // Check if result is in a set already
+      EscapeSet mergeSet = latticeValues.get(setIndex);
+      if (mergeSet != escSet) {
+        // If it is, merge the sets and states, then delete the copy
+        escSet.replaceableArray = false;
+        escSet.regSet.or(mergeSet.regSet);
+        if (escSet.escape.compareTo(mergeSet.escape) < 0) {
+          escSet.escape = mergeSet.escape;
+        }
+        replaceNode(escSet, mergeSet);
+        latticeValues.remove(setIndex);
+      }
+    } else {
+      // If no set is found, add it to this escSet and the worklist
+      escSet.regSet.set(use.getResult().getReg());
+      regWorklist.add(use.getResult());
+    }
+  }
+
+  /**
+   * Handles non-phi uses of new objects. Checks to see how instruction is
+   * used and updates the escape state accordingly.
+   *
+   * @param def {@code non-null;} register holding definition of new object
+   * @param use {@code non-null;} use of object being processed
+   * @param escSet {@code non-null;} EscapeSet for the object
+   * @param regWorklist {@code non-null;} worklist of instructions left to
+   * process for this object
+   */
+  private void processUse(RegisterSpec def, SsaInsn use, EscapeSet escSet,
+      ArrayList<RegisterSpec> regWorklist) {
+    int useOpcode = use.getOpcode().getOpcode();
+    switch (useOpcode) {
+      case RegOps.MOVE:
+        // Follow uses of the move by adding it to the worklist
+        escSet.regSet.set(use.getResult().getReg());
+        regWorklist.add(use.getResult());
+        break;
+      case RegOps.IF_EQ:
+      case RegOps.IF_NE:
+      case RegOps.CHECK_CAST:
+        // Compared objects can't be replaced, so promote if necessary
+        if (escSet.escape.compareTo(EscapeState.METHOD) < 0) {
+          escSet.escape = EscapeState.METHOD;
+        }
+        break;
+      case RegOps.APUT:
+        // For array puts, check for a constant array index
+        RegisterSpec putIndex = use.getSources().get(2);
+        if (!putIndex.getTypeBearer().isConstant()) {
+          // If not constant, array can't be replaced
+          escSet.replaceableArray = false;
+        }
+    // Intentional fallthrough
+      case RegOps.PUT_FIELD:
+        // Skip non-object puts
+        RegisterSpec putValue = use.getSources().get(0);
+        if (putValue.getTypeBearer().getBasicType() != Type.BT_OBJECT) {
+          break;
+        }
+        escSet.replaceableArray = false;
+
+        // Raise 1st object's escape state to 2nd if 2nd is higher
+        RegisterSpecList sources = use.getSources();
+        if (sources.get(0).getReg() == def.getReg()) {
+          int setIndex = findSetIndex(sources.get(1));
+          if (setIndex != latticeValues.size()) {
+            EscapeSet parentSet = latticeValues.get(setIndex);
+            addEdge(parentSet, escSet);
+            if (escSet.escape.compareTo(parentSet.escape) < 0) {
+              escSet.escape = parentSet.escape;
             }
-
-            // Get the instructions for the definition and move of the array
-            int e = escSet.regSet.nextSetBit(0);
-            SsaInsn def = ssaMeth.getDefinitionForRegister(e);
-            SsaInsn prev = getInsnForMove(def);
-
-            // Create a map for the new registers that will be created
-            TypeBearer lengthReg = prev.getSources().get(0).getTypeBearer();
-            int length = ((CstLiteralBits) lengthReg).getIntBits();
-            ArrayList<RegisterSpec> newRegs =
-                new ArrayList<RegisterSpec>(length);
-            HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
-
-            // Replace the definition of the array with registers
-            replaceDef(def, prev, length, newRegs);
-
-            // Mark definition instructions for deletion
-            deletedInsns.add(prev);
-            deletedInsns.add(def);
-
-            // Go through all uses of the array
-            List<SsaInsn> useList = ssaMeth.getUseListForRegister(e);
-            for (SsaInsn use : useList) {
-                // Replace the use with scalars and then mark it for deletion
-                replaceUse(use, prev, newRegs, deletedInsns);
-                deletedInsns.add(use);
+          }
+        } else {
+          int setIndex = findSetIndex(sources.get(0));
+          if (setIndex != latticeValues.size()) {
+            EscapeSet childSet = latticeValues.get(setIndex);
+            addEdge(escSet, childSet);
+            if (childSet.escape.compareTo(escSet.escape) < 0) {
+              childSet.escape = escSet.escape;
             }
-
-            // Delete all marked instructions
-            ssaMeth.deleteInsns(deletedInsns);
-            ssaMeth.onInsnsChanged();
-
-            // Convert the method back to SSA form
-            SsaConverter.updateSsaMethod(ssaMeth, regCount);
-
-            // Propagate and remove extra moves added by scalar replacement
-            movePropagate();
+          }
         }
+        break;
+      case RegOps.AGET:
+        // For array gets, check for a constant array index
+        RegisterSpec getIndex = use.getSources().get(1);
+        if (!getIndex.getTypeBearer().isConstant()) {
+          // If not constant, array can't be replaced
+          escSet.replaceableArray = false;
+        }
+        break;
+      case RegOps.PUT_STATIC:
+        // Static puts cause an object to escape globally
+        escSet.escape = EscapeState.GLOBAL;
+        break;
+      case RegOps.INVOKE_STATIC:
+      case RegOps.INVOKE_VIRTUAL:
+      case RegOps.INVOKE_SUPER:
+      case RegOps.INVOKE_DIRECT:
+      case RegOps.INVOKE_INTERFACE:
+      case RegOps.RETURN:
+      case RegOps.THROW:
+        // These operations cause an object to escape interprocedurally
+        escSet.escape = EscapeState.INTER;
+        break;
+      default:
+        break;
     }
+  }
 
-    /**
-     * Replaces the instructions that define an array with equivalent registers.
-     * For each entry in the array, a register is created, initialized to zero.
-     * A mapping between this register and the corresponding array index is
-     * added.
-     *
-     * @param def {@code non-null;} move result instruction for array
-     * @param prev {@code non-null;} instruction for instantiating new array
-     * @param length size of the new array
-     * @param newRegs {@code non-null;} mapping of array indices to new
-     * registers to be populated
-     */
-    private void replaceDef(SsaInsn def, SsaInsn prev, int length,
-                                ArrayList<RegisterSpec> newRegs) {
-        Type resultType = def.getResult().getType();
+  /**
+   * Performs scalar replacement on all eligible arrays.
+   */
+  private void scalarReplacement() {
+    // Iterate through lattice, looking for non-escaping replaceable arrays
+    for (EscapeSet escSet : latticeValues) {
+      if (!escSet.replaceableArray || escSet.escape != EscapeState.NONE) {
+        continue;
+      }
 
-        // Create new zeroed out registers for each element in the array
+      // Get the instructions for the definition and move of the array
+      int e = escSet.regSet.nextSetBit(0);
+      SsaInsn def = ssaMeth.getDefinitionForRegister(e);
+      SsaInsn prev = getInsnForMove(def);
+
+      // Create a map for the new registers that will be created
+      TypeBearer lengthReg = prev.getSources().get(0).getTypeBearer();
+      int length = ((CstLiteralBits) lengthReg).getIntBits();
+      ArrayList<RegisterSpec> newRegs = new ArrayList<RegisterSpec>(length);
+      HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
+
+      // Replace the definition of the array with registers
+      replaceDef(def, prev, length, newRegs);
+
+      // Mark definition instructions for deletion
+      deletedInsns.add(prev);
+      deletedInsns.add(def);
+
+      // Go through all uses of the array
+      List<SsaInsn> useList = ssaMeth.getUseListForRegister(e);
+      for (SsaInsn use : useList) {
+        // Replace the use with scalars and then mark it for deletion
+        replaceUse(use, prev, newRegs, deletedInsns);
+        deletedInsns.add(use);
+      }
+
+      // Delete all marked instructions
+      ssaMeth.deleteInsns(deletedInsns);
+      ssaMeth.onInsnsChanged();
+
+      // Convert the method back to SSA form
+      SsaConverter.updateSsaMethod(ssaMeth, regCount);
+
+      // Propagate and remove extra moves added by scalar replacement
+      movePropagate();
+    }
+  }
+
+  /**
+   * Replaces the instructions that define an array with equivalent registers.
+   * For each entry in the array, a register is created, initialized to zero.
+   * A mapping between this register and the corresponding array index is
+   * added.
+   *
+   * @param def {@code non-null;} move result instruction for array
+   * @param prev {@code non-null;} instruction for instantiating new array
+   * @param length size of the new array
+   * @param newRegs {@code non-null;} mapping of array indices to new
+   * registers to be populated
+   */
+  private void replaceDef(SsaInsn def, SsaInsn prev, int length, ArrayList<RegisterSpec> newRegs) {
+    Type resultType = def.getResult().getType();
+
+    // Create new zeroed out registers for each element in the array
+    for (int i = 0; i < length; i++) {
+      Constant newZero = Zeroes.zeroFor(resultType.getComponentType());
+      TypedConstant typedZero = (TypedConstant) newZero;
+      RegisterSpec newReg = RegisterSpec.make(ssaMeth.makeNewSsaReg(), typedZero);
+      newRegs.add(newReg);
+      insertPlainInsnBefore(def, RegisterSpecList.EMPTY, newReg, RegOps.CONST, newZero);
+    }
+  }
+
+  /**
+   * Replaces the use for a scalar replaceable array. Gets and puts become
+   * move instructions, and array lengths and fills are handled. Can also
+   * identify ArrayIndexOutOfBounds exceptions and throw them if detected.
+   *
+   * @param use {@code non-null;} move result instruction for array
+   * @param prev {@code non-null;} instruction for instantiating new array
+   * @param newRegs {@code non-null;} mapping of array indices to new
+   * registers
+   * @param deletedInsns {@code non-null;} set of instructions marked for
+   * deletion
+   */
+  private void replaceUse(SsaInsn use, SsaInsn prev, ArrayList<RegisterSpec> newRegs,
+      HashSet<SsaInsn> deletedInsns) {
+    int index;
+    int length = newRegs.size();
+    SsaInsn next;
+    RegisterSpecList sources;
+    RegisterSpec source, result;
+    CstLiteralBits indexReg;
+
+    switch (use.getOpcode().getOpcode()) {
+      case RegOps.AGET:
+        // Replace array gets with moves
+        next = getMoveForInsn(use);
+        sources = use.getSources();
+        indexReg = ((CstLiteralBits) sources.get(1).getTypeBearer());
+        index = indexReg.getIntBits();
+        if (index < length) {
+          source = newRegs.get(index);
+          result = source.withReg(next.getResult().getReg());
+          insertPlainInsnBefore(next, RegisterSpecList.make(source), result, RegOps.MOVE, null);
+        } else {
+          // Throw an exception if the index is out of bounds
+          insertExceptionThrow(next, sources.get(1), deletedInsns);
+          deletedInsns.add(next.getBlock().getInsns().get(2));
+        }
+        deletedInsns.add(next);
+        break;
+      case RegOps.APUT:
+        // Replace array puts with moves
+        sources = use.getSources();
+        indexReg = ((CstLiteralBits) sources.get(2).getTypeBearer());
+        index = indexReg.getIntBits();
+        if (index < length) {
+          source = sources.get(0);
+          result = source.withReg(newRegs.get(index).getReg());
+          insertPlainInsnBefore(use, RegisterSpecList.make(source), result, RegOps.MOVE, null);
+          // Update the newReg entry to mark value as unknown now
+          newRegs.set(index, result.withSimpleType());
+        } else {
+          // Throw an exception if the index is out of bounds
+          insertExceptionThrow(use, sources.get(2), deletedInsns);
+        }
+        break;
+      case RegOps.ARRAY_LENGTH:
+        // Replace array lengths with const instructions
+        TypeBearer lengthReg = prev.getSources().get(0).getTypeBearer();
+        //CstInteger lengthReg = CstInteger.make(length);
+        next = getMoveForInsn(use);
+        insertPlainInsnBefore(next, RegisterSpecList.EMPTY, next.getResult(), RegOps.CONST,
+            (Constant) lengthReg);
+        deletedInsns.add(next);
+        break;
+      case RegOps.MARK_LOCAL:
+        // Remove mark local instructions
+        break;
+      case RegOps.FILL_ARRAY_DATA:
+        // Create const instructions for each fill value
+        Insn ropUse = use.getOriginalRopInsn();
+        FillArrayDataInsn fill = (FillArrayDataInsn) ropUse;
+        ArrayList<Constant> constList = fill.getInitValues();
         for (int i = 0; i < length; i++) {
-            Constant newZero = Zeroes.zeroFor(resultType.getComponentType());
-            TypedConstant typedZero = (TypedConstant) newZero;
-            RegisterSpec newReg =
-                RegisterSpec.make(ssaMeth.makeNewSsaReg(), typedZero);
-            newRegs.add(newReg);
-            insertPlainInsnBefore(def, RegisterSpecList.EMPTY, newReg,
-                                      RegOps.CONST, newZero);
+          RegisterSpec newFill =
+              RegisterSpec.make(newRegs.get(i).getReg(), (TypeBearer) constList.get(i));
+          insertPlainInsnBefore(use, RegisterSpecList.EMPTY, newFill, RegOps.CONST,
+              constList.get(i));
+          // Update the newRegs to hold the new const value
+          newRegs.set(i, newFill);
         }
+        break;
+      default:
     }
+  }
 
-    /**
-     * Replaces the use for a scalar replaceable array. Gets and puts become
-     * move instructions, and array lengths and fills are handled. Can also
-     * identify ArrayIndexOutOfBounds exceptions and throw them if detected.
-     *
-     * @param use {@code non-null;} move result instruction for array
-     * @param prev {@code non-null;} instruction for instantiating new array
-     * @param newRegs {@code non-null;} mapping of array indices to new
-     * registers
-     * @param deletedInsns {@code non-null;} set of instructions marked for
-     * deletion
-     */
-    private void replaceUse(SsaInsn use, SsaInsn prev,
-                                ArrayList<RegisterSpec> newRegs,
-                                HashSet<SsaInsn> deletedInsns) {
-        int index;
-        int length = newRegs.size();
-        SsaInsn next;
-        RegisterSpecList sources;
-        RegisterSpec source, result;
-        CstLiteralBits indexReg;
+  /**
+   * Identifies extra moves added by scalar replacement and propagates the
+   * source of the move to any users of the result.
+   */
+  private void movePropagate() {
+    for (int i = 0; i < ssaMeth.getRegCount(); i++) {
+      SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
 
-        switch (use.getOpcode().getOpcode()) {
-            case RegOps.AGET:
-                // Replace array gets with moves
-                next = getMoveForInsn(use);
-                sources = use.getSources();
-                indexReg = ((CstLiteralBits) sources.get(1).getTypeBearer());
-                index = indexReg.getIntBits();
-                if (index < length) {
-                    source = newRegs.get(index);
-                    result = source.withReg(next.getResult().getReg());
-                    insertPlainInsnBefore(next, RegisterSpecList.make(source),
-                                              result, RegOps.MOVE, null);
-                } else {
-                    // Throw an exception if the index is out of bounds
-                    insertExceptionThrow(next, sources.get(1), deletedInsns);
-                    deletedInsns.add(next.getBlock().getInsns().get(2));
-                }
-                deletedInsns.add(next);
-                break;
-            case RegOps.APUT:
-                // Replace array puts with moves
-                sources = use.getSources();
-                indexReg = ((CstLiteralBits) sources.get(2).getTypeBearer());
-                index = indexReg.getIntBits();
-                if (index < length) {
-                    source = sources.get(0);
-                    result = source.withReg(newRegs.get(index).getReg());
-                    insertPlainInsnBefore(use, RegisterSpecList.make(source),
-                                              result, RegOps.MOVE, null);
-                    // Update the newReg entry to mark value as unknown now
-                    newRegs.set(index, result.withSimpleType());
-                } else {
-                    // Throw an exception if the index is out of bounds
-                    insertExceptionThrow(use, sources.get(2), deletedInsns);
-                }
-                break;
-            case RegOps.ARRAY_LENGTH:
-                // Replace array lengths with const instructions
-                TypeBearer lengthReg = prev.getSources().get(0).getTypeBearer();
-                //CstInteger lengthReg = CstInteger.make(length);
-                next = getMoveForInsn(use);
-                insertPlainInsnBefore(next, RegisterSpecList.EMPTY,
-                                          next.getResult(), RegOps.CONST,
-                                          (Constant) lengthReg);
-                deletedInsns.add(next);
-                break;
-            case RegOps.MARK_LOCAL:
-                // Remove mark local instructions
-                break;
-            case RegOps.FILL_ARRAY_DATA:
-                // Create const instructions for each fill value
-                Insn ropUse = use.getOriginalRopInsn();
-                FillArrayDataInsn fill = (FillArrayDataInsn) ropUse;
-                ArrayList<Constant> constList = fill.getInitValues();
-                for (int i = 0; i < length; i++) {
-                    RegisterSpec newFill =
-                        RegisterSpec.make(newRegs.get(i).getReg(),
-                                              (TypeBearer) constList.get(i));
-                    insertPlainInsnBefore(use, RegisterSpecList.EMPTY, newFill,
-                                              RegOps.CONST, constList.get(i));
-                    // Update the newRegs to hold the new const value
-                    newRegs.set(i, newFill);
-                }
-                break;
-            default:
+      // Look for move instructions only
+      if (insn == null || insn.getOpcode() == null || insn.getOpcode().getOpcode() != RegOps.MOVE) {
+        continue;
+      }
+
+      final ArrayList<SsaInsn>[] useList = ssaMeth.getUseListCopy();
+      final RegisterSpec source = insn.getSources().get(0);
+      final RegisterSpec result = insn.getResult();
+
+      // Ignore moves that weren't added due to scalar replacement
+      if (source.getReg() < regCount && result.getReg() < regCount) {
+        continue;
+      }
+
+      // Create a mapping from source to result
+      RegisterMapper mapper = new RegisterMapper() {
+        @Override
+        public int getNewRegisterCount() {
+          return ssaMeth.getRegCount();
         }
-    }
 
-    /**
-     * Identifies extra moves added by scalar replacement and propagates the
-     * source of the move to any users of the result.
-     */
-    private void movePropagate() {
-        for (int i = 0; i < ssaMeth.getRegCount(); i++) {
-            SsaInsn insn = ssaMeth.getDefinitionForRegister(i);
+        @Override
+        public RegisterSpec map(RegisterSpec registerSpec) {
+          if (registerSpec.getReg() == result.getReg()) {
+            return source;
+          }
 
-            // Look for move instructions only
-            if (insn == null || insn.getOpcode() == null ||
-                insn.getOpcode().getOpcode() != RegOps.MOVE) {
-                continue;
-            }
-
-            final ArrayList<SsaInsn>[] useList = ssaMeth.getUseListCopy();
-            final RegisterSpec source = insn.getSources().get(0);
-            final RegisterSpec result = insn.getResult();
-
-            // Ignore moves that weren't added due to scalar replacement
-            if (source.getReg() < regCount && result.getReg() < regCount) {
-                continue;
-            }
-
-            // Create a mapping from source to result
-            RegisterMapper mapper = new RegisterMapper() {
-                @Override
-                public int getNewRegisterCount() {
-                    return ssaMeth.getRegCount();
-                }
-
-                @Override
-                public RegisterSpec map(RegisterSpec registerSpec) {
-                    if (registerSpec.getReg() == result.getReg()) {
-                        return source;
-                    }
-
-                    return registerSpec;
-                }
-            };
-
-            // Modify all uses of the move to use the source of the move instead
-            for (SsaInsn use : useList[result.getReg()]) {
-                use.mapSourceRegisters(mapper);
-            }
+          return registerSpec;
         }
+      };
+
+      // Modify all uses of the move to use the source of the move instead
+      for (SsaInsn use : useList[result.getReg()]) {
+        use.mapSourceRegisters(mapper);
+      }
     }
+  }
 
-    /**
-     * Runs escape analysis and scalar replacement of arrays.
-     */
-    private void run() {
-        ssaMeth.forEachBlockDepthFirstDom(new SsaBasicBlock.Visitor() {
-            public void visitBlock (SsaBasicBlock block,
-                    SsaBasicBlock unused) {
-                block.forEachInsn(new SsaInsn.Visitor() {
-                    public void visitMoveInsn(NormalSsaInsn insn) {
-                        // do nothing
-                    }
+  /**
+   * Runs escape analysis and scalar replacement of arrays.
+   */
+  private void run() {
+    ssaMeth.forEachBlockDepthFirstDom(new SsaBasicBlock.Visitor() {
+      @Override
+      public void visitBlock(SsaBasicBlock block, SsaBasicBlock unused) {
+        block.forEachInsn(new SsaInsn.Visitor() {
+          @Override
+          public void visitMoveInsn(NormalSsaInsn insn) {
+            // do nothing
+          }
 
-                    public void visitPhiInsn(PhiInsn insn) {
-                        // do nothing
-                    }
+          @Override
+          public void visitPhiInsn(PhiInsn insn) {
+            // do nothing
+          }
 
-                    public void visitNonMoveInsn(NormalSsaInsn insn) {
-                        processInsn(insn);
-                    }
-                });
-            }
+          @Override
+          public void visitNonMoveInsn(NormalSsaInsn insn) {
+            processInsn(insn);
+          }
         });
+      }
+    });
 
-        // Go through lattice and promote fieldSets as necessary
-        for (EscapeSet e : latticeValues) {
-            if (e.escape != EscapeState.NONE) {
-                for (EscapeSet field : e.childSets) {
-                    if (e.escape.compareTo(field.escape) > 0) {
-                        field.escape = e.escape;
-                    }
-                }
-            }
+    // Go through lattice and promote fieldSets as necessary
+    for (EscapeSet e : latticeValues) {
+      if (e.escape != EscapeState.NONE) {
+        for (EscapeSet field : e.childSets) {
+          if (e.escape.compareTo(field.escape) > 0) {
+            field.escape = e.escape;
+          }
         }
-
-        // Perform scalar replacement for arrays
-        scalarReplacement();
+      }
     }
 
-    /**
-     * Replaces instructions that trigger an ArrayIndexOutofBounds exception
-     * with an actual throw of the exception.
-     *
-     * @param insn {@code non-null;} instruction causing the exception
-     * @param index {@code non-null;} index value that is out of bounds
-     * @param deletedInsns {@code non-null;} set of instructions marked for
-     * deletion
-     */
-    private void insertExceptionThrow(SsaInsn insn, RegisterSpec index,
-                                          HashSet<SsaInsn> deletedInsns) {
-        // Create a new ArrayIndexOutOfBoundsException
-        CstType exception =
-            new CstType(Exceptions.TYPE_ArrayIndexOutOfBoundsException);
-        insertThrowingInsnBefore(insn, RegisterSpecList.EMPTY, null,
-                                     RegOps.NEW_INSTANCE, exception);
+    // Perform scalar replacement for arrays
+    scalarReplacement();
+  }
 
-        // Add a successor block with a move result pseudo for the exception
-        SsaBasicBlock currBlock = insn.getBlock();
-        SsaBasicBlock newBlock =
-            currBlock.insertNewSuccessor(currBlock.getPrimarySuccessor());
-        SsaInsn newInsn = newBlock.getInsns().get(0);
-        RegisterSpec newReg =
-            RegisterSpec.make(ssaMeth.makeNewSsaReg(), exception);
-        insertPlainInsnBefore(newInsn, RegisterSpecList.EMPTY, newReg,
-                                  RegOps.MOVE_RESULT_PSEUDO, null);
+  /**
+   * Replaces instructions that trigger an ArrayIndexOutofBounds exception
+   * with an actual throw of the exception.
+   *
+   * @param insn {@code non-null;} instruction causing the exception
+   * @param index {@code non-null;} index value that is out of bounds
+   * @param deletedInsns {@code non-null;} set of instructions marked for
+   * deletion
+   */
+  private void insertExceptionThrow(SsaInsn insn, RegisterSpec index,
+      HashSet<SsaInsn> deletedInsns) {
+    // Create a new ArrayIndexOutOfBoundsException
+    CstType exception = new CstType(Exceptions.TYPE_ArrayIndexOutOfBoundsException);
+    insertThrowingInsnBefore(insn, RegisterSpecList.EMPTY, null, RegOps.NEW_INSTANCE, exception);
 
-        // Add another successor block to initialize the exception
-        SsaBasicBlock newBlock2 =
-            newBlock.insertNewSuccessor(newBlock.getPrimarySuccessor());
-        SsaInsn newInsn2 = newBlock2.getInsns().get(0);
-        CstNat newNat = new CstNat(new CstString("<init>"), new CstString("(I)V"));
-        CstMethodRef newRef = new CstMethodRef(exception, newNat);
-        insertThrowingInsnBefore(newInsn2, RegisterSpecList.make(newReg, index),
-                                     null, RegOps.INVOKE_DIRECT, newRef);
-        deletedInsns.add(newInsn2);
+    // Add a successor block with a move result pseudo for the exception
+    SsaBasicBlock currBlock = insn.getBlock();
+    SsaBasicBlock newBlock = currBlock.insertNewSuccessor(currBlock.getPrimarySuccessor());
+    SsaInsn newInsn = newBlock.getInsns().get(0);
+    RegisterSpec newReg = RegisterSpec.make(ssaMeth.makeNewSsaReg(), exception);
+    insertPlainInsnBefore(newInsn, RegisterSpecList.EMPTY, newReg, RegOps.MOVE_RESULT_PSEUDO, null);
 
-        // Add another successor block to throw the new exception
-        SsaBasicBlock newBlock3 =
-            newBlock2.insertNewSuccessor(newBlock2.getPrimarySuccessor());
-        SsaInsn newInsn3 = newBlock3.getInsns().get(0);
-        insertThrowingInsnBefore(newInsn3, RegisterSpecList.make(newReg), null,
-                                     RegOps.THROW, null);
-        newBlock3.replaceSuccessor(newBlock3.getPrimarySuccessorIndex(),
-                                       ssaMeth.getExitBlock().getIndex());
-        deletedInsns.add(newInsn3);
+    // Add another successor block to initialize the exception
+    SsaBasicBlock newBlock2 = newBlock.insertNewSuccessor(newBlock.getPrimarySuccessor());
+    SsaInsn newInsn2 = newBlock2.getInsns().get(0);
+    CstNat newNat = new CstNat(new CstString("<init>"), new CstString("(I)V"));
+    CstMethodRef newRef = new CstMethodRef(exception, newNat);
+    insertThrowingInsnBefore(newInsn2, RegisterSpecList.make(newReg, index), null,
+        RegOps.INVOKE_DIRECT, newRef);
+    deletedInsns.add(newInsn2);
+
+    // Add another successor block to throw the new exception
+    SsaBasicBlock newBlock3 = newBlock2.insertNewSuccessor(newBlock2.getPrimarySuccessor());
+    SsaInsn newInsn3 = newBlock3.getInsns().get(0);
+    insertThrowingInsnBefore(newInsn3, RegisterSpecList.make(newReg), null, RegOps.THROW, null);
+    newBlock3.replaceSuccessor(newBlock3.getPrimarySuccessorIndex(),
+        ssaMeth.getExitBlock().getIndex());
+    deletedInsns.add(newInsn3);
+  }
+
+  /**
+   * Inserts a new PlainInsn before the given instruction.
+   * TODO(dx team): move this somewhere more appropriate
+   *
+   * @param insn {@code non-null;} instruction to insert before
+   * @param newSources {@code non-null;} sources of new instruction
+   * @param newResult {@code non-null;} result of new instruction
+   * @param newOpcode opcode of new instruction
+   * @param cst {@code null-ok;} constant for new instruction, if any
+   */
+  private void insertPlainInsnBefore(SsaInsn insn, RegisterSpecList newSources,
+      RegisterSpec newResult, int newOpcode, Constant cst) {
+
+    Insn originalRopInsn = insn.getOriginalRopInsn();
+    Rop newRop;
+    if (newOpcode == RegOps.MOVE_RESULT_PSEUDO) {
+      newRop = Rops.opMoveResultPseudo(newResult.getType());
+    } else {
+      newRop = Rops.ropFor(newOpcode, newResult, newSources, cst);
     }
 
-    /**
-     * Inserts a new PlainInsn before the given instruction.
-     * TODO: move this somewhere more appropriate
-     *
-     * @param insn {@code non-null;} instruction to insert before
-     * @param newSources {@code non-null;} sources of new instruction
-     * @param newResult {@code non-null;} result of new instruction
-     * @param newOpcode opcode of new instruction
-     * @param cst {@code null-ok;} constant for new instruction, if any
-     */
-    private void insertPlainInsnBefore(SsaInsn insn,
-        RegisterSpecList newSources, RegisterSpec newResult, int newOpcode,
-        Constant cst) {
-
-        Insn originalRopInsn = insn.getOriginalRopInsn();
-        Rop newRop;
-        if (newOpcode == RegOps.MOVE_RESULT_PSEUDO) {
-            newRop = Rops.opMoveResultPseudo(newResult.getType());
-        } else {
-            newRop = Rops.ropFor(newOpcode, newResult, newSources, cst);
-        }
-
-        Insn newRopInsn;
-        if (cst == null) {
-            newRopInsn = new PlainInsn(newRop,
-                    originalRopInsn.getPosition(), newResult, newSources);
-        } else {
-            newRopInsn = new PlainCstInsn(newRop,
-                originalRopInsn.getPosition(), newResult, newSources, cst);
-        }
-
-        NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
-        List<SsaInsn> insns = insn.getBlock().getInsns();
-
-        insns.add(insns.lastIndexOf(insn), newInsn);
-        ssaMeth.onInsnAdded(newInsn);
+    Insn newRopInsn;
+    if (cst == null) {
+      newRopInsn = new PlainInsn(newRop, originalRopInsn.getPosition(), newResult, newSources);
+    } else {
+      newRopInsn =
+          new PlainCstInsn(newRop, originalRopInsn.getPosition(), newResult, newSources, cst);
     }
 
-    /**
-     * Inserts a new ThrowingInsn before the given instruction.
-     * TODO: move this somewhere more appropriate
-     *
-     * @param insn {@code non-null;} instruction to insert before
-     * @param newSources {@code non-null;} sources of new instruction
-     * @param newResult {@code non-null;} result of new instruction
-     * @param newOpcode opcode of new instruction
-     * @param cst {@code null-ok;} constant for new instruction, if any
-     */
-    private void insertThrowingInsnBefore(SsaInsn insn,
-        RegisterSpecList newSources, RegisterSpec newResult, int newOpcode,
-        Constant cst) {
+    NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
+    List<SsaInsn> insns = insn.getBlock().getInsns();
 
-        Insn origRopInsn = insn.getOriginalRopInsn();
-        Rop newRop = Rops.ropFor(newOpcode, newResult, newSources, cst);
-        Insn newRopInsn;
-        if (cst == null) {
-            newRopInsn = new ThrowingInsn(newRop,
-                origRopInsn.getPosition(), newSources, StdTypeList.EMPTY);
-        } else {
-            newRopInsn = new ThrowingCstInsn(newRop,
-                origRopInsn.getPosition(), newSources, StdTypeList.EMPTY, cst);
-        }
+    insns.add(insns.lastIndexOf(insn), newInsn);
+    ssaMeth.onInsnAdded(newInsn);
+  }
 
-        NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
-        List<SsaInsn> insns = insn.getBlock().getInsns();
+  /**
+   * Inserts a new ThrowingInsn before the given instruction.
+   * TODO(dx team): move this somewhere more appropriate
+   *
+   * @param insn {@code non-null;} instruction to insert before
+   * @param newSources {@code non-null;} sources of new instruction
+   * @param newResult {@code non-null;} result of new instruction
+   * @param newOpcode opcode of new instruction
+   * @param cst {@code null-ok;} constant for new instruction, if any
+   */
+  private void insertThrowingInsnBefore(SsaInsn insn, RegisterSpecList newSources,
+      RegisterSpec newResult, int newOpcode, Constant cst) {
 
-        insns.add(insns.lastIndexOf(insn), newInsn);
-        ssaMeth.onInsnAdded(newInsn);
+    Insn origRopInsn = insn.getOriginalRopInsn();
+    Rop newRop = Rops.ropFor(newOpcode, newResult, newSources, cst);
+    Insn newRopInsn;
+    if (cst == null) {
+      newRopInsn =
+          new ThrowingInsn(newRop, origRopInsn.getPosition(), newSources, StdTypeList.EMPTY);
+    } else {
+      newRopInsn = new ThrowingCstInsn(newRop, origRopInsn.getPosition(), newSources,
+          StdTypeList.EMPTY, cst);
     }
+
+    NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
+    List<SsaInsn> insns = insn.getBlock().getInsns();
+
+    insns.add(insns.lastIndexOf(insn), newInsn);
+    ssaMeth.onInsnAdded(newInsn);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/InterferenceRegisterMapper.java b/dx/src/com/android/jack/dx/ssa/InterferenceRegisterMapper.java
index 589e2f2..0f3f845 100644
--- a/dx/src/com/android/jack/dx/ssa/InterferenceRegisterMapper.java
+++ b/dx/src/com/android/jack/dx/ssa/InterferenceRegisterMapper.java
@@ -23,7 +23,6 @@
 import com.android.jack.dx.util.IntSet;
 
 import java.util.ArrayList;
-import java.util.BitSet;
 
 /**
  * A register mapper that keeps track of the accumulated interference
@@ -33,132 +32,127 @@
  * have variable register widths/categories, and the new namespace does.
  */
 public class InterferenceRegisterMapper extends BasicRegisterMapper {
-    /**
-     * Array of interference sets. ArrayList is indexed by new namespace
-     * and BitIntSet's are indexed by old namespace.  The list expands
-     * as needed and missing items are assumed to interfere with nothing.
-     *
-     * Bit sets are always used here, unlike elsewhere, because the max
-     * size of this matrix will be (countSsaRegs * countRopRegs), which may
-     * grow to hundreds of K but not megabytes.
-     */
-    private final ArrayList<BitIntSet> newRegInterference;
+  /**
+   * Array of interference sets. ArrayList is indexed by new namespace
+   * and BitIntSet's are indexed by old namespace.  The list expands
+   * as needed and missing items are assumed to interfere with nothing.
+   *
+   * Bit sets are always used here, unlike elsewhere, because the max
+   * size of this matrix will be (countSsaRegs * countRopRegs), which may
+   * grow to hundreds of K but not megabytes.
+   */
+  private final ArrayList<BitIntSet> newRegInterference;
 
-    /** the interference graph for the old namespace */
-    private final InterferenceGraph oldRegInterference;
+  /** the interference graph for the old namespace */
+  private final InterferenceGraph oldRegInterference;
 
-    /**
-     * Constructs an instance
-     *
-     * @param countOldRegisters number of registers in old namespace
-     */
-    public InterferenceRegisterMapper(InterferenceGraph oldRegInterference,
-            int countOldRegisters) {
-        super(countOldRegisters);
+  /**
+   * Constructs an instance
+   *
+   * @param countOldRegisters number of registers in old namespace
+   */
+  public InterferenceRegisterMapper(InterferenceGraph oldRegInterference, int countOldRegisters) {
+    super(countOldRegisters);
 
-        newRegInterference = new ArrayList<BitIntSet>();
-        this.oldRegInterference = oldRegInterference;
+    newRegInterference = new ArrayList<BitIntSet>();
+    this.oldRegInterference = oldRegInterference;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void addMapping(int oldReg, int newReg, int category) {
+    super.addMapping(oldReg, newReg, category);
+
+    addInterfence(newReg, oldReg);
+
+    if (category == 2) {
+      addInterfence(newReg + 1, oldReg);
     }
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void addMapping(int oldReg, int newReg, int category) {
-        super.addMapping(oldReg, newReg, category);
+  /**
+   * Checks to see if old namespace reg {@code oldReg} interferes
+   * with what currently maps to {@code newReg}.
+   *
+   * @param oldReg old namespace register
+   * @param newReg new namespace register
+   * @param category category of old namespace register
+   * @return true if oldReg will interfere with newReg
+   */
+  public boolean interferes(int oldReg, int newReg, int category) {
+    if (newReg >= newRegInterference.size()) {
+      return false;
+    } else {
+      IntSet existing = newRegInterference.get(newReg);
 
-        addInterfence(newReg, oldReg);
-
-        if (category == 2) {
-            addInterfence(newReg + 1, oldReg);
-        }
-    }
-
-    /**
-     * Checks to see if old namespace reg {@code oldReg} interferes
-     * with what currently maps to {@code newReg}.
-     *
-     * @param oldReg old namespace register
-     * @param newReg new namespace register
-     * @param category category of old namespace register
-     * @return true if oldReg will interfere with newReg
-     */
-    public boolean interferes(int oldReg, int newReg, int category) {
-        if (newReg >= newRegInterference.size()) {
-            return false;
-        } else {
-            IntSet existing = newRegInterference.get(newReg);
-
-            if (existing == null) {
-                return false;
-            } else if (category == 1) {
-                return existing.has(oldReg);
-            } else {
-                return existing.has(oldReg)
-                        || (interferes(oldReg, newReg+1, category-1));
-            }
-        }
-    }
-
-    /**
-     * Checks to see if old namespace reg {@code oldReg} interferes
-     * with what currently maps to {@code newReg}.
-     *
-     * @param oldSpec {@code non-null;} old namespace register
-     * @param newReg new namespace register
-     * @return true if oldReg will interfere with newReg
-     */
-    public boolean interferes(RegisterSpec oldSpec, int newReg) {
-        return interferes(oldSpec.getReg(), newReg, oldSpec.getCategory());
-    }
-
-    /**
-     * Adds a register's interference set to the interference list,
-     * growing it if necessary.
-     *
-     * @param newReg register in new namespace
-     * @param oldReg register in old namespace
-     */
-    private void addInterfence(int newReg, int oldReg) {
-        newRegInterference.ensureCapacity(newReg + 1);
-
-        while (newReg >= newRegInterference.size()) {
-            newRegInterference.add(new BitIntSet(newReg +1));
-        }
-
-        oldRegInterference.mergeInterferenceSet(
-                oldReg, newRegInterference.get(newReg));
-    }
-
-    /**
-     * Checks to see if any of a set of old-namespace registers are
-     * pinned to the specified new-namespace reg + category. Takes into
-     * account the category of the old-namespace registers.
-     *
-     * @param oldSpecs {@code non-null;} set of old-namespace regs
-     * @param newReg {@code >= 0;} new-namespace register
-     * @param targetCategory {@code 1..2;} the number of adjacent new-namespace
-     * registers (starting at ropReg) to consider
-     * @return true if any of the old-namespace register have been mapped
-     * to the new-namespace register + category
-     */
-    public boolean areAnyPinned(RegisterSpecList oldSpecs,
-            int newReg, int targetCategory) {
-        int sz = oldSpecs.size();
-
-        for (int i = 0; i < sz; i++) {
-            RegisterSpec oldSpec = oldSpecs.get(i);
-            int r = oldToNew(oldSpec.getReg());
-
-            /*
-             * If oldSpec is a category-2 register, then check both newReg
-             * and newReg - 1.
-             */
-            if (r == newReg
-                || (oldSpec.getCategory() == 2 && (r + 1) == newReg)
-                || (targetCategory == 2 && (r == newReg + 1))) {
-                return true;
-            }
-        }
-
+      if (existing == null) {
         return false;
+      } else if (category == 1) {
+        return existing.has(oldReg);
+      } else {
+        return existing.has(oldReg) || (interferes(oldReg, newReg + 1, category - 1));
+      }
     }
+  }
+
+  /**
+   * Checks to see if old namespace reg {@code oldReg} interferes
+   * with what currently maps to {@code newReg}.
+   *
+   * @param oldSpec {@code non-null;} old namespace register
+   * @param newReg new namespace register
+   * @return true if oldReg will interfere with newReg
+   */
+  public boolean interferes(RegisterSpec oldSpec, int newReg) {
+    return interferes(oldSpec.getReg(), newReg, oldSpec.getCategory());
+  }
+
+  /**
+   * Adds a register's interference set to the interference list,
+   * growing it if necessary.
+   *
+   * @param newReg register in new namespace
+   * @param oldReg register in old namespace
+   */
+  private void addInterfence(int newReg, int oldReg) {
+    newRegInterference.ensureCapacity(newReg + 1);
+
+    while (newReg >= newRegInterference.size()) {
+      newRegInterference.add(new BitIntSet(newReg + 1));
+    }
+
+    oldRegInterference.mergeInterferenceSet(oldReg, newRegInterference.get(newReg));
+  }
+
+  /**
+   * Checks to see if any of a set of old-namespace registers are
+   * pinned to the specified new-namespace reg + category. Takes into
+   * account the category of the old-namespace registers.
+   *
+   * @param oldSpecs {@code non-null;} set of old-namespace regs
+   * @param newReg {@code >= 0;} new-namespace register
+   * @param targetCategory {@code 1..2;} the number of adjacent new-namespace
+   * registers (starting at ropReg) to consider
+   * @return true if any of the old-namespace register have been mapped
+   * to the new-namespace register + category
+   */
+  public boolean areAnyPinned(RegisterSpecList oldSpecs, int newReg, int targetCategory) {
+    int sz = oldSpecs.size();
+
+    for (int i = 0; i < sz; i++) {
+      RegisterSpec oldSpec = oldSpecs.get(i);
+      int r = oldToNew(oldSpec.getReg());
+
+      /*
+       * If oldSpec is a category-2 register, then check both newReg
+       * and newReg - 1.
+       */
+      if (r == newReg || (oldSpec.getCategory() == 2 && (r + 1) == newReg)
+          || (targetCategory == 2 && (r == newReg + 1))) {
+        return true;
+      }
+    }
+
+    return false;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/LiteralOpUpgrader.java b/dx/src/com/android/jack/dx/ssa/LiteralOpUpgrader.java
index ebf9401..5bbfdcb 100644
--- a/dx/src/com/android/jack/dx/ssa/LiteralOpUpgrader.java
+++ b/dx/src/com/android/jack/dx/ssa/LiteralOpUpgrader.java
@@ -40,168 +40,163 @@
  */
 public class LiteralOpUpgrader {
 
-    /** method we're processing */
-    private final SsaMethod ssaMeth;
+  /** method we're processing */
+  private final SsaMethod ssaMeth;
 
-    /**
-     * Process a method.
-     *
-     * @param ssaMethod {@code non-null;} method to process
-     */
-    public static void process(SsaMethod ssaMethod) {
-        LiteralOpUpgrader dc;
+  /**
+   * Process a method.
+   *
+   * @param ssaMethod {@code non-null;} method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    LiteralOpUpgrader dc;
 
-        dc = new LiteralOpUpgrader(ssaMethod);
+    dc = new LiteralOpUpgrader(ssaMethod);
 
-        dc.run();
+    dc.run();
+  }
+
+  private LiteralOpUpgrader(SsaMethod ssaMethod) {
+    this.ssaMeth = ssaMethod;
+  }
+
+  /**
+   * Returns true if the register contains an integer 0 or a known-null
+   * object reference
+   *
+   * @param spec non-null spec
+   * @return true for 0 or null type bearers
+   */
+  private static boolean isConstIntZeroOrKnownNull(RegisterSpec spec) {
+    TypeBearer tb = spec.getTypeBearer();
+    if (tb instanceof CstLiteralBits) {
+      CstLiteralBits clb = (CstLiteralBits) tb;
+      return (clb.getLongBits() == 0);
     }
+    return false;
+  }
 
-    private LiteralOpUpgrader(SsaMethod ssaMethod) {
-        this.ssaMeth = ssaMethod;
-    }
+  /**
+   * Run the literal op upgrader
+   */
+  private void run() {
+    final TranslationAdvice advice = Optimizer.getAdvice();
 
-    /**
-     * Returns true if the register contains an integer 0 or a known-null
-     * object reference
-     *
-     * @param spec non-null spec
-     * @return true for 0 or null type bearers
-     */
-    private static boolean isConstIntZeroOrKnownNull(RegisterSpec spec) {
-        TypeBearer tb = spec.getTypeBearer();
-        if (tb instanceof CstLiteralBits) {
-            CstLiteralBits clb = (CstLiteralBits) tb;
-            return (clb.getLongBits() == 0);
-        }
-        return false;
-    }
+    ssaMeth.forEachInsn(new SsaInsn.Visitor() {
+      @Override
+      public void visitMoveInsn(NormalSsaInsn insn) {
+        // do nothing
+      }
 
-    /**
-     * Run the literal op upgrader
-     */
-    private void run() {
-        final TranslationAdvice advice = Optimizer.getAdvice();
+      @Override
+      public void visitPhiInsn(PhiInsn insn) {
+        // do nothing
+      }
 
-        ssaMeth.forEachInsn(new SsaInsn.Visitor() {
-            public void visitMoveInsn(NormalSsaInsn insn) {
-                // do nothing
-            }
+      @Override
+      public void visitNonMoveInsn(NormalSsaInsn insn) {
 
-            public void visitPhiInsn(PhiInsn insn) {
-                // do nothing
-            }
-
-            public void visitNonMoveInsn(NormalSsaInsn insn) {
-
-                Insn originalRopInsn = insn.getOriginalRopInsn();
-                Rop opcode = originalRopInsn.getOpcode();
-                RegisterSpecList sources = insn.getSources();
-
-                // Replace insns with constant results with const insns
-                if (tryReplacingWithConstant(insn)) return;
-
-                if (sources.size() != 2 ) {
-                    // We're only dealing with two-source insns here.
-                    return;
-                }
-
-                if (opcode.getBranchingness() == Rop.BRANCH_IF) {
-                    /*
-                     * An if instruction can become an if-*z instruction.
-                     */
-                    if (isConstIntZeroOrKnownNull(sources.get(0))) {
-                        replacePlainInsn(insn, sources.withoutFirst(),
-                              RegOps.flippedIfOpcode(opcode.getOpcode()), null);
-                    } else if (isConstIntZeroOrKnownNull(sources.get(1))) {
-                        replacePlainInsn(insn, sources.withoutLast(),
-                              opcode.getOpcode(), null);
-                    }
-                } else if (advice.hasConstantOperation(
-                        opcode, sources.get(0), sources.get(1))) {
-                    insn.upgradeToLiteral();
-                } else  if (opcode.isCommutative()
-                        && advice.hasConstantOperation(
-                        opcode, sources.get(1), sources.get(0))) {
-                    /*
-                     * An instruction can be commuted to a literal operation
-                     */
-
-                    insn.setNewSources(
-                            RegisterSpecList.make(
-                                    sources.get(1), sources.get(0)));
-
-                    insn.upgradeToLiteral();
-                }
-            }
-        });
-    }
-
-    /**
-     * Tries to replace an instruction with a const instruction. The given
-     * instruction must have a constant result for it to be replaced.
-     *
-     * @param insn {@code non-null;} instruction to try to replace
-     * @return true if the instruction was replaced
-     */
-    private boolean tryReplacingWithConstant(NormalSsaInsn insn) {
         Insn originalRopInsn = insn.getOriginalRopInsn();
         Rop opcode = originalRopInsn.getOpcode();
-        RegisterSpec result = insn.getResult();
+        RegisterSpecList sources = insn.getSources();
 
-        if (result != null && !ssaMeth.isRegALocal(result) &&
-                opcode.getOpcode() != RegOps.CONST) {
-            TypeBearer type = insn.getResult().getTypeBearer();
-            if (type.isConstant() && type.getBasicType() == Type.BT_INT) {
-                // Replace the instruction with a constant
-                replacePlainInsn(insn, RegisterSpecList.EMPTY,
-                        RegOps.CONST, (Constant) type);
-
-                // Remove the source as well if this is a move-result-pseudo
-                if (opcode.getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
-                    int pred = insn.getBlock().getPredecessors().nextSetBit(0);
-                    ArrayList<SsaInsn> predInsns =
-                            ssaMeth.getBlocks().get(pred).getInsns();
-                    NormalSsaInsn sourceInsn =
-                            (NormalSsaInsn) predInsns.get(predInsns.size()-1);
-                    replacePlainInsn(sourceInsn, RegisterSpecList.EMPTY,
-                            RegOps.GOTO, null);
-                }
-                return true;
-            }
+        // Replace insns with constant results with const insns
+        if (tryReplacingWithConstant(insn)) {
+          return;
         }
-        return false;
-    }
 
-    /**
-     * Replaces an SsaInsn containing a PlainInsn with a new PlainInsn. The
-     * new PlainInsn is constructed with a new RegOp and new sources.
-     *
-     * TODO move this somewhere else.
-     *
-     * @param insn {@code non-null;} an SsaInsn containing a PlainInsn
-     * @param newSources {@code non-null;} new sources list for new insn
-     * @param newOpcode A RegOp from {@link RegOps}
-     * @param cst {@code null-ok;} constant for new instruction, if any
-     */
-    private void replacePlainInsn(NormalSsaInsn insn,
-            RegisterSpecList newSources, int newOpcode, Constant cst) {
-
-        Insn originalRopInsn = insn.getOriginalRopInsn();
-        Rop newRop = Rops.ropFor(newOpcode, insn.getResult(), newSources, cst);
-        Insn newRopInsn;
-        if (cst == null) {
-            newRopInsn = new PlainInsn(newRop, originalRopInsn.getPosition(),
-                    insn.getResult(), newSources);
-        } else {
-            newRopInsn = new PlainCstInsn(newRop, originalRopInsn.getPosition(),
-                    insn.getResult(), newSources, cst);
+        if (sources.size() != 2) {
+          // We're only dealing with two-source insns here.
+          return;
         }
-        NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
 
-        List<SsaInsn> insns = insn.getBlock().getInsns();
+        if (opcode.getBranchingness() == Rop.BRANCH_IF) {
+          /*
+           * An if instruction can become an if-*z instruction.
+           */
+          if (isConstIntZeroOrKnownNull(sources.get(0))) {
+            replacePlainInsn(insn, sources.withoutFirst(),
+                RegOps.flippedIfOpcode(opcode.getOpcode()), null);
+          } else if (isConstIntZeroOrKnownNull(sources.get(1))) {
+            replacePlainInsn(insn, sources.withoutLast(), opcode.getOpcode(), null);
+          }
+        } else if (advice.hasConstantOperation(opcode, sources.get(0), sources.get(1))) {
+          insn.upgradeToLiteral();
+        } else if (opcode.isCommutative()
+            && advice.hasConstantOperation(opcode, sources.get(1), sources.get(0))) {
+          /*
+           * An instruction can be commuted to a literal operation
+           */
 
-        ssaMeth.onInsnRemoved(insn);
-        insns.set(insns.lastIndexOf(insn), newInsn);
-        ssaMeth.onInsnAdded(newInsn);
+insn.setNewSources(RegisterSpecList.make(sources.get(1), sources.get(0)));
+
+          insn.upgradeToLiteral();
+        }
+      }
+    });
+  }
+
+  /**
+   * Tries to replace an instruction with a const instruction. The given
+   * instruction must have a constant result for it to be replaced.
+   *
+   * @param insn {@code non-null;} instruction to try to replace
+   * @return true if the instruction was replaced
+   */
+  private boolean tryReplacingWithConstant(NormalSsaInsn insn) {
+    Insn originalRopInsn = insn.getOriginalRopInsn();
+    Rop opcode = originalRopInsn.getOpcode();
+    RegisterSpec result = insn.getResult();
+
+    if (result != null && !ssaMeth.isRegALocal(result) && opcode.getOpcode() != RegOps.CONST) {
+      TypeBearer type = insn.getResult().getTypeBearer();
+      if (type.isConstant() && type.getBasicType() == Type.BT_INT) {
+        // Replace the instruction with a constant
+        replacePlainInsn(insn, RegisterSpecList.EMPTY, RegOps.CONST, (Constant) type);
+
+        // Remove the source as well if this is a move-result-pseudo
+        if (opcode.getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
+          int pred = insn.getBlock().getPredecessors().nextSetBit(0);
+          ArrayList<SsaInsn> predInsns = ssaMeth.getBlocks().get(pred).getInsns();
+          NormalSsaInsn sourceInsn = (NormalSsaInsn) predInsns.get(predInsns.size() - 1);
+          replacePlainInsn(sourceInsn, RegisterSpecList.EMPTY, RegOps.GOTO, null);
+        }
+        return true;
+      }
     }
+    return false;
+  }
+
+  /**
+   * Replaces an SsaInsn containing a PlainInsn with a new PlainInsn. The
+   * new PlainInsn is constructed with a new RegOp and new sources.
+   *
+   * TODO(dx team) move this somewhere else.
+   *
+   * @param insn {@code non-null;} an SsaInsn containing a PlainInsn
+   * @param newSources {@code non-null;} new sources list for new insn
+   * @param newOpcode A RegOp from {@link RegOps}
+   * @param cst {@code null-ok;} constant for new instruction, if any
+   */
+  private void replacePlainInsn(NormalSsaInsn insn, RegisterSpecList newSources, int newOpcode,
+      Constant cst) {
+
+    Insn originalRopInsn = insn.getOriginalRopInsn();
+    Rop newRop = Rops.ropFor(newOpcode, insn.getResult(), newSources, cst);
+    Insn newRopInsn;
+    if (cst == null) {
+      newRopInsn =
+          new PlainInsn(newRop, originalRopInsn.getPosition(), insn.getResult(), newSources);
+    } else {
+      newRopInsn = new PlainCstInsn(newRop, originalRopInsn.getPosition(), insn.getResult(),
+          newSources, cst);
+    }
+    NormalSsaInsn newInsn = new NormalSsaInsn(newRopInsn, insn.getBlock());
+
+    List<SsaInsn> insns = insn.getBlock().getInsns();
+
+    ssaMeth.onInsnRemoved(insn);
+    insns.set(insns.lastIndexOf(insn), newInsn);
+    ssaMeth.onInsnAdded(newInsn);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/LocalVariableExtractor.java b/dx/src/com/android/jack/dx/ssa/LocalVariableExtractor.java
index a16eeb1..38490ae 100644
--- a/dx/src/com/android/jack/dx/ssa/LocalVariableExtractor.java
+++ b/dx/src/com/android/jack/dx/ssa/LocalVariableExtractor.java
@@ -29,180 +29,172 @@
  * a method. Stolen and retrofitted from
  * com.android.jack.dx.rop.code.LocalVariableExtractor
  *
- * TODO remove this. Allow Rop-form LocalVariableInfo to be passed in,
+ * TODO(dx team) remove this. Allow Rop-form LocalVariableInfo to be passed in,
  * converted, and adapted through edge-splitting.
  */
 public class LocalVariableExtractor {
-    /** {@code non-null;} method being extracted from */
-    private final SsaMethod method;
+  /** {@code non-null;} method being extracted from */
+  private final SsaMethod method;
 
-    /** {@code non-null;} block list for the method */
-    private final ArrayList<SsaBasicBlock> blocks;
+  /** {@code non-null;} block list for the method */
+  private final ArrayList<SsaBasicBlock> blocks;
 
-    /** {@code non-null;} result in-progress */
-    private final LocalVariableInfo resultInfo;
+  /** {@code non-null;} result in-progress */
+  private final LocalVariableInfo resultInfo;
 
-    /** {@code non-null;} work set indicating blocks needing to be processed */
-    private final BitSet workSet;
+  /** {@code non-null;} work set indicating blocks needing to be processed */
+  private final BitSet workSet;
 
-    /**
-     * Extracts out all the local variable information from the given method.
-     *
-     * @param method {@code non-null;} the method to extract from
-     * @return {@code non-null;} the extracted information
-     */
-    public static LocalVariableInfo extract(SsaMethod method) {
-        LocalVariableExtractor lve = new LocalVariableExtractor(method);
-        return lve.doit();
+  /**
+   * Extracts out all the local variable information from the given method.
+   *
+   * @param method {@code non-null;} the method to extract from
+   * @return {@code non-null;} the extracted information
+   */
+  public static LocalVariableInfo extract(SsaMethod method) {
+    LocalVariableExtractor lve = new LocalVariableExtractor(method);
+    return lve.doit();
+  }
+
+  /**
+   * Constructs an instance. This method is private. Use {@link #extract}.
+   *
+   * @param method {@code non-null;} the method to extract from
+   */
+  private LocalVariableExtractor(SsaMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /**
-     * Constructs an instance. This method is private. Use {@link #extract}.
-     *
-     * @param method {@code non-null;} the method to extract from
-     */
-    private LocalVariableExtractor(SsaMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
+    ArrayList<SsaBasicBlock> blocks = method.getBlocks();
 
-        ArrayList<SsaBasicBlock> blocks = method.getBlocks();
+    this.method = method;
+    this.blocks = blocks;
+    this.resultInfo = new LocalVariableInfo(method);
+    this.workSet = new BitSet(blocks.size());
+  }
 
-        this.method = method;
-        this.blocks = blocks;
-        this.resultInfo = new LocalVariableInfo(method);
-        this.workSet = new BitSet(blocks.size());
+  /**
+   * Does the extraction.
+   *
+   * @return {@code non-null;} the extracted information
+   */
+  private LocalVariableInfo doit() {
+
+    //TODO(dx team) why is this needed here?
+    if (method.getRegCount() > 0) {
+      for (int bi = method.getEntryBlockIndex(); bi >= 0; bi = workSet.nextSetBit(0)) {
+        workSet.clear(bi);
+        processBlock(bi);
+      }
     }
 
-    /**
-     * Does the extraction.
-     *
-     * @return {@code non-null;} the extracted information
-     */
-    private LocalVariableInfo doit() {
+    resultInfo.setImmutable();
+    return resultInfo;
+  }
 
-        //FIXME why is this needed here?
-        if (method.getRegCount() > 0 ) {
-            for (int bi = method.getEntryBlockIndex();
-                 bi >= 0;
-                 bi = workSet.nextSetBit(0)) {
-                workSet.clear(bi);
-                processBlock(bi);
-            }
-        }
+  /**
+   * Processes a single block.
+   *
+   * @param blockIndex {@code >= 0;} block index of the block to process
+   */
+  private void processBlock(int blockIndex) {
+    RegisterSpecSet primaryState = resultInfo.mutableCopyOfStarts(blockIndex);
+    SsaBasicBlock block = blocks.get(blockIndex);
+    List<SsaInsn> insns = block.getInsns();
+    int insnSz = insns.size();
 
-        resultInfo.setImmutable();
-        return resultInfo;
+    // The exit block has no insns and no successors
+    if (blockIndex == method.getExitBlockIndex()) {
+      return;
     }
 
-    /**
-     * Processes a single block.
-     *
-     * @param blockIndex {@code >= 0;} block index of the block to process
+    /*
+     * We may have to treat the last instruction specially: If it
+     * can (but doesn't always) throw, and the exception can be
+     * caught within the same method, then we need to use the
+     * state *before* executing it to be what is merged into
+     * exception targets.
      */
-    private void processBlock(int blockIndex) {
-        RegisterSpecSet primaryState
-                = resultInfo.mutableCopyOfStarts(blockIndex);
-        SsaBasicBlock block = blocks.get(blockIndex);
-        List<SsaInsn> insns = block.getInsns();
-        int insnSz = insns.size();
+    SsaInsn lastInsn = insns.get(insnSz - 1);
+    boolean hasExceptionHandlers = lastInsn.getOriginalRopInsn().getCatches().size() != 0;
+    boolean canThrowDuringLastInsn = hasExceptionHandlers && (lastInsn.getResult() != null);
+    int freezeSecondaryStateAt = insnSz - 1;
+    RegisterSpecSet secondaryState = primaryState;
 
-        // The exit block has no insns and no successors
-        if (blockIndex == method.getExitBlockIndex()) {
-            return;
-        }
+    /*
+     * Iterate over the instructions, adding information for each place
+     * that the active variable set changes.
+     */
 
-        /*
-         * We may have to treat the last instruction specially: If it
-         * can (but doesn't always) throw, and the exception can be
-         * caught within the same method, then we need to use the
-         * state *before* executing it to be what is merged into
-         * exception targets.
-         */
-        SsaInsn lastInsn = insns.get(insnSz - 1);
-        boolean hasExceptionHandlers
-                = lastInsn.getOriginalRopInsn().getCatches().size() !=0 ;
-        boolean canThrowDuringLastInsn = hasExceptionHandlers
-                && (lastInsn.getResult() != null);
-        int freezeSecondaryStateAt = insnSz - 1;
-        RegisterSpecSet secondaryState = primaryState;
-
-        /*
-         * Iterate over the instructions, adding information for each place
-         * that the active variable set changes.
-         */
-
-        for (int i = 0; i < insnSz; i++) {
-            if (canThrowDuringLastInsn && (i == freezeSecondaryStateAt)) {
-                // Until this point, primaryState == secondaryState.
-                primaryState.setImmutable();
-                primaryState = primaryState.mutableCopy();
-            }
-
-            SsaInsn insn = insns.get(i);
-            RegisterSpec result;
-
-            result = insn.getLocalAssignment();
-
-            if (result == null) {
-                // We may be nuking an existing local
-
-                result = insn.getResult();
-
-                if (result != null && primaryState.get(result.getReg()) != null) {
-                    primaryState.remove(primaryState.get(result.getReg()));
-                }
-                continue;
-            }
-
-            result = result.withSimpleType();
-
-            RegisterSpec already = primaryState.get(result);
-            /*
-             * The equals() check ensures we only add new info if
-             * the instruction causes a change to the set of
-             * active variables.
-             */
-            if (!result.equals(already)) {
-                /*
-                 * If this insn represents a local moving from one register
-                 * to another, remove the association between the old register
-                 * and the local.
-                 */
-                RegisterSpec previous
-                        = primaryState.localItemToSpec(result.getLocalItem());
-
-                if (previous != null
-                        && (previous.getReg() != result.getReg())) {
-
-                    primaryState.remove(previous);
-                }
-
-                resultInfo.addAssignment(insn, result);
-                primaryState.put(result);
-            }
-        }
-
+for (int i = 0; i < insnSz; i++) {
+      if (canThrowDuringLastInsn && (i == freezeSecondaryStateAt)) {
+        // Until this point, primaryState == secondaryState.
         primaryState.setImmutable();
+        primaryState = primaryState.mutableCopy();
+      }
 
-        /*
-         * Merge this state into the start state for each successor,
-         * and update the work set where required (that is, in cases
-         * where the start state for a block changes).
-         */
+      SsaInsn insn = insns.get(i);
+      RegisterSpec result;
 
-        IntList successors = block.getSuccessorList();
-        int succSz = successors.size();
-        int primarySuccessor = block.getPrimarySuccessorIndex();
+      result = insn.getLocalAssignment();
 
-        for (int i = 0; i < succSz; i++) {
-            int succ = successors.get(i);
-            RegisterSpecSet state = (succ == primarySuccessor) ?
-                primaryState : secondaryState;
+      if (result == null) {
+        // We may be nuking an existing local
 
-            if (resultInfo.mergeStarts(succ, state)) {
-                workSet.set(succ);
-            }
+        result = insn.getResult();
+
+        if (result != null && primaryState.get(result.getReg()) != null) {
+          primaryState.remove(primaryState.get(result.getReg()));
         }
+        continue;
+      }
+
+      result = result.withSimpleType();
+
+      RegisterSpec already = primaryState.get(result);
+      /*
+       * The equals() check ensures we only add new info if
+       * the instruction causes a change to the set of
+       * active variables.
+       */
+      if (!result.equals(already)) {
+        /*
+         * If this insn represents a local moving from one register
+         * to another, remove the association between the old register
+         * and the local.
+         */
+        RegisterSpec previous = primaryState.localItemToSpec(result.getLocalItem());
+
+        if (previous != null && (previous.getReg() != result.getReg())) {
+
+          primaryState.remove(previous);
+        }
+
+        resultInfo.addAssignment(insn, result);
+        primaryState.put(result);
+      }
     }
+
+    primaryState.setImmutable();
+
+    /*
+     * Merge this state into the start state for each successor,
+     * and update the work set where required (that is, in cases
+     * where the start state for a block changes).
+     */
+
+IntList successors = block.getSuccessorList();
+    int succSz = successors.size();
+    int primarySuccessor = block.getPrimarySuccessorIndex();
+
+    for (int i = 0; i < succSz; i++) {
+      int succ = successors.get(i);
+      RegisterSpecSet state = (succ == primarySuccessor) ? primaryState : secondaryState;
+
+      if (resultInfo.mergeStarts(succ, state)) {
+        workSet.set(succ);
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/LocalVariableInfo.java b/dx/src/com/android/jack/dx/ssa/LocalVariableInfo.java
index 0ff957c..8bc7634 100644
--- a/dx/src/com/android/jack/dx/ssa/LocalVariableInfo.java
+++ b/dx/src/com/android/jack/dx/ssa/LocalVariableInfo.java
@@ -28,224 +28,221 @@
  * com.android.jack.dx.ssa.SsaMethod}.
  * Stolen from {@link com.android.jack.dx.rop.code.LocalVariableInfo}.
  */
-public class LocalVariableInfo         extends MutabilityControl {
-    /** {@code >= 0;} the register count for the method */
-    private final int regCount;
+public class LocalVariableInfo extends MutabilityControl {
+  /** {@code >= 0;} the register count for the method */
+  private final int regCount;
 
-    /**
-     * {@code non-null;} {@link com.android.jack.dx.rop.code.RegisterSpecSet} to use when indicating a block
-     * that has no locals; it is empty and immutable but has an appropriate
-     * max size for the method
-     */
-    private final RegisterSpecSet emptySet;
+  /**
+   * {@code non-null;} {@link com.android.jack.dx.rop.code.RegisterSpecSet} to use when indicating a
+   * block that has no locals; it is empty and immutable but has an appropriate max size for the
+   * method
+   */
+  private final RegisterSpecSet emptySet;
 
-    /**
-     * {@code non-null;} array consisting of register sets representing the
-     * sets of variables already assigned upon entry to each block,
-     * where array indices correspond to block indices
-     */
-    private final RegisterSpecSet[] blockStarts;
+  /**
+   * {@code non-null;} array consisting of register sets representing the
+   * sets of variables already assigned upon entry to each block,
+   * where array indices correspond to block indices
+   */
+  private final RegisterSpecSet[] blockStarts;
 
-    /** {@code non-null;} map from instructions to the variable each assigns */
-    private final HashMap<SsaInsn, RegisterSpec> insnAssignments;
+  /** {@code non-null;} map from instructions to the variable each assigns */
+  private final HashMap<SsaInsn, RegisterSpec> insnAssignments;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param method {@code non-null;} the method being represented by this instance
-     */
-    public LocalVariableInfo(SsaMethod method) {
-        if (method == null) {
-            throw new NullPointerException("method == null");
-        }
-
-        List<SsaBasicBlock> blocks = method.getBlocks();
-
-        this.regCount = method.getRegCount();
-        this.emptySet = new RegisterSpecSet(regCount);
-        this.blockStarts = new RegisterSpecSet[blocks.size()];
-        this.insnAssignments =
-            new HashMap<SsaInsn, RegisterSpec>(/*hint here*/);
-
-        emptySet.setImmutable();
+  /**
+   * Constructs an instance.
+   *
+   * @param method {@code non-null;} the method being represented by this instance
+   */
+  public LocalVariableInfo(SsaMethod method) {
+    if (method == null) {
+      throw new NullPointerException("method == null");
     }
 
-    /**
-     * Sets the register set associated with the start of the block with
-     * the given index.
-     *
-     * @param index {@code >= 0;} the block index
-     * @param specs {@code non-null;} the register set to associate with the block
-     */
-    public void setStarts(int index, RegisterSpecSet specs) {
-        throwIfImmutable();
+    List<SsaBasicBlock> blocks = method.getBlocks();
 
-        if (specs == null) {
-            throw new NullPointerException("specs == null");
-        }
+    this.regCount = method.getRegCount();
+    this.emptySet = new RegisterSpecSet(regCount);
+    this.blockStarts = new RegisterSpecSet[blocks.size()];
+    this.insnAssignments = new HashMap<SsaInsn, RegisterSpec>(/*hint here*/);
 
-        try {
-            blockStarts[index] = specs;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus index");
-        }
+    emptySet.setImmutable();
+  }
+
+  /**
+   * Sets the register set associated with the start of the block with
+   * the given index.
+   *
+   * @param index {@code >= 0;} the block index
+   * @param specs {@code non-null;} the register set to associate with the block
+   */
+  public void setStarts(int index, RegisterSpecSet specs) {
+    throwIfImmutable();
+
+    if (specs == null) {
+      throw new NullPointerException("specs == null");
     }
 
-    /**
-     * Merges the given register set into the set for the block with the
-     * given index. If there was not already an associated set, then this
-     * is the same as calling {@link #setStarts}. Otherwise, this will
-     * merge the two sets and call {@link #setStarts} on the result of the
-     * merge.
-     *
-     * @param index {@code >= 0;} the block index
-     * @param specs {@code non-null;} the register set to merge into the start set
-     * for the block
-     * @return {@code true} if the merge resulted in an actual change
-     * to the associated set (including storing one for the first time) or
-     * {@code false} if there was no change
-     */
-    public boolean mergeStarts(int index, RegisterSpecSet specs) {
-        RegisterSpecSet start = getStarts0(index);
-        boolean changed = false;
+    try {
+      blockStarts[index] = specs;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus index");
+    }
+  }
 
-        if (start == null) {
-            setStarts(index, specs);
-            return true;
-        }
+  /**
+   * Merges the given register set into the set for the block with the
+   * given index. If there was not already an associated set, then this
+   * is the same as calling {@link #setStarts}. Otherwise, this will
+   * merge the two sets and call {@link #setStarts} on the result of the
+   * merge.
+   *
+   * @param index {@code >= 0;} the block index
+   * @param specs {@code non-null;} the register set to merge into the start set
+   * for the block
+   * @return {@code true} if the merge resulted in an actual change
+   * to the associated set (including storing one for the first time) or
+   * {@code false} if there was no change
+   */
+  public boolean mergeStarts(int index, RegisterSpecSet specs) {
+    RegisterSpecSet start = getStarts0(index);
 
-        RegisterSpecSet newStart = start.mutableCopy();
-        newStart.intersect(specs, true);
-
-        if (start.equals(newStart)) {
-            return false;
-        }
-
-        newStart.setImmutable();
-        setStarts(index, newStart);
-
-        return true;
+    if (start == null) {
+      setStarts(index, specs);
+      return true;
     }
 
-    /**
-     * Gets the register set associated with the start of the block
-     * with the given index. This returns an empty set with the appropriate
-     * max size if no set was associated with the block in question.
-     *
-     * @param index {@code >= 0;} the block index
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet getStarts(int index) {
-        RegisterSpecSet result = getStarts0(index);
+    RegisterSpecSet newStart = start.mutableCopy();
+    newStart.intersect(specs, true);
 
-        return (result != null) ? result : emptySet;
+    if (start.equals(newStart)) {
+      return false;
     }
 
-    /**
-     * Gets the register set associated with the start of the given
-     * block. This is just convenient shorthand for
-     * {@code getStarts(block.getLabel())}.
-     *
-     * @param block {@code non-null;} the block in question
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet getStarts(SsaBasicBlock block) {
-        return getStarts(block.getIndex());
+    newStart.setImmutable();
+    setStarts(index, newStart);
+
+    return true;
+  }
+
+  /**
+   * Gets the register set associated with the start of the block
+   * with the given index. This returns an empty set with the appropriate
+   * max size if no set was associated with the block in question.
+   *
+   * @param index {@code >= 0;} the block index
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet getStarts(int index) {
+    RegisterSpecSet result = getStarts0(index);
+
+    return (result != null) ? result : emptySet;
+  }
+
+  /**
+   * Gets the register set associated with the start of the given
+   * block. This is just convenient shorthand for
+   * {@code getStarts(block.getLabel())}.
+   *
+   * @param block {@code non-null;} the block in question
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet getStarts(SsaBasicBlock block) {
+    return getStarts(block.getIndex());
+  }
+
+  /**
+   * Gets a mutable copy of the register set associated with the
+   * start of the block with the given index. This returns a
+   * newly-allocated empty {@link RegisterSpecSet} of appropriate
+   * max size if there is not yet any set associated with the block.
+   *
+   * @param index {@code >= 0;} the block index
+   * @return {@code non-null;} the associated register set
+   */
+  public RegisterSpecSet mutableCopyOfStarts(int index) {
+    RegisterSpecSet result = getStarts0(index);
+
+    return (result != null) ? result.mutableCopy() : new RegisterSpecSet(regCount);
+  }
+
+  /**
+   * Adds an assignment association for the given instruction and
+   * register spec. This throws an exception if the instruction
+   * doesn't actually perform a named variable assignment.
+   *
+   * <b>Note:</b> Although the instruction contains its own spec for
+   * the result, it still needs to be passed in explicitly to this
+   * method, since the spec that is stored here should always have a
+   * simple type and the one in the instruction can be an arbitrary
+   * {@link com.android.jack.dx.rop.type.TypeBearer} (such as a constant value).
+   *
+   * @param insn {@code non-null;} the instruction in question
+   * @param spec {@code non-null;} the associated register spec
+   */
+  public void addAssignment(SsaInsn insn, RegisterSpec spec) {
+    throwIfImmutable();
+
+    if (insn == null) {
+      throw new NullPointerException("insn == null");
     }
 
-    /**
-     * Gets a mutable copy of the register set associated with the
-     * start of the block with the given index. This returns a
-     * newly-allocated empty {@link RegisterSpecSet} of appropriate
-     * max size if there is not yet any set associated with the block.
-     *
-     * @param index {@code >= 0;} the block index
-     * @return {@code non-null;} the associated register set
-     */
-    public RegisterSpecSet mutableCopyOfStarts(int index) {
-        RegisterSpecSet result = getStarts0(index);
-
-        return (result != null) ?
-            result.mutableCopy() : new RegisterSpecSet(regCount);
+    if (spec == null) {
+      throw new NullPointerException("spec == null");
     }
 
-    /**
-     * Adds an assignment association for the given instruction and
-     * register spec. This throws an exception if the instruction
-     * doesn't actually perform a named variable assignment.
-     *
-     * <b>Note:</b> Although the instruction contains its own spec for
-     * the result, it still needs to be passed in explicitly to this
-     * method, since the spec that is stored here should always have a
-     * simple type and the one in the instruction can be an arbitrary
-     * {@link com.android.jack.dx.rop.type.TypeBearer} (such as a constant value).
-     *
-     * @param insn {@code non-null;} the instruction in question
-     * @param spec {@code non-null;} the associated register spec
-     */
-    public void addAssignment(SsaInsn insn, RegisterSpec spec) {
-        throwIfImmutable();
+    insnAssignments.put(insn, spec);
+  }
 
-        if (insn == null) {
-            throw new NullPointerException("insn == null");
-        }
+  /**
+   * Gets the named register being assigned by the given instruction, if
+   * previously stored in this instance.
+   *
+   * @param insn {@code non-null;} instruction in question
+   * @return {@code null-ok;} the named register being assigned, if any
+   */
+  public RegisterSpec getAssignment(SsaInsn insn) {
+    return insnAssignments.get(insn);
+  }
 
-        if (spec == null) {
-            throw new NullPointerException("spec == null");
-        }
+  /**
+   * Gets the number of assignments recorded by this instance.
+   *
+   * @return {@code >= 0;} the number of assignments
+   */
+  public int getAssignmentCount() {
+    return insnAssignments.size();
+  }
 
-        insnAssignments.put(insn, spec);
+  public void debugDump() {
+    for (int index = 0; index < blockStarts.length; index++) {
+      if (blockStarts[index] == null) {
+        continue;
+      }
+
+      if (blockStarts[index] == emptySet) {
+        System.out.printf("%04x: empty set\n", index);
+      } else {
+        System.out.printf("%04x: %s\n", index, blockStarts[index]);
+      }
     }
+  }
 
-    /**
-     * Gets the named register being assigned by the given instruction, if
-     * previously stored in this instance.
-     *
-     * @param insn {@code non-null;} instruction in question
-     * @return {@code null-ok;} the named register being assigned, if any
-     */
-    public RegisterSpec getAssignment(SsaInsn insn) {
-        return insnAssignments.get(insn);
+  /**
+   * Helper method, to get the starts for a index, throwing the
+   * right exception for range problems.
+   *
+   * @param index {@code >= 0;} the block index
+   * @return {@code null-ok;} associated register set or {@code null} if there
+   * is none
+   */
+  private RegisterSpecSet getStarts0(int index) {
+    try {
+      return blockStarts[index];
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("bogus index");
     }
-
-    /**
-     * Gets the number of assignments recorded by this instance.
-     *
-     * @return {@code >= 0;} the number of assignments
-     */
-    public int getAssignmentCount() {
-        return insnAssignments.size();
-    }
-
-    public void debugDump() {
-        for (int index = 0 ; index < blockStarts.length; index++) {
-            if (blockStarts[index] == null) {
-                continue;
-            }
-
-            if (blockStarts[index] == emptySet) {
-                System.out.printf("%04x: empty set\n", index);
-            } else {
-                System.out.printf("%04x: %s\n", index, blockStarts[index]);
-            }
-        }
-    }
-
-    /**
-     * Helper method, to get the starts for a index, throwing the
-     * right exception for range problems.
-     *
-     * @param index {@code >= 0;} the block index
-     * @return {@code null-ok;} associated register set or {@code null} if there
-     * is none
-     */
-    private RegisterSpecSet getStarts0(int index) {
-        try {
-            return blockStarts[index];
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("bogus index");
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/MoveParamCombiner.java b/dx/src/com/android/jack/dx/ssa/MoveParamCombiner.java
index dc05a6e..95fc869 100644
--- a/dx/src/com/android/jack/dx/ssa/MoveParamCombiner.java
+++ b/dx/src/com/android/jack/dx/ssa/MoveParamCombiner.java
@@ -23,7 +23,6 @@
 import com.android.jack.dx.rop.cst.CstInteger;
 
 import java.util.HashSet;
-import java.util.ArrayList;
 import java.util.List;
 
 /**
@@ -32,125 +31,127 @@
  */
 public class MoveParamCombiner {
 
-    /** method to process */
-    private final SsaMethod ssaMeth;
+  /** method to process */
+  private final SsaMethod ssaMeth;
 
-    /**
-     * Processes a method with this optimization step.
-     *
-     * @param ssaMethod method to process
-     */
-    public static void process(SsaMethod ssaMethod) {
-        new MoveParamCombiner(ssaMethod).run();
-    }
+  /**
+   * Processes a method with this optimization step.
+   *
+   * @param ssaMethod method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    new MoveParamCombiner(ssaMethod).run();
+  }
 
-    private MoveParamCombiner(SsaMethod ssaMeth) {
-        this.ssaMeth = ssaMeth;
-    }
+  private MoveParamCombiner(SsaMethod ssaMeth) {
+    this.ssaMeth = ssaMeth;
+  }
 
-    /**
-     * Runs this optimization step.
-     */
-    private void run() {
-        // This will contain the definition specs for each parameter
-        final RegisterSpec[] paramSpecs
-                = new RegisterSpec[ssaMeth.getParamWidth()];
+  /**
+   * Runs this optimization step.
+   */
+  private void run() {
+    // This will contain the definition specs for each parameter
+    final RegisterSpec[] paramSpecs = new RegisterSpec[ssaMeth.getParamWidth()];
 
-        // Insns to delete when all done
-        final HashSet<SsaInsn> deletedInsns = new HashSet();
+    // Insns to delete when all done
+    final HashSet<SsaInsn> deletedInsns = new HashSet<SsaInsn>();
 
-        ssaMeth.forEachInsn(new SsaInsn.Visitor() {
-            public void visitMoveInsn (NormalSsaInsn insn) {
+    ssaMeth.forEachInsn(new SsaInsn.Visitor() {
+      @Override
+      public void visitMoveInsn(NormalSsaInsn insn) {}
+
+      @Override
+      public void visitPhiInsn(PhiInsn phi) {}
+
+      @Override
+      public void visitNonMoveInsn(NormalSsaInsn insn) {
+        if (insn.getOpcode().getOpcode() != RegOps.MOVE_PARAM) {
+          return;
+        }
+
+        int param = getParamIndex(insn);
+
+        if (paramSpecs[param] == null) {
+          paramSpecs[param] = insn.getResult();
+        } else {
+          final RegisterSpec specA = paramSpecs[param];
+          final RegisterSpec specB = insn.getResult();
+          LocalItem localA = specA.getLocalItem();
+          LocalItem localB = specB.getLocalItem();
+          LocalItem newLocal;
+
+          /*
+           * Is there local information to preserve?
+           */
+
+if (localA == null) {
+            newLocal = localB;
+          } else if (localB == null) {
+            newLocal = localA;
+          } else if (localA.equals(localB)) {
+            newLocal = localA;
+          } else {
+            /*
+             * Oddly, these two identical move-params have distinct
+             * debug info. We'll just keep them distinct.
+             */
+            return;
+          }
+
+          ssaMeth.getDefinitionForRegister(specA.getReg()).setResultLocal(newLocal);
+
+          /*
+           * Map all uses of specB to specA
+           */
+
+RegisterMapper mapper = new RegisterMapper() {
+            /** @inheritDoc */
+            @Override
+            public int getNewRegisterCount() {
+              return ssaMeth.getRegCount();
             }
-            public void visitPhiInsn (PhiInsn phi) {
+
+            /** @inheritDoc */
+            @Override
+            public RegisterSpec map(RegisterSpec registerSpec) {
+              if (registerSpec.getReg() == specB.getReg()) {
+                return specA;
+              }
+
+              return registerSpec;
             }
-            public void visitNonMoveInsn (NormalSsaInsn insn) {
-                if (insn.getOpcode().getOpcode() != RegOps.MOVE_PARAM) {
-                    return;
-                }
+          };
 
-                int param = getParamIndex(insn);
+          List<SsaInsn> uses = ssaMeth.getUseListForRegister(specB.getReg());
 
-                if (paramSpecs[param] == null) {
-                    paramSpecs[param] = insn.getResult();
-                } else {
-                    final RegisterSpec specA = paramSpecs[param];
-                    final RegisterSpec specB = insn.getResult();
-                    LocalItem localA = specA.getLocalItem();
-                    LocalItem localB = specB.getLocalItem();
-                    LocalItem newLocal;
+          // Use list is modified by mapSourceRegisters
+          for (int i = uses.size() - 1; i >= 0; i--) {
+            SsaInsn use = uses.get(i);
+            use.mapSourceRegisters(mapper);
+          }
 
-                    /*
-                     * Is there local information to preserve?
-                     */
+          deletedInsns.add(insn);
+        }
 
-                    if (localA == null) {
-                        newLocal = localB;
-                    } else if (localB == null) {
-                        newLocal = localA;
-                    } else if (localA.equals(localB)) {
-                        newLocal = localA;
-                    } else {
-                        /*
-                         * Oddly, these two identical move-params have distinct
-                         * debug info. We'll just keep them distinct.
-                         */
-                        return;
-                    }
+      }
+    });
 
-                    ssaMeth.getDefinitionForRegister(specA.getReg())
-                            .setResultLocal(newLocal);
+    ssaMeth.deleteInsns(deletedInsns);
+  }
 
-                    /*
-                     * Map all uses of specB to specA
-                     */
+  /**
+   * Returns the parameter index associated with a move-param insn. Does
+   * not verify that the insn is a move-param insn.
+   *
+   * @param insn {@code non-null;} a move-param insn
+   * @return {@code >=0;} parameter index
+   */
+  private int getParamIndex(NormalSsaInsn insn) {
+    CstInsn cstInsn = (CstInsn) (insn.getOriginalRopInsn());
 
-                    RegisterMapper mapper = new RegisterMapper() {
-                        /** @inheritDoc */
-                        public int getNewRegisterCount() {
-                            return ssaMeth.getRegCount();
-                        }
-
-                        /** @inheritDoc */
-                        public RegisterSpec map(RegisterSpec registerSpec) {
-                            if (registerSpec.getReg() == specB.getReg()) {
-                                return specA;
-                            }
-
-                            return registerSpec;
-                        }
-                    };
-
-                    List<SsaInsn> uses
-                            = ssaMeth.getUseListForRegister(specB.getReg());
-
-                    // Use list is modified by mapSourceRegisters
-                    for (int i = uses.size() - 1; i >= 0; i--) {
-                        SsaInsn use = uses.get(i);
-                        use.mapSourceRegisters(mapper);
-                    }
-
-                    deletedInsns.add(insn);
-                }
-
-            }
-        });
-
-        ssaMeth.deleteInsns(deletedInsns);
-    }
-
-    /**
-     * Returns the parameter index associated with a move-param insn. Does
-     * not verify that the insn is a move-param insn.
-     *
-     * @param insn {@code non-null;} a move-param insn
-     * @return {@code >=0;} parameter index
-     */
-    private int getParamIndex(NormalSsaInsn insn) {
-        CstInsn cstInsn = (CstInsn)(insn.getOriginalRopInsn());
-
-        int param = ((CstInteger)cstInsn.getConstant()).getValue();
-        return param;
-    }
+    int param = ((CstInteger) cstInsn.getConstant()).getValue();
+    return param;
+  }
 
 }
diff --git a/dx/src/com/android/jack/dx/ssa/NormalSsaInsn.java b/dx/src/com/android/jack/dx/ssa/NormalSsaInsn.java
index c669566..b62e554 100644
--- a/dx/src/com/android/jack/dx/ssa/NormalSsaInsn.java
+++ b/dx/src/com/android/jack/dx/ssa/NormalSsaInsn.java
@@ -16,221 +16,226 @@
 
 package com.android.jack.dx.ssa;
 
-import com.android.jack.dx.rop.code.*;
+import com.android.jack.dx.rop.code.Insn;
+import com.android.jack.dx.rop.code.LocalItem;
+import com.android.jack.dx.rop.code.RegOps;
+import com.android.jack.dx.rop.code.RegisterSpec;
+import com.android.jack.dx.rop.code.RegisterSpecList;
+import com.android.jack.dx.rop.code.Rop;
 
 /**
  * A "normal" (non-phi) instruction in SSA form. Always wraps a rop insn.
  */
 public final class NormalSsaInsn extends SsaInsn implements Cloneable {
-    /** {@code non-null;} rop insn that we're wrapping */
-    private Insn insn;
+  /** {@code non-null;} rop insn that we're wrapping */
+  private Insn insn;
 
-    /**
-     * Creates an instance.
-     *
-     * @param insn Rop insn to wrap
-     * @param block block that contains this insn
-     */
-    NormalSsaInsn(final Insn insn, final SsaBasicBlock block) {
-        super(insn.getResult(), block);
-        this.insn = insn;
+  /**
+   * Creates an instance.
+   *
+   * @param insn Rop insn to wrap
+   * @param block block that contains this insn
+   */
+  NormalSsaInsn(final Insn insn, final SsaBasicBlock block) {
+    super(insn.getResult(), block);
+    this.insn = insn;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final void mapSourceRegisters(RegisterMapper mapper) {
+    RegisterSpecList oldSources = insn.getSources();
+    RegisterSpecList newSources = mapper.map(oldSources);
+
+    if (newSources != oldSources) {
+      insn = insn.withNewRegisters(getResult(), newSources);
+      getBlock().getParent().onSourcesChanged(this, oldSources);
+    }
+  }
+
+  /**
+   * Changes one of the insn's sources. New source should be of same type
+   * and category.
+   *
+   * @param index {@code >=0;} index of source to change
+   * @param newSpec spec for new source
+   */
+  public final void changeOneSource(int index, RegisterSpec newSpec) {
+    RegisterSpecList origSources = insn.getSources();
+    int sz = origSources.size();
+    RegisterSpecList newSources = new RegisterSpecList(sz);
+
+    for (int i = 0; i < sz; i++) {
+      newSources.set(i, i == index ? newSpec : origSources.get(i));
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final void mapSourceRegisters(RegisterMapper mapper) {
-        RegisterSpecList oldSources = insn.getSources();
-        RegisterSpecList newSources = mapper.map(oldSources);
+    newSources.setImmutable();
 
-        if (newSources != oldSources) {
-            insn = insn.withNewRegisters(getResult(), newSources);
-            getBlock().getParent().onSourcesChanged(this, oldSources);
-        }
+    RegisterSpec origSpec = origSources.get(index);
+    if (origSpec.getReg() != newSpec.getReg()) {
+      /*
+       * If the register remains unchanged, we're only changing
+       * the type or local var name so don't update use list
+       */
+      getBlock().getParent().onSourceChanged(this, origSpec, newSpec);
     }
 
-    /**
-     * Changes one of the insn's sources. New source should be of same type
-     * and category.
-     *
-     * @param index {@code >=0;} index of source to change
-     * @param newSpec spec for new source
-     */
-    public final void changeOneSource(int index, RegisterSpec newSpec) {
-        RegisterSpecList origSources = insn.getSources();
-        int sz = origSources.size();
-        RegisterSpecList newSources = new RegisterSpecList(sz);
+    insn = insn.withNewRegisters(getResult(), newSources);
+  }
 
-        for (int i = 0; i < sz; i++) {
-            newSources.set(i, i == index ? newSpec : origSources.get(i));
-        }
+  /**
+   * Changes the source list of the insn. New source list should be the
+   * same size and consist of sources of identical types.
+   *
+   * @param newSources non-null new sources list.
+   */
+  public final void setNewSources(RegisterSpecList newSources) {
+    RegisterSpecList origSources = insn.getSources();
 
-        newSources.setImmutable();
-
-        RegisterSpec origSpec = origSources.get(index);
-        if (origSpec.getReg() != newSpec.getReg()) {
-            /*
-             * If the register remains unchanged, we're only changing
-             * the type or local var name so don't update use list
-             */
-            getBlock().getParent().onSourceChanged(this, origSpec, newSpec);
-        }
-
-        insn = insn.withNewRegisters(getResult(), newSources);
+    if (origSources.size() != newSources.size()) {
+      throw new RuntimeException("Sources counts don't match");
     }
 
-    /**
-     * Changes the source list of the insn. New source list should be the
-     * same size and consist of sources of identical types.
-     *
-     * @param newSources non-null new sources list.
-     */
-    public final void setNewSources (RegisterSpecList newSources) {
-        RegisterSpecList origSources = insn.getSources();
+    insn = insn.withNewRegisters(getResult(), newSources);
+  }
 
-        if (origSources.size() != newSources.size()) {
-            throw new RuntimeException("Sources counts don't match");
-        }
+  /** {@inheritDoc} */
+  @Override
+  public NormalSsaInsn clone() {
+    return (NormalSsaInsn) super.clone();
+  }
 
-        insn = insn.withNewRegisters(getResult(), newSources);
+  /**
+   * Like rop.Insn.getSources().
+   *
+   * @return {@code null-ok;} sources list
+   */
+  @Override
+  public RegisterSpecList getSources() {
+    return insn.getSources();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return toRopInsn().toHuman();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn toRopInsn() {
+    return insn.withNewRegisters(getResult(), insn.getSources());
+  }
+
+  /**
+   * @return the Rop opcode for this insn
+   */
+  @Override
+  public Rop getOpcode() {
+    return insn.getOpcode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public Insn getOriginalRopInsn() {
+    return insn;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public RegisterSpec getLocalAssignment() {
+    RegisterSpec assignment;
+
+    if (insn.getOpcode().getOpcode() == RegOps.MARK_LOCAL) {
+      assignment = insn.getSources().get(0);
+    } else {
+      assignment = getResult();
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public NormalSsaInsn clone() {
-        return (NormalSsaInsn) super.clone();
+    if (assignment == null) {
+      return null;
     }
 
-    /**
-     * Like rop.Insn.getSources().
-     *
-     * @return {@code null-ok;} sources list
-     */
-    @Override
-    public RegisterSpecList getSources() {
-        return insn.getSources();
+    LocalItem local = assignment.getLocalItem();
+
+    if (local == null) {
+      return null;
     }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return toRopInsn().toHuman();
+    return assignment;
+  }
+
+  /**
+   * Upgrades this insn to a version that represents the constant source
+   * literally. If the upgrade is not possible, this does nothing.
+   *
+   * @see Insn#withSourceLiteral
+   */
+  public void upgradeToLiteral() {
+    RegisterSpecList oldSources = insn.getSources();
+
+    insn = insn.withSourceLiteral();
+    getBlock().getParent().onSourcesChanged(this, oldSources);
+  }
+
+  /**
+   * @return true if this is a move (but not a move-operand) instruction
+   */
+  @Override
+  public boolean isNormalMoveInsn() {
+    return insn.getOpcode().getOpcode() == RegOps.MOVE;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isMoveException() {
+    return insn.getOpcode().getOpcode() == RegOps.MOVE_EXCEPTION;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean canThrow() {
+    return insn.canThrow();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void accept(Visitor v) {
+    if (isNormalMoveInsn()) {
+      v.visitMoveInsn(this);
+    } else {
+      v.visitNonMoveInsn(this);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isPhiOrMove() {
+    return isNormalMoveInsn();
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * TODO(dx team): Increase the scope of this.
+   */
+  @Override
+  public boolean hasSideEffect() {
+    Rop opcode = getOpcode();
+
+    if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
+      return true;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public Insn toRopInsn() {
-        return insn.withNewRegisters(getResult(), insn.getSources());
+    boolean hasLocalSideEffect = Optimizer.getPreserveLocals() && getLocalAssignment() != null;
+
+    switch (opcode.getOpcode()) {
+      case RegOps.MOVE_RESULT:
+      case RegOps.MOVE:
+      case RegOps.CONST:
+        return hasLocalSideEffect;
+      default:
+        return true;
     }
-
-    /**
-     * @return the Rop opcode for this insn
-     */
-    @Override
-    public Rop getOpcode() {
-        return insn.getOpcode();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public Insn getOriginalRopInsn() {
-        return insn;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public RegisterSpec getLocalAssignment() {
-        RegisterSpec assignment;
-
-        if (insn.getOpcode().getOpcode() == RegOps.MARK_LOCAL) {
-            assignment = insn.getSources().get(0);
-        } else {
-            assignment = getResult();
-        }
-
-        if (assignment == null) {
-            return null;
-        }
-
-        LocalItem local = assignment.getLocalItem();
-
-        if (local == null) {
-            return null;
-        }
-
-        return assignment;
-    }
-
-    /**
-     * Upgrades this insn to a version that represents the constant source
-     * literally. If the upgrade is not possible, this does nothing.
-     *
-     * @see Insn#withSourceLiteral
-     */
-    public void upgradeToLiteral() {
-        RegisterSpecList oldSources = insn.getSources();
-
-        insn = insn.withSourceLiteral();
-        getBlock().getParent().onSourcesChanged(this, oldSources);
-    }
-
-    /**
-     * @return true if this is a move (but not a move-operand) instruction
-     */
-    @Override
-    public boolean isNormalMoveInsn() {
-        return insn.getOpcode().getOpcode() == RegOps.MOVE;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isMoveException() {
-        return insn.getOpcode().getOpcode() == RegOps.MOVE_EXCEPTION;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean canThrow() {
-        return insn.canThrow();
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void accept(Visitor v) {
-        if (isNormalMoveInsn()) {
-            v.visitMoveInsn(this);
-        } else {
-            v.visitNonMoveInsn(this);
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public  boolean isPhiOrMove() {
-        return isNormalMoveInsn();
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * TODO: Increase the scope of this.
-     */
-    @Override
-    public boolean hasSideEffect() {
-        Rop opcode = getOpcode();
-
-        if (opcode.getBranchingness() != Rop.BRANCH_NONE) {
-            return true;
-        }
-
-        boolean hasLocalSideEffect
-            = Optimizer.getPreserveLocals() && getLocalAssignment() != null;
-
-        switch (opcode.getOpcode()) {
-            case RegOps.MOVE_RESULT:
-            case RegOps.MOVE:
-            case RegOps.CONST:
-                return hasLocalSideEffect;
-            default:
-                return true;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/Optimizer.java b/dx/src/com/android/jack/dx/ssa/Optimizer.java
index 799b704..35d6460 100644
--- a/dx/src/com/android/jack/dx/ssa/Optimizer.java
+++ b/dx/src/com/android/jack/dx/ssa/Optimizer.java
@@ -28,230 +28,229 @@
  * and returns it to rop form.
  */
 public class Optimizer {
-    private static boolean preserveLocals = true;
+  private static boolean preserveLocals = true;
 
-    private static TranslationAdvice advice;
+  private static TranslationAdvice advice;
 
-    /** optional optimizer steps */
-    public enum OptionalStep {
-        MOVE_PARAM_COMBINER, SCCP, LITERAL_UPGRADE, CONST_COLLECTOR,
-            ESCAPE_ANALYSIS
+  /** optional optimizer steps */
+  public enum OptionalStep {
+    MOVE_PARAM_COMBINER, SCCP, LITERAL_UPGRADE, CONST_COLLECTOR, ESCAPE_ANALYSIS
+  }
+
+  /**
+   * @return true if local variable information should be preserved, even
+   * at code size/register size cost
+   */
+  public static boolean getPreserveLocals() {
+    return preserveLocals;
+  }
+
+  /**
+   * @return {@code non-null;} translation advice
+   */
+  public static TranslationAdvice getAdvice() {
+    return advice;
+  }
+
+  /**
+   * Runs optimization algorthims over this method, and returns a new
+   * instance of RopMethod with the changes.
+   *
+   * @param rmeth method to process
+   * @param paramWidth the total width, in register-units, of this method's
+   * parameters
+   * @param isStatic true if this method has no 'this' pointer argument.
+   * @param inPreserveLocals true if local variable info should be preserved,
+   * at the cost of some registers and insns
+   * @param inAdvice {@code non-null;} translation advice
+   * @return optimized method
+   */
+  public static RopMethod optimize(RopMethod rmeth, int paramWidth, boolean isStatic,
+      boolean inPreserveLocals, TranslationAdvice inAdvice) {
+
+    return optimize(rmeth,
+        paramWidth,
+        isStatic,
+        inPreserveLocals,
+        inAdvice,
+        EnumSet.allOf(OptionalStep.class));
+  }
+
+  /**
+   * Runs optimization algorthims over this method, and returns a new
+   * instance of RopMethod with the changes.
+   *
+   * @param rmeth method to process
+   * @param paramWidth the total width, in register-units, of this method's
+   * parameters
+   * @param isStatic true if this method has no 'this' pointer argument.
+   * @param inPreserveLocals true if local variable info should be preserved,
+   * at the cost of some registers and insns
+   * @param inAdvice {@code non-null;} translation advice
+   * @param steps set of optional optimization steps to run
+   * @return optimized method
+   */
+  public static RopMethod optimize(RopMethod rmeth,
+      int paramWidth,
+      boolean isStatic,
+      boolean inPreserveLocals,
+      TranslationAdvice inAdvice,
+      EnumSet<OptionalStep> steps) {
+    SsaMethod ssaMeth = null;
+
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
+
+    ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
+    runSsaFormSteps(ssaMeth, steps);
+
+    RopMethod resultMeth = SsaToRop.convertToRopMethod(ssaMeth, false);
+
+    if (resultMeth.getBlocks().getRegCount() > advice.getMaxOptimalRegisterCount()) {
+      // Try to see if we can squeeze it under the register count bar
+      resultMeth = optimizeMinimizeRegisters(rmeth, paramWidth, isStatic, steps);
     }
+    return resultMeth;
+  }
 
-    /**
-     * @return true if local variable information should be preserved, even
-     * at code size/register size cost
+  /**
+   * Runs the optimizer with a strategy to minimize the number of rop-form
+   * registers used by the end result. Dex bytecode does not have instruction
+   * forms that take register numbers larger than 15 for all instructions.
+   * If we've produced a method that uses more than 16 registers, try again
+   * with a different strategy to see if we can get under the bar. The end
+   * result will be much more efficient.
+   *
+   * @param rmeth method to process
+   * @param paramWidth the total width, in register-units, of this method's
+   * parameters
+   * @param isStatic true if this method has no 'this' pointer argument.
+   * @param steps set of optional optimization steps to run
+   * @return optimized method
+   */
+  private static RopMethod optimizeMinimizeRegisters(RopMethod rmeth, int paramWidth,
+      boolean isStatic, EnumSet<OptionalStep> steps) {
+    SsaMethod ssaMeth;
+    RopMethod resultMeth;
+
+    ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
+
+    EnumSet<OptionalStep> newSteps = steps.clone();
+
+    /*
+     * CONST_COLLECTOR trades insns for registers, which is not an
+     * appropriate strategy here.
      */
-    public static boolean getPreserveLocals() {
-        return preserveLocals;
+    newSteps.remove(OptionalStep.CONST_COLLECTOR);
+
+    runSsaFormSteps(ssaMeth, newSteps);
+
+    resultMeth = SsaToRop.convertToRopMethod(ssaMeth, true);
+    return resultMeth;
+  }
+
+  private static void runSsaFormSteps(SsaMethod ssaMeth, EnumSet<OptionalStep> steps) {
+    boolean needsDeadCodeRemover = true;
+
+    if (steps.contains(OptionalStep.MOVE_PARAM_COMBINER)) {
+      MoveParamCombiner.process(ssaMeth);
     }
 
-    /**
-     * @return {@code non-null;} translation advice
+    if (steps.contains(OptionalStep.SCCP)) {
+      SCCP.process(ssaMeth);
+      DeadCodeRemover.process(ssaMeth);
+      needsDeadCodeRemover = false;
+    }
+
+    if (steps.contains(OptionalStep.LITERAL_UPGRADE)) {
+      LiteralOpUpgrader.process(ssaMeth);
+      DeadCodeRemover.process(ssaMeth);
+      needsDeadCodeRemover = false;
+    }
+
+    /*
+     * ESCAPE_ANALYSIS impacts debuggability, so left off by default
      */
-    public static TranslationAdvice getAdvice() {
-        return advice;
+    steps.remove(OptionalStep.ESCAPE_ANALYSIS);
+    if (steps.contains(OptionalStep.ESCAPE_ANALYSIS)) {
+      EscapeAnalysis.process(ssaMeth);
+      DeadCodeRemover.process(ssaMeth);
+      needsDeadCodeRemover = false;
     }
 
-    /**
-     * Runs optimization algorthims over this method, and returns a new
-     * instance of RopMethod with the changes.
-     *
-     * @param rmeth method to process
-     * @param paramWidth the total width, in register-units, of this method's
-     * parameters
-     * @param isStatic true if this method has no 'this' pointer argument.
-     * @param inPreserveLocals true if local variable info should be preserved,
-     * at the cost of some registers and insns
-     * @param inAdvice {@code non-null;} translation advice
-     * @return optimized method
-     */
-    public static RopMethod optimize(RopMethod rmeth, int paramWidth,
-            boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice) {
-
-        return optimize(rmeth, paramWidth, isStatic, inPreserveLocals, inAdvice,
-                EnumSet.allOf(OptionalStep.class));
+    if (steps.contains(OptionalStep.CONST_COLLECTOR)) {
+      ConstCollector.process(ssaMeth);
+      DeadCodeRemover.process(ssaMeth);
+      needsDeadCodeRemover = false;
     }
 
-    /**
-     * Runs optimization algorthims over this method, and returns a new
-     * instance of RopMethod with the changes.
-     *
-     * @param rmeth method to process
-     * @param paramWidth the total width, in register-units, of this method's
-     * parameters
-     * @param isStatic true if this method has no 'this' pointer argument.
-     * @param inPreserveLocals true if local variable info should be preserved,
-     * at the cost of some registers and insns
-     * @param inAdvice {@code non-null;} translation advice
-     * @param steps set of optional optimization steps to run
-     * @return optimized method
-     */
-    public static RopMethod optimize(RopMethod rmeth, int paramWidth,
-            boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice, EnumSet<OptionalStep> steps) {
-        SsaMethod ssaMeth = null;
-
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
-
-        ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
-        runSsaFormSteps(ssaMeth, steps);
-
-        RopMethod resultMeth = SsaToRop.convertToRopMethod(ssaMeth, false);
-
-        if (resultMeth.getBlocks().getRegCount()
-                > advice.getMaxOptimalRegisterCount()) {
-            // Try to see if we can squeeze it under the register count bar
-            resultMeth = optimizeMinimizeRegisters(rmeth, paramWidth, isStatic,
-                    steps);
-        }
-        return resultMeth;
+    // dead code remover must be run before phi type resolver
+    if (needsDeadCodeRemover) {
+      DeadCodeRemover.process(ssaMeth);
     }
 
-    /**
-     * Runs the optimizer with a strategy to minimize the number of rop-form
-     * registers used by the end result. Dex bytecode does not have instruction
-     * forms that take register numbers larger than 15 for all instructions.
-     * If we've produced a method that uses more than 16 registers, try again
-     * with a different strategy to see if we can get under the bar. The end
-     * result will be much more efficient.
-     *
-     * @param rmeth method to process
-     * @param paramWidth the total width, in register-units, of this method's
-     * parameters
-     * @param isStatic true if this method has no 'this' pointer argument.
-     * @param steps set of optional optimization steps to run
-     * @return optimized method
-     */
-    private static RopMethod optimizeMinimizeRegisters(RopMethod rmeth,
-            int paramWidth, boolean isStatic,
-            EnumSet<OptionalStep> steps) {
-        SsaMethod ssaMeth;
-        RopMethod resultMeth;
+    PhiTypeResolver.process(ssaMeth);
+  }
 
-        ssaMeth = SsaConverter.convertToSsaMethod(
-                rmeth, paramWidth, isStatic);
+  public static SsaMethod debugEdgeSplit(RopMethod rmeth, int paramWidth, boolean isStatic,
+      boolean inPreserveLocals, TranslationAdvice inAdvice) {
 
-        EnumSet<OptionalStep> newSteps = steps.clone();
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
 
-        /*
-         * CONST_COLLECTOR trades insns for registers, which is not an
-         * appropriate strategy here.
-         */
-        newSteps.remove(OptionalStep.CONST_COLLECTOR);
+    return SsaConverter.testEdgeSplit(rmeth, paramWidth, isStatic);
+  }
 
-        runSsaFormSteps(ssaMeth, newSteps);
+  public static SsaMethod debugPhiPlacement(RopMethod rmeth, int paramWidth, boolean isStatic,
+      boolean inPreserveLocals, TranslationAdvice inAdvice) {
 
-        resultMeth = SsaToRop.convertToRopMethod(ssaMeth, true);
-        return resultMeth;
-    }
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
 
-    private static void runSsaFormSteps(SsaMethod ssaMeth,
-            EnumSet<OptionalStep> steps) {
-        boolean needsDeadCodeRemover = true;
+    return SsaConverter.testPhiPlacement(rmeth, paramWidth, isStatic);
+  }
 
-        if (steps.contains(OptionalStep.MOVE_PARAM_COMBINER)) {
-            MoveParamCombiner.process(ssaMeth);
-        }
+  public static SsaMethod debugRenaming(RopMethod rmeth, int paramWidth, boolean isStatic,
+      boolean inPreserveLocals, TranslationAdvice inAdvice) {
 
-        if (steps.contains(OptionalStep.SCCP)) {
-            SCCP.process(ssaMeth);
-            DeadCodeRemover.process(ssaMeth);
-            needsDeadCodeRemover = false;
-        }
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
 
-        if (steps.contains(OptionalStep.LITERAL_UPGRADE)) {
-            LiteralOpUpgrader.process(ssaMeth);
-            DeadCodeRemover.process(ssaMeth);
-            needsDeadCodeRemover = false;
-        }
+    return SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
+  }
 
-        /*
-         * ESCAPE_ANALYSIS impacts debuggability, so left off by default
-         */
-        steps.remove(OptionalStep.ESCAPE_ANALYSIS);
-        if (steps.contains(OptionalStep.ESCAPE_ANALYSIS)) {
-            EscapeAnalysis.process(ssaMeth);
-            DeadCodeRemover.process(ssaMeth);
-            needsDeadCodeRemover = false;
-        }
+  public static SsaMethod debugDeadCodeRemover(RopMethod rmeth, int paramWidth, boolean isStatic,
+      boolean inPreserveLocals, TranslationAdvice inAdvice) {
 
-        if (steps.contains(OptionalStep.CONST_COLLECTOR)) {
-            ConstCollector.process(ssaMeth);
-            DeadCodeRemover.process(ssaMeth);
-            needsDeadCodeRemover = false;
-        }
+    SsaMethod ssaMeth;
 
-        // dead code remover must be run before phi type resolver
-        if (needsDeadCodeRemover) {
-            DeadCodeRemover.process(ssaMeth);
-        }
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
 
-        PhiTypeResolver.process(ssaMeth);
-    }
+    ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
+    DeadCodeRemover.process(ssaMeth);
 
-    public static SsaMethod debugEdgeSplit(RopMethod rmeth, int paramWidth,
-            boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice) {
+    return ssaMeth;
+  }
 
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
+  public static SsaMethod debugNoRegisterAllocation(RopMethod rmeth,
+      int paramWidth,
+      boolean isStatic,
+      boolean inPreserveLocals,
+      TranslationAdvice inAdvice,
+      EnumSet<OptionalStep> steps) {
 
-        return SsaConverter.testEdgeSplit(rmeth, paramWidth, isStatic);
-    }
+    SsaMethod ssaMeth;
 
-    public static SsaMethod debugPhiPlacement(RopMethod rmeth, int paramWidth,
-            boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice) {
+    preserveLocals = inPreserveLocals;
+    advice = inAdvice;
 
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
+    ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
 
-        return SsaConverter.testPhiPlacement(rmeth, paramWidth, isStatic);
-    }
+    runSsaFormSteps(ssaMeth, steps);
 
-    public static SsaMethod debugRenaming(RopMethod rmeth, int paramWidth,
-            boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice) {
+    LivenessAnalyzer.constructInterferenceGraph(ssaMeth);
 
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
-
-        return SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
-    }
-
-    public static SsaMethod debugDeadCodeRemover(RopMethod rmeth,
-            int paramWidth, boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice) {
-
-        SsaMethod ssaMeth;
-
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
-
-        ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
-        DeadCodeRemover.process(ssaMeth);
-
-        return ssaMeth;
-    }
-
-    public static SsaMethod debugNoRegisterAllocation(RopMethod rmeth,
-            int paramWidth, boolean isStatic, boolean inPreserveLocals,
-            TranslationAdvice inAdvice, EnumSet<OptionalStep> steps) {
-
-        SsaMethod ssaMeth;
-
-        preserveLocals = inPreserveLocals;
-        advice = inAdvice;
-
-        ssaMeth = SsaConverter.convertToSsaMethod(rmeth, paramWidth, isStatic);
-
-        runSsaFormSteps(ssaMeth, steps);
-
-        LivenessAnalyzer.constructInterferenceGraph(ssaMeth);
-
-        return ssaMeth;
-    }
+    return ssaMeth;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/PhiInsn.java b/dx/src/com/android/jack/dx/ssa/PhiInsn.java
index 9372305..d7419d6 100644
--- a/dx/src/com/android/jack/dx/ssa/PhiInsn.java
+++ b/dx/src/com/android/jack/dx/ssa/PhiInsn.java
@@ -16,7 +16,12 @@
 
 package com.android.jack.dx.ssa;
 
-import com.android.jack.dx.rop.code.*;
+import com.android.jack.dx.rop.code.Insn;
+import com.android.jack.dx.rop.code.LocalItem;
+import com.android.jack.dx.rop.code.RegisterSpec;
+import com.android.jack.dx.rop.code.RegisterSpecList;
+import com.android.jack.dx.rop.code.Rop;
+import com.android.jack.dx.rop.code.SourcePosition;
 import com.android.jack.dx.rop.type.Type;
 import com.android.jack.dx.rop.type.TypeBearer;
 import com.android.jack.dx.util.Hex;
@@ -30,369 +35,362 @@
  * conversion back to ROP form.
  */
 public final class PhiInsn extends SsaInsn {
-    /**
-     * result register. The original result register of the phi insn
-     * is needed during the renaming process after the new result
-     * register has already been chosen.
-     */
-    private final int ropResultReg;
+  /**
+   * result register. The original result register of the phi insn
+   * is needed during the renaming process after the new result
+   * register has already been chosen.
+   */
+  private final int ropResultReg;
 
-    /**
-     * {@code non-null;} operands of the instruction; built up by
-     * {@link #addPhiOperand}
-     */
-    private final ArrayList<Operand> operands = new ArrayList<Operand>();
+  /**
+   * {@code non-null;} operands of the instruction; built up by
+   * {@link #addPhiOperand}
+   */
+  private final ArrayList<Operand> operands = new ArrayList<Operand>();
 
-    /** {@code null-ok;} source registers; constructed lazily */
-    private RegisterSpecList sources;
+  /** {@code null-ok;} source registers; constructed lazily */
+  private RegisterSpecList sources;
 
-    /**
-     * Constructs a new phi insn with no operands.
-     *
-     * @param resultReg the result reg for this phi insn
-     * @param block block containing this insn.
+  /**
+   * Constructs a new phi insn with no operands.
+   *
+   * @param resultReg the result reg for this phi insn
+   * @param block block containing this insn.
+   */
+  public PhiInsn(RegisterSpec resultReg, SsaBasicBlock block) {
+    super(resultReg, block);
+    ropResultReg = resultReg.getReg();
+  }
+
+  /**
+   * Makes a phi insn with a void result type.
+   *
+   * @param resultReg the result register for this phi insn.
+   * @param block block containing this insn.
+   */
+  public PhiInsn(final int resultReg, final SsaBasicBlock block) {
+    /*
+     * The result type here is bogus: The type depends on the
+     * operand and will be derived later.
      */
-    public PhiInsn(RegisterSpec resultReg, SsaBasicBlock block) {
-        super(resultReg, block);
-        ropResultReg = resultReg.getReg();
+    super(RegisterSpec.make(resultReg, Type.VOID), block);
+    ropResultReg = resultReg;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public PhiInsn clone() {
+    throw new UnsupportedOperationException("can't clone phi");
+  }
+
+  /**
+   * Updates the TypeBearers of all the sources (phi operands) to be
+   * the current TypeBearer of the register-defining instruction's result.
+   * This is used during phi-type resolution.<p>
+   *
+   * Note that local association of operands are preserved in this step.
+   *
+   * @param ssaMeth method that contains this insn
+   */
+  public void updateSourcesToDefinitions(SsaMethod ssaMeth) {
+    for (Operand o : operands) {
+      RegisterSpec def = ssaMeth.getDefinitionForRegister(o.regSpec.getReg()).getResult();
+
+      o.regSpec = o.regSpec.withType(def.getType());
     }
 
-    /**
-     * Makes a phi insn with a void result type.
-     *
-     * @param resultReg the result register for this phi insn.
-     * @param block block containing this insn.
+    sources = null;
+  }
+
+  /**
+   * Changes the result type. Used during phi type resolution
+   *
+   * @param type {@code non-null;} new TypeBearer
+   * @param local {@code null-ok;} new local info, if available
+   */
+  public void changeResultType(TypeBearer type, LocalItem local) {
+    setResult(RegisterSpec.makeLocalOptional(getResult().getReg(), type, local));
+  }
+
+  /**
+   * Gets the original rop-form result reg. This is useful during renaming.
+   *
+   * @return the original rop-form result reg
+   */
+  public int getRopResultReg() {
+    return ropResultReg;
+  }
+
+  /**
+   * Adds an operand to this phi instruction.
+   *
+   * @param registerSpec register spec, including type and reg of operand
+   * @param predBlock predecessor block to be associated with this operand
+   */
+  public void addPhiOperand(RegisterSpec registerSpec, SsaBasicBlock predBlock) {
+    operands.add(new Operand(registerSpec, predBlock.getIndex(), predBlock.getRopLabel()));
+
+    // Un-cache sources, in case someone has already called getSources().
+    sources = null;
+  }
+
+  /**
+   * Removes all operand uses of a register from this phi instruction.
+   *
+   * @param registerSpec register spec, including type and reg of operand
+   */
+  public void removePhiRegister(RegisterSpec registerSpec) {
+    ArrayList<Operand> operandsToRemove = new ArrayList<Operand>();
+    for (Operand o : operands) {
+      if (o.regSpec.getReg() == registerSpec.getReg()) {
+        operandsToRemove.add(o);
+      }
+    }
+
+    operands.removeAll(operandsToRemove);
+
+    // Un-cache sources, in case someone has already called getSources().
+    sources = null;
+  }
+
+  /**
+   * Gets the index of the pred block associated with the RegisterSpec
+   * at the particular getSources() index.
+   *
+   * @param sourcesIndex index of source in getSources()
+   * @return block index
+   */
+  public int predBlockIndexForSourcesIndex(int sourcesIndex) {
+    return operands.get(sourcesIndex).blockIndex;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Always returns null for {@code PhiInsn}s.
+   */
+  @Override
+  public Rop getOpcode() {
+    return null;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Always returns null for {@code PhiInsn}s.
+   */
+  @Override
+  public Insn getOriginalRopInsn() {
+    return null;
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * Always returns false for {@code PhiInsn}s.
+   */
+  @Override
+  public boolean canThrow() {
+    return false;
+  }
+
+  /**
+   * Gets sources. Constructed lazily from phi operand data structures and
+   * then cached.
+   *
+   * @return {@code non-null;} sources list
+   */
+  @Override
+  public RegisterSpecList getSources() {
+    if (sources != null) {
+      return sources;
+    }
+
+    if (operands.size() == 0) {
+      // How'd this happen? A phi insn with no operand?
+      return RegisterSpecList.EMPTY;
+    }
+
+    int szSources = operands.size();
+    sources = new RegisterSpecList(szSources);
+
+    for (int i = 0; i < szSources; i++) {
+      Operand o = operands.get(i);
+
+      sources.set(i, o.regSpec);
+    }
+
+    sources.setImmutable();
+    return sources;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isRegASource(int reg) {
+    /*
+     * Avoid creating a sources list in case it has not already been
+     * created.
      */
-    public PhiInsn(final int resultReg, final SsaBasicBlock block) {
-        /*
-         * The result type here is bogus: The type depends on the
-         * operand and will be derived later.
-         */
-        super(RegisterSpec.make(resultReg, Type.VOID), block);
-        ropResultReg = resultReg;
-    }
 
-    /** {@inheritDoc} */
-    @Override
-    public PhiInsn clone() {
-        throw new UnsupportedOperationException("can't clone phi");
-    }
-
-    /**
-     * Updates the TypeBearers of all the sources (phi operands) to be
-     * the current TypeBearer of the register-defining instruction's result.
-     * This is used during phi-type resolution.<p>
-     *
-     * Note that local association of operands are preserved in this step.
-     *
-     * @param ssaMeth method that contains this insn
-     */
-    public void updateSourcesToDefinitions(SsaMethod ssaMeth) {
-        for (Operand o : operands) {
-            RegisterSpec def
-                = ssaMeth.getDefinitionForRegister(
-                    o.regSpec.getReg()).getResult();
-
-            o.regSpec = o.regSpec.withType(def.getType());
-        }
-
-        sources = null;
-    }
-
-    /**
-     * Changes the result type. Used during phi type resolution
-     *
-     * @param type {@code non-null;} new TypeBearer
-     * @param local {@code null-ok;} new local info, if available
-     */
-    public void changeResultType(TypeBearer type, LocalItem local) {
-        setResult(RegisterSpec.makeLocalOptional(
-                          getResult().getReg(), type, local));
-    }
-
-    /**
-     * Gets the original rop-form result reg. This is useful during renaming.
-     *
-     * @return the original rop-form result reg
-     */
-    public int getRopResultReg() {
-        return ropResultReg;
-    }
-
-    /**
-     * Adds an operand to this phi instruction.
-     *
-     * @param registerSpec register spec, including type and reg of operand
-     * @param predBlock predecessor block to be associated with this operand
-     */
-    public void addPhiOperand(RegisterSpec registerSpec,
-            SsaBasicBlock predBlock) {
-        operands.add(new Operand(registerSpec, predBlock.getIndex(),
-                predBlock.getRopLabel()));
-
-        // Un-cache sources, in case someone has already called getSources().
-        sources = null;
-    }
-
-    /**
-     * Removes all operand uses of a register from this phi instruction.
-     *
-     * @param registerSpec register spec, including type and reg of operand
-     */
-    public void removePhiRegister(RegisterSpec registerSpec) {
-        ArrayList<Operand> operandsToRemove = new ArrayList<Operand>();
-        for (Operand o : operands) {
-            if (o.regSpec.getReg() == registerSpec.getReg()) {
-                operandsToRemove.add(o);
-            }
-        }
-
-        operands.removeAll(operandsToRemove);
-
-        // Un-cache sources, in case someone has already called getSources().
-        sources = null;
-    }
-
-    /**
-     * Gets the index of the pred block associated with the RegisterSpec
-     * at the particular getSources() index.
-     *
-     * @param sourcesIndex index of source in getSources()
-     * @return block index
-     */
-    public int predBlockIndexForSourcesIndex(int sourcesIndex) {
-        return operands.get(sourcesIndex).blockIndex;
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * Always returns null for {@code PhiInsn}s.
-     */
-    @Override
-    public Rop getOpcode() {
-        return null;
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * Always returns null for {@code PhiInsn}s.
-     */
-    @Override
-    public Insn getOriginalRopInsn() {
-        return null;
-    }
-
-    /**
-     * {@inheritDoc}
-     *
-     * Always returns false for {@code PhiInsn}s.
-     */
-    @Override
-    public boolean canThrow() {
-        return false;
-    }
-
-    /**
-     * Gets sources. Constructed lazily from phi operand data structures and
-     * then cached.
-     *
-     * @return {@code non-null;} sources list
-     */
-    @Override
-    public RegisterSpecList getSources() {
-        if (sources != null) {
-            return sources;
-        }
-
-        if (operands.size() == 0) {
-            // How'd this happen? A phi insn with no operand?
-            return RegisterSpecList.EMPTY;
-        }
-
-        int szSources = operands.size();
-        sources = new RegisterSpecList(szSources);
-
-        for (int i = 0; i < szSources; i++) {
-            Operand o = operands.get(i);
-
-            sources.set(i, o.regSpec);
-        }
-
-        sources.setImmutable();
-        return sources;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean isRegASource(int reg) {
-        /*
-         * Avoid creating a sources list in case it has not already been
-         * created.
-         */
-
-        for (Operand o : operands) {
-            if (o.regSpec.getReg() == reg) {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    /**
-     * @return true if all operands use the same register
-     */
-    public boolean areAllOperandsEqual() {
-        if (operands.size() == 0 ) {
-            // This should never happen.
-            return true;
-        }
-
-        int firstReg = operands.get(0).regSpec.getReg();
-        for (Operand o : operands) {
-            if (firstReg != o.regSpec.getReg()) {
-                return false;
-            }
-        }
-
+for (Operand o : operands) {
+      if (o.regSpec.getReg() == reg) {
         return true;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public final void mapSourceRegisters(RegisterMapper mapper) {
-        for (Operand o : operands) {
-            RegisterSpec old = o.regSpec;
-            o.regSpec = mapper.map(old);
-            if (old != o.regSpec) {
-                getBlock().getParent().onSourceChanged(this, old, o.regSpec);
-            }
-        }
-        sources = null;
+    return false;
+  }
+
+  /**
+   * @return true if all operands use the same register
+   */
+  public boolean areAllOperandsEqual() {
+    if (operands.size() == 0) {
+      // This should never happen.
+      return true;
     }
 
-    /**
-     * Always throws an exeption, since a phi insn may not be
-     * converted back to rop form.
-     *
-     * @return always throws exception
-     */
-    @Override
-    public Insn toRopInsn() {
-        throw new IllegalArgumentException(
-                "Cannot convert phi insns to rop form");
+    int firstReg = operands.get(0).regSpec.getReg();
+    for (Operand o : operands) {
+      if (firstReg != o.regSpec.getReg()) {
+        return false;
+      }
     }
 
-    /**
-     * Returns the list of predecessor blocks associated with all operands
-     * that have {@code reg} as an operand register.
-     *
-     * @param reg register to look up
-     * @param ssaMeth method we're operating on
-     * @return list of predecessor blocks, empty if none
-     */
-    public List<SsaBasicBlock> predBlocksForReg(int reg, SsaMethod ssaMeth) {
-        ArrayList<SsaBasicBlock> ret = new ArrayList<SsaBasicBlock>();
+    return true;
+  }
 
-        for (Operand o : operands) {
-            if (o.regSpec.getReg() == reg) {
-                ret.add(ssaMeth.getBlocks().get(o.blockIndex));
-            }
-        }
+  /** {@inheritDoc} */
+  @Override
+  public final void mapSourceRegisters(RegisterMapper mapper) {
+    for (Operand o : operands) {
+      RegisterSpec old = o.regSpec;
+      o.regSpec = mapper.map(old);
+      if (old != o.regSpec) {
+        getBlock().getParent().onSourceChanged(this, old, o.regSpec);
+      }
+    }
+    sources = null;
+  }
 
-        return ret;
+  /**
+   * Always throws an exeption, since a phi insn may not be
+   * converted back to rop form.
+   *
+   * @return always throws exception
+   */
+  @Override
+  public Insn toRopInsn() {
+    throw new IllegalArgumentException("Cannot convert phi insns to rop form");
+  }
+
+  /**
+   * Returns the list of predecessor blocks associated with all operands
+   * that have {@code reg} as an operand register.
+   *
+   * @param reg register to look up
+   * @param ssaMeth method we're operating on
+   * @return list of predecessor blocks, empty if none
+   */
+  public List<SsaBasicBlock> predBlocksForReg(int reg, SsaMethod ssaMeth) {
+    ArrayList<SsaBasicBlock> ret = new ArrayList<SsaBasicBlock>();
+
+    for (Operand o : operands) {
+      if (o.regSpec.getReg() == reg) {
+        ret.add(ssaMeth.getBlocks().get(o.blockIndex));
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean isPhiOrMove() {
-        return true;
+    return ret;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isPhiOrMove() {
+    return true;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean hasSideEffect() {
+    return Optimizer.getPreserveLocals() && getLocalAssignment() != null;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void accept(SsaInsn.Visitor v) {
+    v.visitPhiInsn(this);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toHuman() {
+    return toHumanWithInline(null);
+  }
+
+  /**
+   * Returns human-readable string for listing dumps. This method
+   * allows sub-classes to specify extra text.
+   *
+   * @param extra {@code null-ok;} the argument to print after the opcode
+   * @return human-readable string for listing dumps
+   */
+  protected final String toHumanWithInline(String extra) {
+    StringBuffer sb = new StringBuffer(80);
+
+    sb.append(SourcePosition.NO_INFO);
+    sb.append(": phi");
+
+    if (extra != null) {
+      sb.append("(");
+      sb.append(extra);
+      sb.append(")");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean hasSideEffect() {
-        return Optimizer.getPreserveLocals() && getLocalAssignment() != null;
+    RegisterSpec result = getResult();
+
+    if (result == null) {
+      sb.append(" .");
+    } else {
+      sb.append(" ");
+      sb.append(result.toHuman());
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void accept(SsaInsn.Visitor v) {
-        v.visitPhiInsn(this);
+    sb.append(" <-");
+
+    int sz = getSources().size();
+    if (sz == 0) {
+      sb.append(" .");
+    } else {
+      for (int i = 0; i < sz; i++) {
+        sb.append(" ");
+        sb.append(sources.get(i).toHuman() + "[b=" + Hex.u2(operands.get(i).ropLabel) + "]");
+      }
     }
 
-    /** {@inheritDoc} */
-    public String toHuman() {
-        return toHumanWithInline(null);
+    return sb.toString();
+  }
+
+  /**
+   * A single phi operand, consiting of source register and block index
+   * for move.
+   */
+  private static class Operand {
+    public RegisterSpec regSpec;
+    public final int blockIndex;
+    public final int ropLabel; // only used for debugging
+
+    public Operand(RegisterSpec regSpec, int blockIndex, int ropLabel) {
+      this.regSpec = regSpec;
+      this.blockIndex = blockIndex;
+      this.ropLabel = ropLabel;
     }
+  }
 
-    /**
-     * Returns human-readable string for listing dumps. This method
-     * allows sub-classes to specify extra text.
-     *
-     * @param extra {@code null-ok;} the argument to print after the opcode
-     * @return human-readable string for listing dumps
-     */
-    protected final String toHumanWithInline(String extra) {
-        StringBuffer sb = new StringBuffer(80);
-
-        sb.append(SourcePosition.NO_INFO);
-        sb.append(": phi");
-
-        if (extra != null) {
-            sb.append("(");
-            sb.append(extra);
-            sb.append(")");
-        }
-
-        RegisterSpec result = getResult();
-
-        if (result == null) {
-            sb.append(" .");
-        } else {
-            sb.append(" ");
-            sb.append(result.toHuman());
-        }
-
-        sb.append(" <-");
-
-        int sz = getSources().size();
-        if (sz == 0) {
-            sb.append(" .");
-        } else {
-            for (int i = 0; i < sz; i++) {
-                sb.append(" ");
-                sb.append(sources.get(i).toHuman()
-                        + "[b="
-                        + Hex.u2(operands.get(i).ropLabel)  + "]");
-            }
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * A single phi operand, consiting of source register and block index
-     * for move.
-     */
-    private static class Operand {
-        public RegisterSpec regSpec;
-        public final int blockIndex;
-        public final int ropLabel;       // only used for debugging
-
-        public Operand(RegisterSpec regSpec, int blockIndex, int ropLabel) {
-            this.regSpec = regSpec;
-            this.blockIndex = blockIndex;
-            this.ropLabel = ropLabel;
-        }
-    }
-
-    /**
-     * Visitor interface for instances of this (outer) class.
-     */
-    public static interface Visitor {
-        public void visitPhiInsn(PhiInsn insn);
-    }
+  /**
+   * Visitor interface for instances of this (outer) class.
+   */
+  public static interface Visitor {
+    public void visitPhiInsn(PhiInsn insn);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/PhiTypeResolver.java b/dx/src/com/android/jack/dx/ssa/PhiTypeResolver.java
index abc1253..896f816 100644
--- a/dx/src/com/android/jack/dx/ssa/PhiTypeResolver.java
+++ b/dx/src/com/android/jack/dx/ssa/PhiTypeResolver.java
@@ -42,222 +42,218 @@
  */
 public class PhiTypeResolver {
 
-    SsaMethod ssaMeth;
-    /** indexed by register; all registers still defined by unresolved phis */
-    private final BitSet worklist;
+  SsaMethod ssaMeth;
+  /** indexed by register; all registers still defined by unresolved phis */
+  private final BitSet worklist;
 
-    /**
-     * Resolves all phi types in the method
-     * @param ssaMeth method to process
-     */
-    public static void process (SsaMethod ssaMeth) {
-        new PhiTypeResolver(ssaMeth).run();
+  /**
+   * Resolves all phi types in the method
+   * @param ssaMeth method to process
+   */
+  public static void process(SsaMethod ssaMeth) {
+    new PhiTypeResolver(ssaMeth).run();
+  }
+
+  private PhiTypeResolver(SsaMethod ssaMeth) {
+    this.ssaMeth = ssaMeth;
+    worklist = new BitSet(ssaMeth.getRegCount());
+  }
+
+  /**
+   * Runs the phi-type resolver.
+   */
+  private void run() {
+
+    int regCount = ssaMeth.getRegCount();
+
+    for (int reg = 0; reg < regCount; reg++) {
+      SsaInsn definsn = ssaMeth.getDefinitionForRegister(reg);
+
+      if (definsn != null && (definsn.getResult().getBasicType() == Type.BT_VOID)) {
+        worklist.set(reg);
+      }
     }
 
-    private PhiTypeResolver(SsaMethod ssaMeth) {
-        this.ssaMeth = ssaMeth;
-        worklist = new BitSet(ssaMeth.getRegCount());
-    }
+    int reg;
+    while (0 <= (reg = worklist.nextSetBit(0))) {
+      worklist.clear(reg);
 
-    /**
-     * Runs the phi-type resolver.
-     */
-    private void run() {
+      /*
+       * definitions on the worklist have a type of BT_VOID, which
+       * must have originated from a PhiInsn.
+       */
+      PhiInsn definsn = (PhiInsn) ssaMeth.getDefinitionForRegister(reg);
 
-        int regCount = ssaMeth.getRegCount();
+      if (resolveResultType(definsn)) {
+        /*
+         * If the result type has changed, re-resolve all phis
+         * that use this.
+         */
 
-        for (int reg = 0; reg < regCount; reg++) {
-            SsaInsn definsn = ssaMeth.getDefinitionForRegister(reg);
+List<SsaInsn> useList = ssaMeth.getUseListForRegister(reg);
 
-            if (definsn != null
-                    && (definsn.getResult().getBasicType() == Type.BT_VOID)) {
-                worklist.set(reg);
-            }
+        int sz = useList.size();
+        for (int i = 0; i < sz; i++) {
+          SsaInsn useInsn = useList.get(i);
+          RegisterSpec resultReg = useInsn.getResult();
+          if (resultReg != null && useInsn instanceof PhiInsn) {
+            worklist.set(resultReg.getReg());
+          }
         }
+      }
+    }
+  }
 
-        int reg;
-        while ( 0 <= (reg = worklist.nextSetBit(0))) {
-            worklist.clear(reg);
+  /**
+   * Returns true if a and b are equal, whether
+   * or not either of them are null.
+   * @param a
+   * @param b
+   * @return true if equal
+   */
+  private static boolean equalsHandlesNulls(LocalItem a, LocalItem b) {
+    return (a == b) || ((a != null) && a.equals(b));
+  }
 
+  /**
+   * Resolves the result of a phi insn based on its operands. The "void"
+   * type, which is a nonsensical type for a register, is used for
+   * registers defined by as-of-yet-unresolved phi operations.
+   *
+   * @return true if the result type changed, false if no change
+   */
+  boolean resolveResultType(PhiInsn insn) {
+    insn.updateSourcesToDefinitions(ssaMeth);
+
+    RegisterSpecList sources = insn.getSources();
+
+    // Start by finding the first non-void operand
+    RegisterSpec first = null;
+    int firstIndex = -1;
+
+    int szSources = sources.size();
+    for (int i = 0; i < szSources; i++) {
+      RegisterSpec rs = sources.get(i);
+
+      if (rs.getBasicType() != Type.BT_VOID) {
+        first = rs;
+        firstIndex = i;
+      }
+    }
+
+    if (first == null) {
+      // All operands are void -- we're not ready to resolve yet
+      return false;
+    }
+
+    LocalItem firstLocal = first.getLocalItem();
+    TypeBearer mergedType = first.getType();
+    boolean sameLocals = true;
+    for (int i = 0; i < szSources; i++) {
+      if (i == firstIndex) {
+        continue;
+      }
+
+      RegisterSpec rs = sources.get(i);
+
+      // Just skip void (unresolved phi results) for now
+      if (rs.getBasicType() == Type.BT_VOID) {
+        continue;
+      }
+
+      sameLocals = sameLocals && equalsHandlesNulls(firstLocal, rs.getLocalItem());
+
+      mergedType = mergeType(mergedType, rs.getType());
+    }
+
+    TypeBearer newResultType;
+
+    if (mergedType != null) {
+      newResultType = mergedType;
+    } else {
+      StringBuilder sb = new StringBuilder();
+
+      for (int i = 0; i < szSources; i++) {
+        sb.append(sources.get(i).toString());
+        sb.append(' ');
+      }
+
+      throw new RuntimeException("Couldn't map types in phi insn:" + sb);
+    }
+
+    LocalItem newLocal = sameLocals ? firstLocal : null;
+
+    RegisterSpec result = insn.getResult();
+
+    if ((result.getTypeBearer() == newResultType)
+        && equalsHandlesNulls(newLocal, result.getLocalItem())) {
+      return false;
+    }
+
+    insn.changeResultType(newResultType, newLocal);
+
+    return true;
+  }
+
+  /**
+   * Merges two frame types.
+   *
+   * @param ft1 {@code non-null;} a frame type
+   * @param ft2 {@code non-null;} another frame type
+   * @return {@code non-null;} the result of merging the two types
+   */
+  private static TypeBearer mergeType(TypeBearer ft1, TypeBearer ft2) {
+    if ((ft1 == null) || ft1.equals(ft2)) {
+      return ft1;
+    } else if (ft2 == null) {
+      return null;
+    } else {
+      Type type1 = ft1.getType();
+      Type type2 = ft2.getType();
+
+      if (type1 == type2) {
+        return type1;
+      } else if (type1.isReference() && type2.isReference()) {
+        if (type1 == Type.KNOWN_NULL) {
+          /*
+           * A known-null merges with any other reference type to
+           * be that reference type.
+           */
+          return type2;
+        } else if (type2 == Type.KNOWN_NULL) {
+          /*
+           * The same as above, but this time it's type2 that's
+           * the known-null.
+           */
+          return type1;
+        } else if (type1.isArray() && type2.isArray()) {
+          TypeBearer componentUnion = mergeType(type1.getComponentType(), type2.getComponentType());
+          if (componentUnion == null) {
             /*
-             * definitions on the worklist have a type of BT_VOID, which
-             * must have originated from a PhiInsn.
+             * At least one of the types is a primitive type,
+             * so the merged result is just Object.
              */
-            PhiInsn definsn = (PhiInsn)ssaMeth.getDefinitionForRegister(reg);
-
-            if (resolveResultType(definsn)) {
-                /*
-                 * If the result type has changed, re-resolve all phis
-                 * that use this.
-                 */
-
-                List<SsaInsn> useList = ssaMeth.getUseListForRegister(reg);
-
-                int sz = useList.size();
-                for (int i = 0; i < sz; i++ ) {
-                    SsaInsn useInsn = useList.get(i);
-                    RegisterSpec resultReg = useInsn.getResult();
-                    if (resultReg != null && useInsn instanceof PhiInsn) {
-                        worklist.set(resultReg.getReg());
-                    }
-                }
-            }
-        }
-    }
-
-    /**
-     * Returns true if a and b are equal, whether
-     * or not either of them are null.
-     * @param a
-     * @param b
-     * @return true if equal
-     */
-    private static boolean equalsHandlesNulls(LocalItem a, LocalItem b) {
-        return (a == b) || ((a != null) && a.equals(b));
-    }
-
-    /**
-     * Resolves the result of a phi insn based on its operands. The "void"
-     * type, which is a nonsensical type for a register, is used for
-     * registers defined by as-of-yet-unresolved phi operations.
-     *
-     * @return true if the result type changed, false if no change
-     */
-    boolean resolveResultType(PhiInsn insn) {
-        insn.updateSourcesToDefinitions(ssaMeth);
-
-        RegisterSpecList sources = insn.getSources();
-
-        // Start by finding the first non-void operand
-        RegisterSpec first = null;
-        int firstIndex = -1;
-
-        int szSources = sources.size();
-        for (int i = 0 ; i <szSources ; i++) {
-            RegisterSpec rs = sources.get(i);
-
-            if (rs.getBasicType() != Type.BT_VOID) {
-                first = rs;
-                firstIndex = i;
-            }
-        }
-
-        if (first == null) {
-            // All operands are void -- we're not ready to resolve yet
-            return false;
-        }
-
-        LocalItem firstLocal = first.getLocalItem();
-        TypeBearer mergedType = first.getType();
-        boolean sameLocals = true;
-        for (int i = 0 ; i < szSources ; i++) {
-            if (i == firstIndex) {
-                continue;
-            }
-
-            RegisterSpec rs = sources.get(i);
-
-            // Just skip void (unresolved phi results) for now
-            if (rs.getBasicType() == Type.BT_VOID){
-                continue;
-            }
-
-            sameLocals = sameLocals
-                    && equalsHandlesNulls(firstLocal, rs.getLocalItem());
-
-            mergedType = mergeType(mergedType, rs.getType());
-        }
-
-        TypeBearer newResultType;
-
-        if (mergedType != null) {
-            newResultType = mergedType;
+            return Type.OBJECT;
+          }
+          return ((Type) componentUnion).getArrayType();
         } else {
-            StringBuilder sb = new StringBuilder();
-
-            for (int i = 0; i < szSources; i++) {
-                sb.append(sources.get(i).toString());
-                sb.append(' ');
-            }
-
-            throw new RuntimeException ("Couldn't map types in phi insn:" + sb);
+          /*
+           * All other unequal reference types get merged to be
+           * Object in this phase. This is fine here, but it
+           * won't be the right thing to do in the verifier.
+           */
+          return Type.OBJECT;
         }
-
-        LocalItem newLocal = sameLocals ? firstLocal : null;
-
-        RegisterSpec result = insn.getResult();
-
-        if ((result.getTypeBearer() == newResultType)
-                && equalsHandlesNulls(newLocal, result.getLocalItem())) {
-            return false;
-        }
-
-        insn.changeResultType(newResultType, newLocal);
-
-        return true;
+      } else if (type1.isIntlike() && type2.isIntlike()) {
+        /*
+         * Merging two non-identical int-like types results in
+         * the type int.
+         */
+        return Type.INT;
+      } else {
+        return null;
+      }
     }
-
-    /**
-     * Merges two frame types.
-     *
-     * @param ft1 {@code non-null;} a frame type
-     * @param ft2 {@code non-null;} another frame type
-     * @return {@code non-null;} the result of merging the two types
-     */
-    private static TypeBearer mergeType(TypeBearer ft1, TypeBearer ft2) {
-        if ((ft1 == null) || ft1.equals(ft2)) {
-            return ft1;
-        } else if (ft2 == null) {
-            return null;
-        } else {
-            Type type1 = ft1.getType();
-            Type type2 = ft2.getType();
-
-            if (type1 == type2) {
-                return type1;
-            } else if (type1.isReference() && type2.isReference()) {
-                if (type1 == Type.KNOWN_NULL) {
-                    /*
-                     * A known-null merges with any other reference type to
-                     * be that reference type.
-                     */
-                    return type2;
-                } else if (type2 == Type.KNOWN_NULL) {
-                    /*
-                     * The same as above, but this time it's type2 that's
-                     * the known-null.
-                     */
-                    return type1;
-                } else if (type1.isArray() && type2.isArray()) {
-                    TypeBearer componentUnion =
-                        mergeType(type1.getComponentType(),
-                                type2.getComponentType());
-                    if (componentUnion == null) {
-                        /*
-                         * At least one of the types is a primitive type,
-                         * so the merged result is just Object.
-                         */
-                        return Type.OBJECT;
-                    }
-                    return ((Type) componentUnion).getArrayType();
-                } else {
-                    /*
-                     * All other unequal reference types get merged to be
-                     * Object in this phase. This is fine here, but it
-                     * won't be the right thing to do in the verifier.
-                     */
-                    return Type.OBJECT;
-                }
-            } else if (type1.isIntlike() && type2.isIntlike()) {
-                /*
-                 * Merging two non-identical int-like types results in
-                 * the type int.
-                 */
-                return Type.INT;
-            } else {
-                return null;
-            }
-        }
-    }
+  }
 
 }
diff --git a/dx/src/com/android/jack/dx/ssa/RegisterMapper.java b/dx/src/com/android/jack/dx/ssa/RegisterMapper.java
index 300d956..2807fdb 100644
--- a/dx/src/com/android/jack/dx/ssa/RegisterMapper.java
+++ b/dx/src/com/android/jack/dx/ssa/RegisterMapper.java
@@ -18,7 +18,6 @@
 
 import com.android.jack.dx.rop.code.RegisterSpec;
 import com.android.jack.dx.rop.code.RegisterSpecList;
-import com.android.jack.dx.util.ToHuman;
 
 /**
  * Represents a mapping between two register numbering schemes.
@@ -27,35 +26,35 @@
  * instances of this class are passed.
  */
 public abstract class RegisterMapper {
-    /**
-     * Gets the count of registers (really, the total register width, since
-     * category width is counted) in the new namespace.
-     * @return >= 0 width of new namespace.
-     */
-    public abstract int getNewRegisterCount();
+  /**
+   * Gets the count of registers (really, the total register width, since
+   * category width is counted) in the new namespace.
+   * @return >= 0 width of new namespace.
+   */
+  public abstract int getNewRegisterCount();
 
-    /**
-     * @param registerSpec old register
-     * @return register in new space
-     */
-    public abstract RegisterSpec map(RegisterSpec registerSpec);
+  /**
+   * @param registerSpec old register
+   * @return register in new space
+   */
+  public abstract RegisterSpec map(RegisterSpec registerSpec);
 
-    /**
-     *
-     * @param sources old register list
-     * @return new mapped register list, or old if nothing has changed.
-     */
-    public final RegisterSpecList map(RegisterSpecList sources) {
-        int sz = sources.size();
-        RegisterSpecList newSources = new RegisterSpecList(sz);
+  /**
+   *
+   * @param sources old register list
+   * @return new mapped register list, or old if nothing has changed.
+   */
+  public final RegisterSpecList map(RegisterSpecList sources) {
+    int sz = sources.size();
+    RegisterSpecList newSources = new RegisterSpecList(sz);
 
-        for (int i = 0; i < sz; i++) {
-            newSources.set(i, map(sources.get(i)));
-        }
-
-        newSources.setImmutable();
-
-        // Return the old sources if nothing has changed.
-        return newSources.equals(sources) ? sources : newSources;
+    for (int i = 0; i < sz; i++) {
+      newSources.set(i, map(sources.get(i)));
     }
+
+    newSources.setImmutable();
+
+    // Return the old sources if nothing has changed.
+    return newSources.equals(sources) ? sources : newSources;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SCCP.java b/dx/src/com/android/jack/dx/ssa/SCCP.java
index 9575353..4fc3a21 100644
--- a/dx/src/com/android/jack/dx/ssa/SCCP.java
+++ b/dx/src/com/android/jack/dx/ssa/SCCP.java
@@ -39,659 +39,646 @@
  * Propagation algorithm.
  */
 public class SCCP {
-    /** Lattice values  */
-    private static final int TOP = 0;
-    private static final int CONSTANT = 1;
-    private static final int VARYING = 2;
-    /** method we're processing */
-    private SsaMethod ssaMeth;
-    /** ssaMeth.getRegCount() */
-    private int regCount;
-    /** Lattice values for each SSA register */
-    private int[] latticeValues;
-    /** For those registers that are constant, this is the constant value */
-    private Constant[] latticeConstants;
-    /** Worklist of basic blocks to be processed */
-    private ArrayList<SsaBasicBlock> cfgWorklist;
-    /** Worklist of executed basic blocks with phis to be processed */
-    private ArrayList<SsaBasicBlock> cfgPhiWorklist;
-    /** Bitset containing bits for each block that has been found executable */
-    private BitSet executableBlocks;
-    /** Worklist for SSA edges.  This is a list of registers to process */
-    private ArrayList<SsaInsn> ssaWorklist;
-    /**
-     * Worklist for SSA edges that represent varying values.  It makes the
-     * algorithm much faster if you move all values to VARYING as fast as
-     * possible.
-     */
-    private ArrayList<SsaInsn> varyingWorklist;
-    /** Worklist of potential branches to convert to gotos */
-    private ArrayList<SsaInsn> branchWorklist;
+  /** Lattice values  */
+  private static final int TOP = 0;
+  private static final int CONSTANT = 1;
+  private static final int VARYING = 2;
+  /** method we're processing */
+  private SsaMethod ssaMeth;
+  /** ssaMeth.getRegCount() */
+  private int regCount;
+  /** Lattice values for each SSA register */
+  private int[] latticeValues;
+  /** For those registers that are constant, this is the constant value */
+  private Constant[] latticeConstants;
+  /** Worklist of basic blocks to be processed */
+  private ArrayList<SsaBasicBlock> cfgWorklist;
+  /** Worklist of executed basic blocks with phis to be processed */
+  private ArrayList<SsaBasicBlock> cfgPhiWorklist;
+  /** Bitset containing bits for each block that has been found executable */
+  private BitSet executableBlocks;
+  /** Worklist for SSA edges.  This is a list of registers to process */
+  private ArrayList<SsaInsn> ssaWorklist;
+  /**
+   * Worklist for SSA edges that represent varying values.  It makes the
+   * algorithm much faster if you move all values to VARYING as fast as
+   * possible.
+   */
+  private ArrayList<SsaInsn> varyingWorklist;
+  /** Worklist of potential branches to convert to gotos */
+  private ArrayList<SsaInsn> branchWorklist;
 
-    private SCCP(SsaMethod ssaMeth) {
-        this.ssaMeth = ssaMeth;
-        this.regCount = ssaMeth.getRegCount();
-        this.latticeValues = new int[this.regCount];
-        this.latticeConstants = new Constant[this.regCount];
-        this.cfgWorklist = new ArrayList<SsaBasicBlock>();
-        this.cfgPhiWorklist = new ArrayList<SsaBasicBlock>();
-        this.executableBlocks = new BitSet(ssaMeth.getBlocks().size());
-        this.ssaWorklist = new ArrayList<SsaInsn>();
-        this.varyingWorklist = new ArrayList<SsaInsn>();
-        this.branchWorklist = new ArrayList<SsaInsn>();
-        for (int i = 0; i < this.regCount; i++) {
-            latticeValues[i] = TOP;
-            latticeConstants[i] = null;
-        }
+  private SCCP(SsaMethod ssaMeth) {
+    this.ssaMeth = ssaMeth;
+    this.regCount = ssaMeth.getRegCount();
+    this.latticeValues = new int[this.regCount];
+    this.latticeConstants = new Constant[this.regCount];
+    this.cfgWorklist = new ArrayList<SsaBasicBlock>();
+    this.cfgPhiWorklist = new ArrayList<SsaBasicBlock>();
+    this.executableBlocks = new BitSet(ssaMeth.getBlocks().size());
+    this.ssaWorklist = new ArrayList<SsaInsn>();
+    this.varyingWorklist = new ArrayList<SsaInsn>();
+    this.branchWorklist = new ArrayList<SsaInsn>();
+    for (int i = 0; i < this.regCount; i++) {
+      latticeValues[i] = TOP;
+      latticeConstants[i] = null;
+    }
+  }
+
+  /**
+   * Performs sparse conditional constant propagation on a method.
+   * @param ssaMethod Method to process
+   */
+  public static void process(SsaMethod ssaMethod) {
+    new SCCP(ssaMethod).run();
+  }
+
+  /**
+   * Adds a SSA basic block to the CFG worklist if it's unexecuted, or
+   * to the CFG phi worklist if it's already executed.
+   * @param ssaBlock Block to add
+   */
+  private void addBlockToWorklist(SsaBasicBlock ssaBlock) {
+    if (!executableBlocks.get(ssaBlock.getIndex())) {
+      cfgWorklist.add(ssaBlock);
+      executableBlocks.set(ssaBlock.getIndex());
+    } else {
+      cfgPhiWorklist.add(ssaBlock);
+    }
+  }
+
+  /**
+   * Adds an SSA register's uses to the SSA worklist.
+   * @param reg SSA register
+   * @param latticeValue new lattice value for @param reg.
+   */
+  private void addUsersToWorklist(int reg, int latticeValue) {
+    if (latticeValue == VARYING) {
+      for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
+        varyingWorklist.add(insn);
+      }
+    } else {
+      for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
+        ssaWorklist.add(insn);
+      }
+    }
+  }
+
+  /**
+   * Sets a lattice value for a register to value.
+   * @param reg SSA register
+   * @param value Lattice value
+   * @param cst Constant value (may be null)
+   * @return true if the lattice value changed.
+   */
+  private boolean setLatticeValueTo(int reg, int value, Constant cst) {
+    if (value != CONSTANT) {
+      if (latticeValues[reg] != value) {
+        latticeValues[reg] = value;
+        return true;
+      }
+      return false;
+    } else {
+      if (latticeValues[reg] != value || !latticeConstants[reg].equals(cst)) {
+        latticeValues[reg] = value;
+        latticeConstants[reg] = cst;
+        return true;
+      }
+      return false;
+    }
+  }
+
+  /**
+   * Simulates a PHI node and set the lattice for the result
+   * to the appropriate value.
+   * Meet values:
+   * TOP x anything = TOP
+   * VARYING x anything = VARYING
+   * CONSTANT x CONSTANT = CONSTANT if equal constants, VARYING otherwise
+   * @param insn PHI to simulate.
+   */
+  private void simulatePhi(PhiInsn insn) {
+    int phiResultReg = insn.getResult().getReg();
+
+    if (latticeValues[phiResultReg] == VARYING) {
+      return;
     }
 
-    /**
-     * Performs sparse conditional constant propagation on a method.
-     * @param ssaMethod Method to process
-     */
-    public static void process (SsaMethod ssaMethod) {
-        new SCCP(ssaMethod).run();
-    }
+    RegisterSpecList sources = insn.getSources();
+    int phiResultValue = TOP;
+    Constant phiConstant = null;
+    int sourceSize = sources.size();
 
-    /**
-     * Adds a SSA basic block to the CFG worklist if it's unexecuted, or
-     * to the CFG phi worklist if it's already executed.
-     * @param ssaBlock Block to add
-     */
-    private void addBlockToWorklist(SsaBasicBlock ssaBlock) {
-        if (!executableBlocks.get(ssaBlock.getIndex())) {
-            cfgWorklist.add(ssaBlock);
-            executableBlocks.set(ssaBlock.getIndex());
-        } else {
-            cfgPhiWorklist.add(ssaBlock);
+    for (int i = 0; i < sourceSize; i++) {
+      int predBlockIndex = insn.predBlockIndexForSourcesIndex(i);
+      int sourceReg = sources.get(i).getReg();
+      int sourceRegValue = latticeValues[sourceReg];
+
+      if (!executableBlocks.get(predBlockIndex)) {
+        continue;
+      }
+
+      if (sourceRegValue == CONSTANT) {
+        if (phiConstant == null) {
+          phiConstant = latticeConstants[sourceReg];
+          phiResultValue = CONSTANT;
+        } else if (!latticeConstants[sourceReg].equals(phiConstant)) {
+          phiResultValue = VARYING;
+          break;
         }
+      } else {
+        phiResultValue = sourceRegValue;
+        break;
+      }
     }
-
-    /**
-     * Adds an SSA register's uses to the SSA worklist.
-     * @param reg SSA register
-     * @param latticeValue new lattice value for @param reg.
-     */
-    private void addUsersToWorklist(int reg, int latticeValue) {
-        if (latticeValue == VARYING) {
-            for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
-                varyingWorklist.add(insn);
-            }
-        } else {
-            for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
-                ssaWorklist.add(insn);
-            }
-        }
+    if (setLatticeValueTo(phiResultReg, phiResultValue, phiConstant)) {
+      addUsersToWorklist(phiResultReg, phiResultValue);
     }
+  }
 
-    /**
-     * Sets a lattice value for a register to value.
-     * @param reg SSA register
-     * @param value Lattice value
-     * @param cst Constant value (may be null)
-     * @return true if the lattice value changed.
-     */
-    private boolean setLatticeValueTo(int reg, int value, Constant cst) {
-        if (value != CONSTANT) {
-            if (latticeValues[reg] != value) {
-                latticeValues[reg] = value;
-                return true;
-            }
-            return false;
-        } else {
-            if (latticeValues[reg] != value
-                    || !latticeConstants[reg].equals(cst)) {
-                latticeValues[reg] = value;
-                latticeConstants[reg] = cst;
-                return true;
-            }
-            return false;
-        }
+  /**
+   * Simulate a block and note the results in the lattice.
+   * @param block Block to visit
+   */
+  private void simulateBlock(SsaBasicBlock block) {
+    for (SsaInsn insn : block.getInsns()) {
+      if (insn instanceof PhiInsn) {
+        simulatePhi((PhiInsn) insn);
+      } else {
+        simulateStmt(insn);
+      }
     }
+  }
 
-    /**
-     * Simulates a PHI node and set the lattice for the result
-     * to the appropriate value.
-     * Meet values:
-     * TOP x anything = TOP
-     * VARYING x anything = VARYING
-     * CONSTANT x CONSTANT = CONSTANT if equal constants, VARYING otherwise
-     * @param insn PHI to simulate.
-     */
-    private void simulatePhi(PhiInsn insn) {
-        int phiResultReg = insn.getResult().getReg();
+  /**
+   * Simulate the phis in a block and note the results in the lattice.
+   * @param block Block to visit
+   */
+  private void simulatePhiBlock(SsaBasicBlock block) {
+    for (SsaInsn insn : block.getInsns()) {
+      if (insn instanceof PhiInsn) {
+        simulatePhi((PhiInsn) insn);
+      } else {
+        return;
+      }
+    }
+  }
 
-        if (latticeValues[phiResultReg] == VARYING) {
-            return;
+  /**
+   * Simulates branch insns, if possible. Adds reachable successor blocks
+   * to the CFG worklists.
+   * @param insn branch to simulate
+   */
+  private void simulateBranch(SsaInsn insn) {
+    Rop opcode = insn.getOpcode();
+    RegisterSpecList sources = insn.getSources();
+
+    boolean constantBranch = false;
+    boolean constantSuccessor = false;
+
+    // Check if the insn is a branch with a constant condition
+    if (opcode.getBranchingness() == Rop.BRANCH_IF) {
+      Constant cA = null;
+      Constant cB = null;
+
+      RegisterSpec specA = sources.get(0);
+      int regA = specA.getReg();
+      if (!ssaMeth.isRegALocal(specA) && latticeValues[regA] == CONSTANT) {
+        cA = latticeConstants[regA];
+      }
+
+      if (sources.size() == 2) {
+        RegisterSpec specB = sources.get(1);
+        int regB = specB.getReg();
+        if (!ssaMeth.isRegALocal(specB) && latticeValues[regB] == CONSTANT) {
+          cB = latticeConstants[regB];
         }
+      }
 
-        RegisterSpecList sources = insn.getSources();
-        int phiResultValue = TOP;
-        Constant phiConstant = null;
-        int sourceSize = sources.size();
-
-        for (int i = 0; i < sourceSize; i++) {
-            int predBlockIndex = insn.predBlockIndexForSourcesIndex(i);
-            int sourceReg = sources.get(i).getReg();
-            int sourceRegValue = latticeValues[sourceReg];
-
-            if (!executableBlocks.get(predBlockIndex)) {
-                continue;
-            }
-
-            if (sourceRegValue == CONSTANT) {
-                if (phiConstant == null) {
-                    phiConstant = latticeConstants[sourceReg];
-                    phiResultValue = CONSTANT;
-                 } else if (!latticeConstants[sourceReg].equals(phiConstant)){
-                    phiResultValue = VARYING;
-                    break;
-                }
-            } else {
-                phiResultValue = sourceRegValue;
+      // Calculate the result of the condition
+      if (cA != null && sources.size() == 1) {
+        switch (((TypedConstant) cA).getBasicType()) {
+          case Type.BT_BOOLEAN: {
+            constantBranch = true;
+            boolean vA = ((CstBoolean) cA).getValue();
+            switch (opcode.getOpcode()) {
+              case RegOps.IF_EQ:
+                constantSuccessor = !vA;
                 break;
+              case RegOps.IF_NE:
+                constantSuccessor = vA;
+                break;
+              default:
+                throw new RuntimeException("Unexpected op");
             }
+            break;
+          }
+          case Type.BT_INT:
+            constantBranch = true;
+            int vA = ((CstInteger) cA).getValue();
+            switch (opcode.getOpcode()) {
+              case RegOps.IF_EQ:
+                constantSuccessor = (vA == 0);
+                break;
+              case RegOps.IF_NE:
+                constantSuccessor = (vA != 0);
+                break;
+              case RegOps.IF_LT:
+                constantSuccessor = (vA < 0);
+                break;
+              case RegOps.IF_GE:
+                constantSuccessor = (vA >= 0);
+                break;
+              case RegOps.IF_LE:
+                constantSuccessor = (vA <= 0);
+                break;
+              case RegOps.IF_GT:
+                constantSuccessor = (vA > 0);
+                break;
+              default:
+                throw new RuntimeException("Unexpected op");
+            }
+            break;
+          default:
+        // not yet supported
         }
-        if (setLatticeValueTo(phiResultReg, phiResultValue, phiConstant)) {
-            addUsersToWorklist(phiResultReg, phiResultValue);
+      } else if (cA != null && cB != null) {
+        switch (((TypedConstant) cA).getBasicType()) {
+          case Type.BT_INT:
+            constantBranch = true;
+            int vA = ((CstInteger) cA).getValue();
+            int vB = ((CstInteger) cB).getValue();
+            switch (opcode.getOpcode()) {
+              case RegOps.IF_EQ:
+                constantSuccessor = (vA == vB);
+                break;
+              case RegOps.IF_NE:
+                constantSuccessor = (vA != vB);
+                break;
+              case RegOps.IF_LT:
+                constantSuccessor = (vA < vB);
+                break;
+              case RegOps.IF_GE:
+                constantSuccessor = (vA >= vB);
+                break;
+              case RegOps.IF_LE:
+                constantSuccessor = (vA <= vB);
+                break;
+              case RegOps.IF_GT:
+                constantSuccessor = (vA > vB);
+                break;
+              default:
+                throw new RuntimeException("Unexpected op");
+            }
+            break;
+          default:
+        // not yet supported
         }
+      }
     }
 
-    /**
-     * Simulate a block and note the results in the lattice.
-     * @param block Block to visit
+    /*
+     * If condition is constant, add only the target block to the
+     * worklist. Otherwise, add all successors to the worklist.
      */
-    private void simulateBlock(SsaBasicBlock block) {
-        for (SsaInsn insn : block.getInsns()) {
-            if (insn instanceof PhiInsn) {
-                simulatePhi((PhiInsn) insn);
-            } else {
-                simulateStmt(insn);
-            }
-        }
+    SsaBasicBlock block = insn.getBlock();
+
+    if (constantBranch) {
+      int successorBlock;
+      if (constantSuccessor) {
+        successorBlock = block.getSuccessorList().get(1);
+      } else {
+        successorBlock = block.getSuccessorList().get(0);
+      }
+      addBlockToWorklist(ssaMeth.getBlocks().get(successorBlock));
+      branchWorklist.add(insn);
+    } else {
+      for (int i = 0; i < block.getSuccessorList().size(); i++) {
+        int successorBlock = block.getSuccessorList().get(i);
+        addBlockToWorklist(ssaMeth.getBlocks().get(successorBlock));
+      }
+    }
+  }
+
+  /**
+   * Simulates math insns, if possible.
+   *
+   * @param insn non-null insn to simulate
+   * @param resultType basic type of the result
+   * @return constant result or null if not simulatable.
+   */
+  private Constant simulateMath(SsaInsn insn, int resultType) {
+    Insn ropInsn = insn.getOriginalRopInsn();
+    int opcode = insn.getOpcode().getOpcode();
+    RegisterSpecList sources = insn.getSources();
+    int regA = sources.get(0).getReg();
+    Constant cA;
+    Constant cB;
+
+    if (latticeValues[regA] != CONSTANT) {
+      cA = null;
+    } else {
+      cA = latticeConstants[regA];
     }
 
-    /**
-     * Simulate the phis in a block and note the results in the lattice.
-     * @param block Block to visit
-     */
-    private void simulatePhiBlock(SsaBasicBlock block) {
-        for (SsaInsn insn : block.getInsns()) {
-            if (insn instanceof PhiInsn) {
-                simulatePhi((PhiInsn) insn);
-            } else {
-                return;
-            }
-        }
+    if (sources.size() == 1) {
+      CstInsn cstInsn = (CstInsn) ropInsn;
+      cB = cstInsn.getConstant();
+    } else { /* sources.size() == 2 */
+      int regB = sources.get(1).getReg();
+      if (latticeValues[regB] != CONSTANT) {
+        cB = null;
+      } else {
+        cB = latticeConstants[regB];
+      }
     }
 
-    private static String latticeValName(int latticeVal) {
-        switch (latticeVal) {
-            case TOP: return "TOP";
-            case CONSTANT: return "CONSTANT";
-            case VARYING: return "VARYING";
-            default: return "UNKNOWN";
-        }
+    if (cA == null || cB == null) {
+      //TODO(dx team) handle a constant of 0 with MUL or AND
+      return null;
     }
 
-    /**
-     * Simulates branch insns, if possible. Adds reachable successor blocks
-     * to the CFG worklists.
-     * @param insn branch to simulate
-     */
-    private void simulateBranch(SsaInsn insn) {
-        Rop opcode = insn.getOpcode();
-        RegisterSpecList sources = insn.getSources();
+    switch (resultType) {
+      case Type.BT_INT:
+        int vR;
+        boolean skip = false;
 
-        boolean constantBranch = false;
-        boolean constantSuccessor = false;
-
-        // Check if the insn is a branch with a constant condition
-        if (opcode.getBranchingness() == Rop.BRANCH_IF) {
-            Constant cA = null;
-            Constant cB = null;
-
-            RegisterSpec specA = sources.get(0);
-            int regA = specA.getReg();
-            if (!ssaMeth.isRegALocal(specA) &&
-                    latticeValues[regA] == CONSTANT) {
-                cA = latticeConstants[regA];
-            }
-
-            if (sources.size() == 2) {
-                RegisterSpec specB = sources.get(1);
-                int regB = specB.getReg();
-                if (!ssaMeth.isRegALocal(specB) &&
-                        latticeValues[regB] == CONSTANT) {
-                    cB = latticeConstants[regB];
-                }
-            }
-
-            // Calculate the result of the condition
-            if (cA != null && sources.size() == 1) {
-                switch (((TypedConstant) cA).getBasicType()) {
-                    case Type.BT_BOOLEAN: {
-                      constantBranch = true;
-                      boolean vA = ((CstBoolean) cA).getValue();
-                      switch (opcode.getOpcode()) {
-                        case RegOps.IF_EQ:
-                          constantSuccessor = !vA;
-                          break;
-                        case RegOps.IF_NE:
-                          constantSuccessor = vA;
-                          break;
-                        default:
-                          throw new RuntimeException("Unexpected op");
-                      }
-                      break;
-                    }
-                    case Type.BT_INT:
-                        constantBranch = true;
-                        int vA = ((CstInteger) cA).getValue();
-                        switch (opcode.getOpcode()) {
-                            case RegOps.IF_EQ:
-                                constantSuccessor = (vA == 0);
-                                break;
-                            case RegOps.IF_NE:
-                                constantSuccessor = (vA != 0);
-                                break;
-                            case RegOps.IF_LT:
-                                constantSuccessor = (vA < 0);
-                                break;
-                            case RegOps.IF_GE:
-                                constantSuccessor = (vA >= 0);
-                                break;
-                            case RegOps.IF_LE:
-                                constantSuccessor = (vA <= 0);
-                                break;
-                            case RegOps.IF_GT:
-                                constantSuccessor = (vA > 0);
-                                break;
-                            default:
-                                throw new RuntimeException("Unexpected op");
-                        }
-                        break;
-                    default:
-                        // not yet supported
-                }
-            } else if (cA != null && cB != null) {
-                switch (((TypedConstant) cA).getBasicType()) {
-                    case Type.BT_INT:
-                        constantBranch = true;
-                        int vA = ((CstInteger) cA).getValue();
-                        int vB = ((CstInteger) cB).getValue();
-                        switch (opcode.getOpcode()) {
-                            case RegOps.IF_EQ:
-                                constantSuccessor = (vA == vB);
-                                break;
-                            case RegOps.IF_NE:
-                                constantSuccessor = (vA != vB);
-                                break;
-                            case RegOps.IF_LT:
-                                constantSuccessor = (vA < vB);
-                                break;
-                            case RegOps.IF_GE:
-                                constantSuccessor = (vA >= vB);
-                                break;
-                            case RegOps.IF_LE:
-                                constantSuccessor = (vA <= vB);
-                                break;
-                            case RegOps.IF_GT:
-                                constantSuccessor = (vA > vB);
-                                break;
-                            default:
-                                throw new RuntimeException("Unexpected op");
-                        }
-                        break;
-                    default:
-                        // not yet supported
-                }
-            }
-        }
-
-        /*
-         * If condition is constant, add only the target block to the
-         * worklist. Otherwise, add all successors to the worklist.
-         */
-        SsaBasicBlock block = insn.getBlock();
-
-        if (constantBranch) {
-            int successorBlock;
-            if (constantSuccessor) {
-                successorBlock = block.getSuccessorList().get(1);
-            } else {
-                successorBlock = block.getSuccessorList().get(0);
-            }
-            addBlockToWorklist(ssaMeth.getBlocks().get(successorBlock));
-            branchWorklist.add(insn);
-        } else {
-            for (int i = 0; i < block.getSuccessorList().size(); i++) {
-                int successorBlock = block.getSuccessorList().get(i);
-                addBlockToWorklist(ssaMeth.getBlocks().get(successorBlock));
-            }
-        }
-    }
-
-    /**
-     * Simulates math insns, if possible.
-     *
-     * @param insn non-null insn to simulate
-     * @param resultType basic type of the result
-     * @return constant result or null if not simulatable.
-     */
-    private Constant simulateMath(SsaInsn insn, int resultType) {
-        Insn ropInsn = insn.getOriginalRopInsn();
-        int opcode = insn.getOpcode().getOpcode();
-        RegisterSpecList sources = insn.getSources();
-        int regA = sources.get(0).getReg();
-        Constant cA;
-        Constant cB;
-
-        if (latticeValues[regA] != CONSTANT) {
-            cA = null;
-        } else {
-            cA = latticeConstants[regA];
-        }
-
-        if (sources.size() == 1) {
-            CstInsn cstInsn = (CstInsn) ropInsn;
-            cB = cstInsn.getConstant();
-        } else { /* sources.size() == 2 */
-            int regB = sources.get(1).getReg();
-            if (latticeValues[regB] != CONSTANT) {
-                cB = null;
-            } else {
-                cB = latticeConstants[regB];
-            }
-        }
-
-        if (cA == null || cB == null) {
-            //TODO handle a constant of 0 with MUL or AND
-            return null;
-        }
-
-        switch (resultType) {
-            case Type.BT_INT:
-                int vR;
-                boolean skip=false;
-
-                int vA = ((CstInteger) cA).getValue();
-                int vB = ((CstInteger) cB).getValue();
-
-                switch (opcode) {
-                    case RegOps.ADD:
-                        vR = vA + vB;
-                        break;
-                    case RegOps.SUB:
-                        // 1 source for reverse sub, 2 sources for regular sub
-                        if (sources.size() == 1) {
-                            vR = vB - vA;
-                        } else {
-                            vR = vA - vB;
-                        }
-                        break;
-                    case RegOps.MUL:
-                        vR = vA * vB;
-                        break;
-                    case RegOps.DIV:
-                        if (vB == 0) {
-                            skip = true;
-                            vR = 0; // just to hide a warning
-                        } else {
-                            vR = vA / vB;
-                        }
-                        break;
-                    case RegOps.AND:
-                        vR = vA & vB;
-                        break;
-                    case RegOps.OR:
-                        vR = vA | vB;
-                        break;
-                    case RegOps.XOR:
-                        vR = vA ^ vB;
-                        break;
-                    case RegOps.SHL:
-                        vR = vA << vB;
-                        break;
-                    case RegOps.SHR:
-                        vR = vA >> vB;
-                        break;
-                    case RegOps.USHR:
-                        vR = vA >>> vB;
-                        break;
-                    case RegOps.REM:
-                        if (vB == 0) {
-                            skip = true;
-                            vR = 0; // just to hide a warning
-                        } else {
-                            vR = vA % vB;
-                        }
-                        break;
-                    default:
-                        throw new RuntimeException("Unexpected op");
-                }
-
-                return skip ? null : CstInteger.make(vR);
-
-            default:
-                // not yet supported
-                return null;
-        }
-    }
-
-    /**
-     * Simulates a statement and set the result lattice value.
-     * @param insn instruction to simulate
-     */
-    private void simulateStmt(SsaInsn insn) {
-        Insn ropInsn = insn.getOriginalRopInsn();
-        if (ropInsn.getOpcode().getBranchingness() != Rop.BRANCH_NONE
-                || ropInsn.getOpcode().isCallLike()) {
-            simulateBranch(insn);
-        }
-
-        int opcode = insn.getOpcode().getOpcode();
-        RegisterSpec result = insn.getResult();
-
-        if (result == null) {
-            // Find move-result-pseudo result for int div and int rem
-            if (opcode == RegOps.DIV || opcode == RegOps.REM) {
-                SsaBasicBlock succ = insn.getBlock().getPrimarySuccessor();
-                result = succ.getInsns().get(0).getResult();
-            } else {
-                return;
-            }
-        }
-
-        int resultReg = result.getReg();
-        int resultValue = VARYING;
-        Constant resultConstant = null;
+        int vA = ((CstInteger) cA).getValue();
+        int vB = ((CstInteger) cB).getValue();
 
         switch (opcode) {
-            case RegOps.CONST: {
-                CstInsn cstInsn = (CstInsn)ropInsn;
-                resultValue = CONSTANT;
-                resultConstant = cstInsn.getConstant();
-                break;
+          case RegOps.ADD:
+            vR = vA + vB;
+            break;
+          case RegOps.SUB:
+            // 1 source for reverse sub, 2 sources for regular sub
+            if (sources.size() == 1) {
+              vR = vB - vA;
+            } else {
+              vR = vA - vB;
             }
-            case RegOps.MOVE: {
-                if (insn.getSources().size() == 1) {
-                    int sourceReg = insn.getSources().get(0).getReg();
-                    resultValue = latticeValues[sourceReg];
-                    resultConstant = latticeConstants[sourceReg];
-                }
-                break;
+            break;
+          case RegOps.MUL:
+            vR = vA * vB;
+            break;
+          case RegOps.DIV:
+            if (vB == 0) {
+              skip = true;
+              vR = 0; // just to hide a warning
+            } else {
+              vR = vA / vB;
             }
-            case RegOps.ADD:
-            case RegOps.SUB:
-            case RegOps.MUL:
-            case RegOps.DIV:
-            case RegOps.AND:
-            case RegOps.OR:
-            case RegOps.XOR:
-            case RegOps.SHL:
-            case RegOps.SHR:
-            case RegOps.USHR:
-            case RegOps.REM: {
-                resultConstant = simulateMath(insn, result.getBasicType());
-                if (resultConstant != null) {
-                    resultValue = CONSTANT;
-                }
-                break;
+            break;
+          case RegOps.AND:
+            vR = vA & vB;
+            break;
+          case RegOps.OR:
+            vR = vA | vB;
+            break;
+          case RegOps.XOR:
+            vR = vA ^ vB;
+            break;
+          case RegOps.SHL:
+            vR = vA << vB;
+            break;
+          case RegOps.SHR:
+            vR = vA >> vB;
+            break;
+          case RegOps.USHR:
+            vR = vA >>> vB;
+            break;
+          case RegOps.REM:
+            if (vB == 0) {
+              skip = true;
+              vR = 0; // just to hide a warning
+            } else {
+              vR = vA % vB;
             }
-            case RegOps.MOVE_RESULT_PSEUDO: {
-                if (latticeValues[resultReg] == CONSTANT) {
-                    resultValue = latticeValues[resultReg];
-                    resultConstant = latticeConstants[resultReg];
-                }
-                break;
-            }
-            // TODO: Handle non-int arithmetic.
-            // TODO: Eliminate check casts that we can prove the type of.
-            default: {}
+            break;
+          default:
+            throw new RuntimeException("Unexpected op");
         }
-        if (setLatticeValueTo(resultReg, resultValue, resultConstant)) {
-            addUsersToWorklist(resultReg, resultValue);
-        }
+
+        return skip ? null : CstInteger.make(vR);
+
+      default:
+        // not yet supported
+        return null;
+    }
+  }
+
+  /**
+   * Simulates a statement and set the result lattice value.
+   * @param insn instruction to simulate
+   */
+  private void simulateStmt(SsaInsn insn) {
+    Insn ropInsn = insn.getOriginalRopInsn();
+    if (ropInsn.getOpcode().getBranchingness() != Rop.BRANCH_NONE
+        || ropInsn.getOpcode().isCallLike()) {
+      simulateBranch(insn);
     }
 
-    private void run() {
-        SsaBasicBlock firstBlock = ssaMeth.getEntryBlock();
-        addBlockToWorklist(firstBlock);
+    int opcode = insn.getOpcode().getOpcode();
+    RegisterSpec result = insn.getResult();
 
-        /* Empty all the worklists by propagating our values */
-        while (!cfgWorklist.isEmpty()
-                || !cfgPhiWorklist.isEmpty()
-                || !ssaWorklist.isEmpty()
-                || !varyingWorklist.isEmpty()) {
-            while (!cfgWorklist.isEmpty()) {
-                int listSize = cfgWorklist.size() - 1;
-                SsaBasicBlock block = cfgWorklist.remove(listSize);
-                simulateBlock(block);
-            }
-
-            while (!cfgPhiWorklist.isEmpty()) {
-                int listSize = cfgPhiWorklist.size() - 1;
-                SsaBasicBlock block = cfgPhiWorklist.remove(listSize);
-                simulatePhiBlock(block);
-            }
-
-            while (!varyingWorklist.isEmpty()) {
-                int listSize = varyingWorklist.size() - 1;
-                SsaInsn insn = varyingWorklist.remove(listSize);
-
-                if (!executableBlocks.get(insn.getBlock().getIndex())) {
-                    continue;
-                }
-
-                if (insn instanceof PhiInsn) {
-                    simulatePhi((PhiInsn)insn);
-                } else {
-                    simulateStmt(insn);
-                }
-            }
-            while (!ssaWorklist.isEmpty()) {
-                int listSize = ssaWorklist.size() - 1;
-                SsaInsn insn = ssaWorklist.remove(listSize);
-
-                if (!executableBlocks.get(insn.getBlock().getIndex())) {
-                    continue;
-                }
-
-                if (insn instanceof PhiInsn) {
-                    simulatePhi((PhiInsn)insn);
-                } else {
-                    simulateStmt(insn);
-                }
-            }
-        }
-
-        replaceConstants();
-        replaceBranches();
+    if (result == null) {
+      // Find move-result-pseudo result for int div and int rem
+      if (opcode == RegOps.DIV || opcode == RegOps.REM) {
+        SsaBasicBlock succ = insn.getBlock().getPrimarySuccessor();
+        result = succ.getInsns().get(0).getResult();
+      } else {
+        return;
+      }
     }
 
-    /**
-     * Replaces TypeBearers in source register specs with constant type
-     * bearers if possible. These are then referenced in later optimization
-     * steps.
-     */
-    private void replaceConstants() {
-        for (int reg = 0; reg < regCount; reg++) {
-            if (latticeValues[reg] != CONSTANT) {
-                continue;
-            }
-            if (!(latticeConstants[reg] instanceof TypedConstant)) {
-                // We can't do much with these
-                continue;
-            }
+    int resultReg = result.getReg();
+    int resultValue = VARYING;
+    Constant resultConstant = null;
 
-            SsaInsn defn = ssaMeth.getDefinitionForRegister(reg);
-            TypeBearer typeBearer = defn.getResult().getTypeBearer();
-
-            if (typeBearer.isConstant()) {
-                /*
-                 * The definition was a constant already.
-                 * The uses should be as well.
-                 */
-                continue;
-            }
-
-            // Update the destination RegisterSpec with the constant value
-            RegisterSpec dest = defn.getResult();
-            RegisterSpec newDest
-                    = dest.withType((TypedConstant)latticeConstants[reg]);
-            defn.setResult(newDest);
-
-            /*
-             * Update the sources RegisterSpec's of all non-move uses.
-             * These will be used in later steps.
-             */
-            for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
-                if (insn.isPhiOrMove()) {
-                    continue;
-                }
-
-                NormalSsaInsn nInsn = (NormalSsaInsn) insn;
-                RegisterSpecList sources = insn.getSources();
-
-                int index = sources.indexOfRegister(reg);
-
-                RegisterSpec spec = sources.get(index);
-                RegisterSpec newSpec
-                        = spec.withType((TypedConstant)latticeConstants[reg]);
-
-                nInsn.changeOneSource(index, newSpec);
-            }
+    switch (opcode) {
+      case RegOps.CONST: {
+        CstInsn cstInsn = (CstInsn) ropInsn;
+        resultValue = CONSTANT;
+        resultConstant = cstInsn.getConstant();
+        break;
+      }
+      case RegOps.MOVE: {
+        if (insn.getSources().size() == 1) {
+          int sourceReg = insn.getSources().get(0).getReg();
+          resultValue = latticeValues[sourceReg];
+          resultConstant = latticeConstants[sourceReg];
         }
+        break;
+      }
+      case RegOps.ADD:
+      case RegOps.SUB:
+      case RegOps.MUL:
+      case RegOps.DIV:
+      case RegOps.AND:
+      case RegOps.OR:
+      case RegOps.XOR:
+      case RegOps.SHL:
+      case RegOps.SHR:
+      case RegOps.USHR:
+      case RegOps.REM: {
+        resultConstant = simulateMath(insn, result.getBasicType());
+        if (resultConstant != null) {
+          resultValue = CONSTANT;
+        }
+        break;
+      }
+      case RegOps.MOVE_RESULT_PSEUDO: {
+        if (latticeValues[resultReg] == CONSTANT) {
+          resultValue = latticeValues[resultReg];
+          resultConstant = latticeConstants[resultReg];
+        }
+        break;
+      }
+    // TODO(dx team): Handle non-int arithmetic.
+    // TODO(dx team): Eliminate check casts that we can prove the type of.
+      default: {
+      }
+    }
+    if (setLatticeValueTo(resultReg, resultValue, resultConstant)) {
+      addUsersToWorklist(resultReg, resultValue);
+    }
+  }
+
+  private void run() {
+    SsaBasicBlock firstBlock = ssaMeth.getEntryBlock();
+    addBlockToWorklist(firstBlock);
+
+    /* Empty all the worklists by propagating our values */
+    while (!cfgWorklist.isEmpty() || !cfgPhiWorklist.isEmpty() || !ssaWorklist.isEmpty()
+        || !varyingWorklist.isEmpty()) {
+      while (!cfgWorklist.isEmpty()) {
+        int listSize = cfgWorklist.size() - 1;
+        SsaBasicBlock block = cfgWorklist.remove(listSize);
+        simulateBlock(block);
+      }
+
+      while (!cfgPhiWorklist.isEmpty()) {
+        int listSize = cfgPhiWorklist.size() - 1;
+        SsaBasicBlock block = cfgPhiWorklist.remove(listSize);
+        simulatePhiBlock(block);
+      }
+
+      while (!varyingWorklist.isEmpty()) {
+        int listSize = varyingWorklist.size() - 1;
+        SsaInsn insn = varyingWorklist.remove(listSize);
+
+        if (!executableBlocks.get(insn.getBlock().getIndex())) {
+          continue;
+        }
+
+        if (insn instanceof PhiInsn) {
+          simulatePhi((PhiInsn) insn);
+        } else {
+          simulateStmt(insn);
+        }
+      }
+      while (!ssaWorklist.isEmpty()) {
+        int listSize = ssaWorklist.size() - 1;
+        SsaInsn insn = ssaWorklist.remove(listSize);
+
+        if (!executableBlocks.get(insn.getBlock().getIndex())) {
+          continue;
+        }
+
+        if (insn instanceof PhiInsn) {
+          simulatePhi((PhiInsn) insn);
+        } else {
+          simulateStmt(insn);
+        }
+      }
     }
 
-    /**
-     * Replaces branches that have constant conditions with gotos
-     */
-    private void replaceBranches() {
-        for (SsaInsn insn : branchWorklist) {
-            // Find if a successor block is never executed
-            int oldSuccessor = -1;
-            SsaBasicBlock block = insn.getBlock();
-            int successorSize = block.getSuccessorList().size();
-            for (int i = 0; i < successorSize; i++) {
-                int successorBlock = block.getSuccessorList().get(i);
-                if (!executableBlocks.get(successorBlock)) {
-                    oldSuccessor = successorBlock;
-                }
-            }
+    replaceConstants();
+    replaceBranches();
+  }
 
-            /*
-             * Prune branches that have already been handled and ones that no
-             * longer have constant conditions (no nonexecutable successors)
-             */
-            if (successorSize != 2 || oldSuccessor == -1) continue;
+  /**
+   * Replaces TypeBearers in source register specs with constant type
+   * bearers if possible. These are then referenced in later optimization
+   * steps.
+   */
+  private void replaceConstants() {
+    for (int reg = 0; reg < regCount; reg++) {
+      if (latticeValues[reg] != CONSTANT) {
+        continue;
+      }
+      if (!(latticeConstants[reg] instanceof TypedConstant)) {
+        // We can't do much with these
+        continue;
+      }
 
-            // Replace branch with goto
-            Insn originalRopInsn = insn.getOriginalRopInsn();
-            block.replaceLastInsn(new PlainInsn(Rops.GOTO,
-                originalRopInsn.getPosition(), null, RegisterSpecList.EMPTY));
-            block.removeSuccessor(oldSuccessor);
+      SsaInsn defn = ssaMeth.getDefinitionForRegister(reg);
+      TypeBearer typeBearer = defn.getResult().getTypeBearer();
+
+      if (typeBearer.isConstant()) {
+        /*
+         * The definition was a constant already.
+         * The uses should be as well.
+         */
+        continue;
+      }
+
+      // Update the destination RegisterSpec with the constant value
+      RegisterSpec dest = defn.getResult();
+      RegisterSpec newDest = dest.withType((TypedConstant) latticeConstants[reg]);
+      defn.setResult(newDest);
+
+      /*
+       * Update the sources RegisterSpec's of all non-move uses.
+       * These will be used in later steps.
+       */
+      for (SsaInsn insn : ssaMeth.getUseListForRegister(reg)) {
+        if (insn.isPhiOrMove()) {
+          continue;
         }
+
+        NormalSsaInsn nInsn = (NormalSsaInsn) insn;
+        RegisterSpecList sources = insn.getSources();
+
+        int index = sources.indexOfRegister(reg);
+
+        RegisterSpec spec = sources.get(index);
+        RegisterSpec newSpec = spec.withType((TypedConstant) latticeConstants[reg]);
+
+        nInsn.changeOneSource(index, newSpec);
+      }
     }
+  }
+
+  /**
+   * Replaces branches that have constant conditions with gotos
+   */
+  private void replaceBranches() {
+    for (SsaInsn insn : branchWorklist) {
+      // Find if a successor block is never executed
+      int oldSuccessor = -1;
+      SsaBasicBlock block = insn.getBlock();
+      int successorSize = block.getSuccessorList().size();
+      for (int i = 0; i < successorSize; i++) {
+        int successorBlock = block.getSuccessorList().get(i);
+        if (!executableBlocks.get(successorBlock)) {
+          oldSuccessor = successorBlock;
+        }
+      }
+
+      /*
+       * Prune branches that have already been handled and ones that no
+       * longer have constant conditions (no nonexecutable successors)
+       */
+      if (successorSize != 2 || oldSuccessor == -1) {
+        continue;
+      }
+
+      // Replace branch with goto
+      Insn originalRopInsn = insn.getOriginalRopInsn();
+      block.replaceLastInsn(
+          new PlainInsn(Rops.GOTO, originalRopInsn.getPosition(), null, RegisterSpecList.EMPTY));
+      block.removeSuccessor(oldSuccessor);
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SetFactory.java b/dx/src/com/android/jack/dx/ssa/SetFactory.java
index 9c24b8b..0d92d20 100644
--- a/dx/src/com/android/jack/dx/ssa/SetFactory.java
+++ b/dx/src/com/android/jack/dx/ssa/SetFactory.java
@@ -26,70 +26,65 @@
  */
 public final class SetFactory {
 
-    /**
-     * BitIntSet/ListIntSet threshold for dominance frontier sets. These
-     * sets are kept per basic block until phi placement and tend to be,
-     * like the CFG itself, very sparse at large sizes.
-     *
-     * A value of 3072 here is somewhere around 1.125mb of total bitset size.
-     */
-    private static final int DOMFRONT_SET_THRESHOLD_SIZE = 3072;
+  /**
+   * BitIntSet/ListIntSet threshold for dominance frontier sets. These
+   * sets are kept per basic block until phi placement and tend to be,
+   * like the CFG itself, very sparse at large sizes.
+   *
+   * A value of 3072 here is somewhere around 1.125mb of total bitset size.
+   */
+  private static final int DOMFRONT_SET_THRESHOLD_SIZE = 3072;
 
-    /**
-     * BitIntSet/ListIntSet threshold for interference graph sets. These
-     * sets are kept per register until register allocation is done.
-     *
-     * A value of 3072 here is somewhere around 1.125mb of total bitset size.
-     */
-    private static final int INTERFERENCE_SET_THRESHOLD_SIZE = 3072;
+  /**
+   * BitIntSet/ListIntSet threshold for interference graph sets. These
+   * sets are kept per register until register allocation is done.
+   *
+   * A value of 3072 here is somewhere around 1.125mb of total bitset size.
+   */
+  private static final int INTERFERENCE_SET_THRESHOLD_SIZE = 3072;
 
-    /**
-     * BitIntSet/ListIntSet threshold for the live in/out sets kept by
-     * {@link SsaBasicBlock}. These are sets of SSA registers kept per basic
-     * block during register allocation.
-     *
-     * The total size of a bitset for this would be the count of blocks
-     * times the size of registers. The threshold value here is merely
-     * the register count, which is typically on the order of the block
-     * count as well.
-     */
-    private static final int LIVENESS_SET_THRESHOLD_SIZE = 3072;
+  /**
+   * BitIntSet/ListIntSet threshold for the live in/out sets kept by
+   * {@link SsaBasicBlock}. These are sets of SSA registers kept per basic
+   * block during register allocation.
+   *
+   * The total size of a bitset for this would be the count of blocks
+   * times the size of registers. The threshold value here is merely
+   * the register count, which is typically on the order of the block
+   * count as well.
+   */
+  private static final int LIVENESS_SET_THRESHOLD_SIZE = 3072;
 
 
-    /**
-     * Make IntSet for the dominance-frontier sets.
-     *
-     * @param szBlocks {@code >=0;} count of basic blocks in method
-     * @return {@code non-null;} appropriate set
-     */
-    /*package*/ static IntSet makeDomFrontSet(int szBlocks) {
-        return szBlocks <= DOMFRONT_SET_THRESHOLD_SIZE
-                ? new BitIntSet(szBlocks)
-                : new ListIntSet();
-    }
+  /**
+   * Make IntSet for the dominance-frontier sets.
+   *
+   * @param szBlocks {@code >=0;} count of basic blocks in method
+   * @return {@code non-null;} appropriate set
+   */
+  /*package*/static IntSet makeDomFrontSet(int szBlocks) {
+    return szBlocks <= DOMFRONT_SET_THRESHOLD_SIZE ? new BitIntSet(szBlocks) : new ListIntSet();
+  }
 
-    /**
-     * Make IntSet for the interference graph sets. Public because
-     * InterferenceGraph is in another package.
-     *
-     * @param countRegs {@code >=0;} count of SSA registers used in method
-     * @return {@code non-null;} appropriate set
-     */
-    public static IntSet makeInterferenceSet(int countRegs) {
-        return countRegs <= INTERFERENCE_SET_THRESHOLD_SIZE
-                ? new BitIntSet(countRegs)
-                : new ListIntSet();
-    }
+  /**
+   * Make IntSet for the interference graph sets. Public because
+   * InterferenceGraph is in another package.
+   *
+   * @param countRegs {@code >=0;} count of SSA registers used in method
+   * @return {@code non-null;} appropriate set
+   */
+  public static IntSet makeInterferenceSet(int countRegs) {
+    return countRegs <= INTERFERENCE_SET_THRESHOLD_SIZE ? new BitIntSet(countRegs)
+        : new ListIntSet();
+  }
 
-    /**
-     * Make IntSet for register live in/out sets.
-     *
-     * @param countRegs {@code >=0;} count of SSA registers used in method
-     * @return {@code non-null;} appropriate set
-     */
-    /*package*/ static IntSet makeLivenessSet(int countRegs) {
-        return countRegs <= LIVENESS_SET_THRESHOLD_SIZE
-                ? new BitIntSet(countRegs)
-                : new ListIntSet();
-    }
+  /**
+   * Make IntSet for register live in/out sets.
+   *
+   * @param countRegs {@code >=0;} count of SSA registers used in method
+   * @return {@code non-null;} appropriate set
+   */
+  /*package*/static IntSet makeLivenessSet(int countRegs) {
+    return countRegs <= LIVENESS_SET_THRESHOLD_SIZE ? new BitIntSet(countRegs) : new ListIntSet();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SsaBasicBlock.java b/dx/src/com/android/jack/dx/ssa/SsaBasicBlock.java
index 4217184..2d16474 100644
--- a/dx/src/com/android/jack/dx/ssa/SsaBasicBlock.java
+++ b/dx/src/com/android/jack/dx/ssa/SsaBasicBlock.java
@@ -41,992 +41,962 @@
  * An SSA representation of a basic block.
  */
 public final class SsaBasicBlock {
-    /**
-     * {@code non-null;} comparator for instances of this class that
-     * just compares block labels
-     */
-    public static final Comparator<SsaBasicBlock> LABEL_COMPARATOR =
-        new LabelComparator();
 
-    /** {@code non-null;} insn list associated with this instance */
-    private ArrayList<SsaInsn> insns;
+  public static boolean enablePhisBeforeMoveException = false;
 
-    /** {@code non-null;} predecessor set (by block list index) */
-    private BitSet predecessors;
+  /**
+   * {@code non-null;} comparator for instances of this class that
+   * just compares block labels
+   */
+  public static final Comparator<SsaBasicBlock> LABEL_COMPARATOR = new LabelComparator();
 
-    /** {@code non-null;} successor set (by block list index) */
-    private BitSet successors;
+  /** {@code non-null;} insn list associated with this instance */
+  private ArrayList<SsaInsn> insns;
 
-    /**
-     * {@code non-null;} ordered successor list
-     * (same block may be listed more than once)
-     */
-    private IntList successorList;
+  /** {@code non-null;} predecessor set (by block list index) */
+  private BitSet predecessors;
 
-    /**
-     * block list index of primary successor, or {@code -1} for no primary
-     * successor
-     */
-    private int primarySuccessor = -1;
+  /** {@code non-null;} successor set (by block list index) */
+  private BitSet successors;
 
-    /** label of block in rop form */
-    private int ropLabel;
+  /**
+   * {@code non-null;} ordered successor list
+   * (same block may be listed more than once)
+   */
+  private IntList successorList;
 
-    /** {@code non-null;} method we belong to */
-    private SsaMethod parent;
+  /**
+   * block list index of primary successor, or {@code -1} for no primary
+   * successor
+   */
+  private int primarySuccessor = -1;
 
-    /** our index into parent.getBlock() */
-    private int index;
+  /** label of block in rop form */
+  private int ropLabel;
 
-    /** list of dom children */
-    private final ArrayList<SsaBasicBlock> domChildren;
+  /** {@code non-null;} method we belong to */
+  private SsaMethod parent;
 
-    /**
-     * the number of moves added to the end of the block during the
-     * phi-removal process. Retained for subsequent move scheduling.
-     */
-    private int movesFromPhisAtEnd = 0;
+  /** our index into parent.getBlock() */
+  private int index;
 
-    /**
-     * the number of moves added to the beginning of the block during the
-     * phi-removal process. Retained for subsequent move scheduling.
-     */
-    private int movesFromPhisAtBeginning = 0;
+  /** list of dom children */
+  private final ArrayList<SsaBasicBlock> domChildren;
 
-    /**
-     * contains last computed value of reachability of this block, or -1
-     * if reachability hasn't been calculated yet
-     */
-    private int reachable = -1;
+  /**
+   * the number of moves added to the end of the block during the
+   * phi-removal process. Retained for subsequent move scheduling.
+   */
+  private int movesFromPhisAtEnd = 0;
 
-    /**
-     * {@code null-ok;} indexed by reg: the regs that are live-in at
-     * this block
-     */
-    private IntSet liveIn;
+  /**
+   * the number of moves added to the beginning of the block during the
+   * phi-removal process. Retained for subsequent move scheduling.
+   */
+  private int movesFromPhisAtBeginning = 0;
 
-    /**
-     * {@code null-ok;} indexed by reg: the regs that are live-out at
-     * this block
-     */
-    private IntSet liveOut;
+  /**
+   * contains last computed value of reachability of this block, or -1
+   * if reachability hasn't been calculated yet
+   */
+  private int reachable = -1;
 
-    /**
-     * Creates a new empty basic block.
-     *
-     * @param basicBlockIndex index this block will have
-     * @param ropLabel original rop-form label
-     * @param parent method of this block
-     */
-    public SsaBasicBlock(final int basicBlockIndex, final int ropLabel,
-            final SsaMethod parent) {
-        this.parent = parent;
-        this.index = basicBlockIndex;
-        this.insns = new ArrayList<SsaInsn>();
-        this.ropLabel = ropLabel;
+  /**
+   * {@code null-ok;} indexed by reg: the regs that are live-in at
+   * this block
+   */
+  private IntSet liveIn;
 
-        this.predecessors = new BitSet(parent.getBlocks().size());
-        this.successors = new BitSet(parent.getBlocks().size());
-        this.successorList = new IntList();
+  /**
+   * {@code null-ok;} indexed by reg: the regs that are live-out at
+   * this block
+   */
+  private IntSet liveOut;
 
-        domChildren = new ArrayList<SsaBasicBlock>();
+  /**
+   * Creates a new empty basic block.
+   *
+   * @param basicBlockIndex index this block will have
+   * @param ropLabel original rop-form label
+   * @param parent method of this block
+   */
+  public SsaBasicBlock(final int basicBlockIndex, final int ropLabel, final SsaMethod parent) {
+    this.parent = parent;
+    this.index = basicBlockIndex;
+    this.insns = new ArrayList<SsaInsn>();
+    this.ropLabel = ropLabel;
+
+    this.predecessors = new BitSet(parent.getBlocks().size());
+    this.successors = new BitSet(parent.getBlocks().size());
+    this.successorList = new IntList();
+
+    domChildren = new ArrayList<SsaBasicBlock>();
+  }
+
+  /**
+   * Creates a new SSA basic block from a ROP form basic block.
+   *
+   * @param rmeth original method
+   * @param basicBlockIndex index this block will have
+   * @param parent method of this block predecessor set will be
+   * updated
+   * @return new instance
+   */
+  public static SsaBasicBlock newFromRop(RopMethod rmeth, int basicBlockIndex,
+      final SsaMethod parent) {
+    BasicBlockList ropBlocks = rmeth.getBlocks();
+    BasicBlock bb = ropBlocks.get(basicBlockIndex);
+    SsaBasicBlock result = new SsaBasicBlock(basicBlockIndex, bb.getLabel(), parent);
+    InsnList ropInsns = bb.getInsns();
+
+    result.insns.ensureCapacity(ropInsns.size());
+
+    for (int i = 0, sz = ropInsns.size(); i < sz; i++) {
+      result.insns.add(new NormalSsaInsn(ropInsns.get(i), result));
     }
 
-    /**
-     * Creates a new SSA basic block from a ROP form basic block.
-     *
-     * @param rmeth original method
-     * @param basicBlockIndex index this block will have
-     * @param parent method of this block predecessor set will be
-     * updated
-     * @return new instance
-     */
-    public static SsaBasicBlock newFromRop(RopMethod rmeth,
-            int basicBlockIndex, final SsaMethod parent) {
-        BasicBlockList ropBlocks = rmeth.getBlocks();
-        BasicBlock bb = ropBlocks.get(basicBlockIndex);
-        SsaBasicBlock result =
-            new SsaBasicBlock(basicBlockIndex, bb.getLabel(), parent);
-        InsnList ropInsns = bb.getInsns();
+    result.predecessors =
+        SsaMethod.bitSetFromLabelList(ropBlocks, rmeth.labelToPredecessors(bb.getLabel()));
 
-        result.insns.ensureCapacity(ropInsns.size());
+    result.successors = SsaMethod.bitSetFromLabelList(ropBlocks, bb.getSuccessors());
 
-        for (int i = 0, sz = ropInsns.size() ; i < sz ; i++) {
-            result.insns.add(new NormalSsaInsn (ropInsns.get(i), result));
-        }
+    result.successorList = SsaMethod.indexListFromLabelList(ropBlocks, bb.getSuccessors());
 
-        result.predecessors = SsaMethod.bitSetFromLabelList(
-                ropBlocks,
-                rmeth.labelToPredecessors(bb.getLabel()));
+    if (result.successorList.size() != 0) {
+      int primarySuccessor = bb.getPrimarySuccessor();
 
-        result.successors
-                = SsaMethod.bitSetFromLabelList(ropBlocks, bb.getSuccessors());
-
-        result.successorList
-                = SsaMethod.indexListFromLabelList(ropBlocks,
-                    bb.getSuccessors());
-
-        if (result.successorList.size() != 0) {
-            int primarySuccessor = bb.getPrimarySuccessor();
-
-            result.primarySuccessor = (primarySuccessor < 0)
-                    ? -1 : ropBlocks.indexOfLabel(primarySuccessor);
-        }
-
-        return result;
+      result.primarySuccessor =
+          (primarySuccessor < 0) ? -1 : ropBlocks.indexOfLabel(primarySuccessor);
     }
 
-    /**
-     * Adds a basic block as a dom child for this block. Used when constructing
-     * the dom tree.
-     *
-     * @param child {@code non-null;} new dom child
-     */
-    public void addDomChild(SsaBasicBlock child) {
-        domChildren.add(child);
+    return result;
+  }
+
+  /**
+   * Adds a basic block as a dom child for this block. Used when constructing
+   * the dom tree.
+   *
+   * @param child {@code non-null;} new dom child
+   */
+  public void addDomChild(SsaBasicBlock child) {
+    domChildren.add(child);
+  }
+
+  /**
+   * Gets the dom children for this node. Don't modify this list.
+   *
+   * @return {@code non-null;} list of dom children
+   */
+  public ArrayList<SsaBasicBlock> getDomChildren() {
+    return domChildren;
+  }
+
+  /**
+   * Adds a phi insn to the beginning of this block. The result type of
+   * the phi will be set to void, to indicate that it's currently unknown.
+   *
+   * @param reg {@code >=0;} result reg
+   */
+  public void addPhiInsnForReg(int reg) {
+    insns.add(0, new PhiInsn(reg, this));
+  }
+
+  /**
+   * Adds a phi insn to the beginning of this block. This is to be used
+   * when the result type or local-association can be determined at phi
+   * insert time.
+   *
+   * @param resultSpec {@code non-null;} reg
+   */
+  public void addPhiInsnForReg(RegisterSpec resultSpec) {
+    insns.add(0, new PhiInsn(resultSpec, this));
+  }
+
+  /**
+   * Adds an insn to the head of this basic block, just after any phi
+   * insns.
+   *
+   * @param insn {@code non-null;} rop-form insn to add
+   */
+  public void addInsnToHead(Insn insn) {
+    SsaInsn newInsn = SsaInsn.makeFromRop(insn, this);
+    insns.add(getCountPhiInsns(), newInsn);
+    parent.onInsnAdded(newInsn);
+  }
+
+  /**
+   * Replaces the last insn in this block. The provided insn must have
+   * some branchingness.
+   *
+   * @param insn {@code non-null;} rop-form insn to add, which must branch.
+   */
+  public void replaceLastInsn(Insn insn) {
+    if (insn.getOpcode().getBranchingness() == Rop.BRANCH_NONE) {
+      throw new IllegalArgumentException("last insn must branch");
     }
 
-    /**
-     * Gets the dom children for this node. Don't modify this list.
-     *
-     * @return {@code non-null;} list of dom children
-     */
-    public ArrayList<SsaBasicBlock> getDomChildren() {
-        return domChildren;
-    }
+    SsaInsn oldInsn = insns.get(insns.size() - 1);
+    SsaInsn newInsn = SsaInsn.makeFromRop(insn, this);
 
-    /**
-     * Adds a phi insn to the beginning of this block. The result type of
-     * the phi will be set to void, to indicate that it's currently unknown.
-     *
-     * @param reg {@code >=0;} result reg
-     */
-    public void addPhiInsnForReg(int reg) {
-        insns.add(0, new PhiInsn(reg, this));
-    }
+    insns.set(insns.size() - 1, newInsn);
 
-    /**
-     * Adds a phi insn to the beginning of this block. This is to be used
-     * when the result type or local-association can be determined at phi
-     * insert time.
-     *
-     * @param resultSpec {@code non-null;} reg
-     */
-    public void addPhiInsnForReg(RegisterSpec resultSpec) {
-        insns.add(0, new PhiInsn(resultSpec, this));
-    }
+    parent.onInsnRemoved(oldInsn);
+    parent.onInsnAdded(newInsn);
+  }
 
-    /**
-     * Adds an insn to the head of this basic block, just after any phi
-     * insns.
-     *
-     * @param insn {@code non-null;} rop-form insn to add
-     */
-    public void addInsnToHead(Insn insn) {
-        SsaInsn newInsn = SsaInsn.makeFromRop(insn, this);
-        insns.add(getCountPhiInsns(), newInsn);
-        parent.onInsnAdded(newInsn);
-    }
+  /**
+   * Visits each phi insn.
+   *
+   * @param v {@code non-null;} the callback
+   */
+  public void forEachPhiInsn(PhiInsn.Visitor v) {
+    int sz = insns.size();
 
-    /**
-     * Replaces the last insn in this block. The provided insn must have
-     * some branchingness.
-     *
-     * @param insn {@code non-null;} rop-form insn to add, which must branch.
-     */
-    public void replaceLastInsn(Insn insn) {
-        if (insn.getOpcode().getBranchingness() == Rop.BRANCH_NONE) {
-            throw new IllegalArgumentException("last insn must branch");
-        }
-
-        SsaInsn oldInsn = insns.get(insns.size() - 1);
-        SsaInsn newInsn = SsaInsn.makeFromRop(insn, this);
-
-        insns.set(insns.size() - 1, newInsn);
-
-        parent.onInsnRemoved(oldInsn);
-        parent.onInsnAdded(newInsn);
-    }
-
-    /**
-     * Visits each phi insn.
-     *
-     * @param v {@code non-null;} the callback
-     */
-    public void forEachPhiInsn(PhiInsn.Visitor v) {
-        int sz = insns.size();
-
-        for (int i = 0; i < sz; i++) {
-            SsaInsn insn = insns.get(i);
-            if (insn instanceof PhiInsn) {
-                v.visitPhiInsn((PhiInsn) insn);
-            } else {
-                /*
-                 * Presently we assume PhiInsn's are in a continuous
-                 * block at the top of the list
-                 */
-                break;
-            }
-        }
-    }
-
-    /**
-     * Deletes all phi insns. Do this after adding appropriate move insns.
-     */
-    public void removeAllPhiInsns() {
+    for (int i = 0; i < sz; i++) {
+      SsaInsn insn = insns.get(i);
+      if (insn instanceof PhiInsn) {
+        v.visitPhiInsn((PhiInsn) insn);
+      } else {
         /*
          * Presently we assume PhiInsn's are in a continuous
-         * block at the top of the list.
+         * block at the top of the list
          */
+        break;
+      }
+    }
+  }
 
-        insns.subList(0, getCountPhiInsns()).clear();
+  /**
+   * Deletes all phi insns. Do this after adding appropriate move insns.
+   */
+  public void removeAllPhiInsns() {
+    /*
+     * Presently we assume PhiInsn's are in a continuous
+     * block at the top of the list.
+     */
+
+insns.subList(0, getCountPhiInsns()).clear();
+  }
+
+  /**
+   * Gets the number of phi insns at the top of this basic block.
+   *
+   * @return count of phi insns
+   */
+  private int getCountPhiInsns() {
+    int countPhiInsns;
+
+    int sz = insns.size();
+    for (countPhiInsns = 0; countPhiInsns < sz; countPhiInsns++) {
+      SsaInsn insn = insns.get(countPhiInsns);
+      if (!(insn instanceof PhiInsn)) {
+        break;
+      }
     }
 
-    /**
-     * Gets the number of phi insns at the top of this basic block.
-     *
-     * @return count of phi insns
-     */
-    private int getCountPhiInsns() {
-        int countPhiInsns;
+    return countPhiInsns;
+  }
 
-        int sz = insns.size();
-        for (countPhiInsns = 0; countPhiInsns < sz; countPhiInsns++) {
-            SsaInsn insn = insns.get(countPhiInsns);
-            if (!(insn instanceof PhiInsn)) {
-                break;
-            }
-        }
+  /**
+   * @return {@code non-null;} the (mutable) instruction list for this block,
+   * with phi insns at the beginning
+   */
+  public ArrayList<SsaInsn> getInsns() {
+    return insns;
+  }
 
-        return countPhiInsns;
+  /**
+   * @return {@code non-null;} the (mutable) list of phi insns for this block
+   */
+  public List<SsaInsn> getPhiInsns() {
+    return insns.subList(0, getCountPhiInsns());
+  }
+
+  /**
+   * @return the block index of this block
+   */
+  public int getIndex() {
+    return index;
+  }
+
+  /**
+   * @return the label of this block in rop form
+   */
+  public int getRopLabel() {
+    return ropLabel;
+  }
+
+  /**
+   * @return the label of this block in rop form as a hex string
+   */
+  public String getRopLabelString() {
+    return Hex.u2(ropLabel);
+  }
+
+  /**
+   * @return {@code non-null;} predecessors set, indexed by block index
+   */
+  public BitSet getPredecessors() {
+    return predecessors;
+  }
+
+  /**
+   * @return {@code non-null;} successors set, indexed by block index
+   */
+  public BitSet getSuccessors() {
+    return successors;
+  }
+
+  /**
+   * @return {@code non-null;} ordered successor list, containing block
+   * indicies
+   */
+  public IntList getSuccessorList() {
+    return successorList;
+  }
+
+  /**
+   * @return {@code >= -1;} block index of primary successor or
+   * {@code -1} if no primary successor
+   */
+  public int getPrimarySuccessorIndex() {
+    return primarySuccessor;
+  }
+
+  /**
+   * @return rop label of primary successor
+   */
+  public int getPrimarySuccessorRopLabel() {
+    return parent.blockIndexToRopLabel(primarySuccessor);
+  }
+
+  /**
+   * @return {@code null-ok;} the primary successor block or {@code null}
+   * if there is none
+   */
+  public SsaBasicBlock getPrimarySuccessor() {
+    if (primarySuccessor < 0) {
+      return null;
+    } else {
+      return parent.getBlocks().get(primarySuccessor);
+    }
+  }
+
+  /**
+   * @return successor list of rop labels
+   */
+  public IntList getRopLabelSuccessorList() {
+    IntList result = new IntList(successorList.size());
+
+    int sz = successorList.size();
+
+    for (int i = 0; i < sz; i++) {
+      result.add(parent.blockIndexToRopLabel(successorList.get(i)));
+    }
+    return result;
+  }
+
+  /**
+   * @return {@code non-null;} method that contains this block
+   */
+  public SsaMethod getParent() {
+    return parent;
+  }
+
+  /**
+   * Inserts a new empty GOTO block as a predecessor to this block.
+   * All previous predecessors will be predecessors to the new block.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public SsaBasicBlock insertNewPredecessor() {
+    SsaBasicBlock newPred = parent.makeNewGotoBlock();
+
+    // Update the new block.
+    newPred.predecessors = predecessors;
+    newPred.successors.set(index);
+    newPred.successorList.add(index);
+    newPred.primarySuccessor = index;
+
+
+    // Update us.
+    predecessors = new BitSet(parent.getBlocks().size());
+    predecessors.set(newPred.index);
+
+    // Update our (soon-to-be) old predecessors.
+    for (int i = newPred.predecessors.nextSetBit(0); i >= 0;
+        i = newPred.predecessors.nextSetBit(i + 1)) {
+
+      SsaBasicBlock predBlock = parent.getBlocks().get(i);
+
+      predBlock.replaceSuccessor(index, newPred.index);
     }
 
-    /**
-     * @return {@code non-null;} the (mutable) instruction list for this block,
-     * with phi insns at the beginning
-     */
-    public ArrayList<SsaInsn> getInsns() {
-        return insns;
+    return newPred;
+  }
+
+  /**
+   * Constructs and inserts a new empty GOTO block {@code Z} between
+   * this block ({@code A}) and a current successor block
+   * ({@code B}). The new block will replace B as A's successor and
+   * A as B's predecessor. A and B will no longer be directly connected.
+   * If B is listed as a successor multiple times, all references
+   * are replaced.
+   *
+   * @param other current successor (B)
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public SsaBasicBlock insertNewSuccessor(SsaBasicBlock other) {
+    SsaBasicBlock newSucc = parent.makeNewGotoBlock();
+
+    if (!successors.get(other.index)) {
+      throw new RuntimeException(
+          "Block " + other.getRopLabelString() + " not successor of " + getRopLabelString());
     }
 
-    /**
-     * @return {@code non-null;} the (mutable) list of phi insns for this block
-     */
-    public List<SsaInsn> getPhiInsns() {
-        return insns.subList(0, getCountPhiInsns());
+    // Update the new block.
+    newSucc.predecessors.set(this.index);
+    newSucc.successors.set(other.index);
+    newSucc.successorList.add(other.index);
+    newSucc.primarySuccessor = other.index;
+
+    // Update us.
+    for (int i = successorList.size() - 1; i >= 0; i--) {
+      if (successorList.get(i) == other.index) {
+        successorList.set(i, newSucc.index);
+      }
     }
 
-    /**
-     * @return the block index of this block
-     */
-    public int getIndex() {
-        return index;
+    if (primarySuccessor == other.index) {
+      primarySuccessor = newSucc.index;
+    }
+    successors.clear(other.index);
+    successors.set(newSucc.index);
+
+    // Update "other".
+    other.predecessors.set(newSucc.index);
+    other.predecessors.set(index, successors.get(other.index));
+
+    return newSucc;
+  }
+
+  /**
+   * Replaces an old successor with a new successor. This will throw
+   * RuntimeException if {@code oldIndex} was not a successor.
+   *
+   * @param oldIndex index of old successor block
+   * @param newIndex index of new successor block
+   */
+  public void replaceSuccessor(int oldIndex, int newIndex) {
+    if (oldIndex == newIndex) {
+      return;
     }
 
-    /**
-     * @return the label of this block in rop form
-     */
-    public int getRopLabel() {
-        return ropLabel;
+    // Update us.
+    successors.set(newIndex);
+
+    if (primarySuccessor == oldIndex) {
+      primarySuccessor = newIndex;
     }
 
-    /**
-     * @return the label of this block in rop form as a hex string
-     */
-    public String getRopLabelString() {
-        return Hex.u2(ropLabel);
+    for (int i = successorList.size() - 1; i >= 0; i--) {
+      if (successorList.get(i) == oldIndex) {
+        successorList.set(i, newIndex);
+      }
     }
 
-    /**
-     * @return {@code non-null;} predecessors set, indexed by block index
-     */
-    public BitSet getPredecessors() {
-        return predecessors;
+    successors.clear(oldIndex);
+
+    // Update new successor.
+    parent.getBlocks().get(newIndex).predecessors.set(index);
+
+    // Update old successor.
+    parent.getBlocks().get(oldIndex).predecessors.clear(index);
+  }
+
+  /**
+   * Removes a successor from this block's successor list.
+   *
+   * @param oldIndex index of successor block to remove
+   */
+  public void removeSuccessor(int oldIndex) {
+    int removeIndex = 0;
+
+    for (int i = successorList.size() - 1; i >= 0; i--) {
+      if (successorList.get(i) == oldIndex) {
+        removeIndex = i;
+      } else {
+        primarySuccessor = successorList.get(i);
+      }
     }
 
-    /**
-     * @return {@code non-null;} successors set, indexed by block index
-     */
-    public BitSet getSuccessors() {
-        return successors;
+    successorList.removeIndex(removeIndex);
+    successors.clear(oldIndex);
+    parent.getBlocks().get(oldIndex).predecessors.clear(index);
+  }
+
+  /**
+   * Attaches block to an exit block if necessary. If this block
+   * is not an exit predecessor or is the exit block, this block does
+   * nothing. For use by {@link com.android.jack.dx.ssa.SsaMethod#makeExitBlock}
+   *
+   * @param exitBlock {@code non-null;} exit block
+   */
+  public void exitBlockFixup(SsaBasicBlock exitBlock) {
+    if (this == exitBlock) {
+      return;
     }
 
-    /**
-     * @return {@code non-null;} ordered successor list, containing block
-     * indicies
-     */
-    public IntList getSuccessorList() {
-        return successorList;
+    if (successorList.size() == 0) {
+      /*
+       * This is an exit predecessor.
+       * Set the successor to the exit block
+       */
+      successors.set(exitBlock.index);
+      successorList.add(exitBlock.index);
+      primarySuccessor = exitBlock.index;
+      exitBlock.predecessors.set(this.index);
+    }
+  }
+
+  /**
+   * Adds a move instruction to the end of this basic block, just
+   * before the last instruction. If the result of the final instruction
+   * is the source in question, then the move is placed at the beginning of
+   * the primary successor block. This is for unversioned registers.
+   *
+   * @param result move destination
+   * @param source move source
+   */
+  public void addMoveToEnd(RegisterSpec result, RegisterSpec source) {
+
+    if (result.getReg() == source.getReg()) {
+      // Sometimes we end up with no-op moves. Ignore them here.
+      return;
     }
 
-    /**
-     * @return {@code >= -1;} block index of primary successor or
-     * {@code -1} if no primary successor
+    /*
+     * The last Insn has to be a normal SSA insn: a phi can't branch
+     * or return or cause an exception, etc.
      */
-    public int getPrimarySuccessorIndex() {
-        return primarySuccessor;
+    NormalSsaInsn lastInsn;
+    lastInsn = (NormalSsaInsn) insns.get(insns.size() - 1);
+
+    if (lastInsn.getResult() != null || lastInsn.getSources().size() > 0) {
+      /*
+       * The final insn in this block has a source or result
+       * register, and the moves we may need to place and
+       * schedule may interfere. We need to insert this
+       * instruction at the beginning of the primary successor
+       * block instead. We know this is safe, because when we
+       * edge-split earlier, we ensured that each successor has
+       * only us as a predecessor.
+       */
+
+for (int i = successors.nextSetBit(0); i >= 0; i = successors.nextSetBit(i + 1)) {
+
+        SsaBasicBlock succ;
+
+        succ = parent.getBlocks().get(i);
+        succ.addMoveToBeginning(result, source);
+      }
+    } else {
+      /*
+       * We can safely add a move to the end of the block just
+       * before the last instruction, because the final insn does
+       * not assign to anything.
+       */
+      RegisterSpecList sources = RegisterSpecList.make(source);
+      NormalSsaInsn toAdd = new NormalSsaInsn(
+          new PlainInsn(Rops.opMove(result.getType()), SourcePosition.NO_INFO, result, sources),
+          this);
+
+      insns.add(insns.size() - 1, toAdd);
+
+      movesFromPhisAtEnd++;
+    }
+  }
+
+  /**
+   * Adds a move instruction after the phi insn block.
+   *
+   * @param result move destination
+   * @param source move source
+   */
+  public void addMoveToBeginning(RegisterSpec result, RegisterSpec source) {
+    if (result.getReg() == source.getReg()) {
+      // Sometimes we end up with no-op moves. Ignore them here.
+      return;
     }
 
-    /**
-     * @return rop label of primary successor
-     */
-    public int getPrimarySuccessorRopLabel() {
-        return parent.blockIndexToRopLabel(primarySuccessor);
+    RegisterSpecList sources = RegisterSpecList.make(source);
+    NormalSsaInsn toAdd = new NormalSsaInsn(
+        new PlainInsn(Rops.opMove(result.getType()), SourcePosition.NO_INFO, result, sources),
+        this);
+
+    insns.add(getCountPhiInsns(), toAdd);
+    movesFromPhisAtBeginning++;
+  }
+
+  /**
+   * Sets the register as used in a bitset, taking into account its
+   * category/width.
+   *
+   * @param regsUsed set, indexed by register number
+   * @param rs register to mark as used
+   */
+  private static void setRegsUsed(BitSet regsUsed, RegisterSpec rs) {
+    regsUsed.set(rs.getReg());
+    if (rs.getCategory() > 1) {
+      regsUsed.set(rs.getReg() + 1);
     }
+  }
 
-    /**
-     * @return {@code null-ok;} the primary successor block or {@code null}
-     * if there is none
-     */
-    public SsaBasicBlock getPrimarySuccessor() {
-        if (primarySuccessor < 0) {
-            return null;
-        } else {
-            return parent.getBlocks().get(primarySuccessor);
-        }
-    }
+  /**
+   * Checks to see if the register is used in a bitset, taking
+   * into account its category/width.
+   *
+   * @param regsUsed set, indexed by register number
+   * @param rs register to mark as used
+   * @return true if register is fully or partially (for the case of wide
+   * registers) used.
+   */
+  private static boolean checkRegUsed(BitSet regsUsed, RegisterSpec rs) {
+    int reg = rs.getReg();
+    int category = rs.getCategory();
 
-    /**
-     * @return successor list of rop labels
-     */
-    public IntList getRopLabelSuccessorList() {
-        IntList result = new IntList(successorList.size());
+    return regsUsed.get(reg) || (category == 2 ? regsUsed.get(reg + 1) : false);
+  }
 
-        int sz = successorList.size();
+  /**
+   * Ensures that all move operations in this block occur such that
+   * reads of any register happen before writes to that register.
+   * NOTE: caller is expected to returnSpareRegisters()!
+   *
+   * TODO(dx team): See Briggs, et al "Practical Improvements to the Construction and
+   * Destruction of Static Single Assignment Form" section 5. a) This can
+   * be done in three passes.
+   *
+   * @param toSchedule List of instructions. Must consist only of moves.
+   */
+  private void scheduleUseBeforeAssigned(List<SsaInsn> toSchedule) {
+    BitSet regsUsedAsSources = new BitSet(parent.getRegCount());
 
-        for (int i = 0; i < sz; i++) {
-            result.add(parent.blockIndexToRopLabel(successorList.get(i)));
-        }
-        return result;
-    }
+    // TODO(dx team): Get rid of this.
+    BitSet regsUsedAsResults = new BitSet(parent.getRegCount());
 
-    /**
-     * @return {@code non-null;} method that contains this block
-     */
-    public SsaMethod getParent() {
-        return parent;
-    }
+    int sz = toSchedule.size();
 
-    /**
-     * Inserts a new empty GOTO block as a predecessor to this block.
-     * All previous predecessors will be predecessors to the new block.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public SsaBasicBlock insertNewPredecessor() {
-        SsaBasicBlock newPred = parent.makeNewGotoBlock();
+    int insertPlace = 0;
 
-        // Update the new block.
-        newPred.predecessors = predecessors;
-        newPred.successors.set(index) ;
-        newPred.successorList.add(index);
-        newPred.primarySuccessor = index;
+    while (insertPlace < sz) {
+      int oldInsertPlace = insertPlace;
 
+      // Record all registers used as sources in this block.
+      for (int i = insertPlace; i < sz; i++) {
+        setRegsUsed(regsUsedAsSources, toSchedule.get(i).getSources().get(0));
 
-        // Update us.
-        predecessors = new BitSet(parent.getBlocks().size());
-        predecessors.set(newPred.index);
+        setRegsUsed(regsUsedAsResults, toSchedule.get(i).getResult());
+      }
 
-        // Update our (soon-to-be) old predecessors.
-        for (int i = newPred.predecessors.nextSetBit(0); i >= 0;
-                i = newPred.predecessors.nextSetBit(i + 1)) {
-
-            SsaBasicBlock predBlock = parent.getBlocks().get(i);
-
-            predBlock.replaceSuccessor(index, newPred.index);
-        }
-
-        return newPred;
-    }
-
-    /**
-     * Constructs and inserts a new empty GOTO block {@code Z} between
-     * this block ({@code A}) and a current successor block
-     * ({@code B}). The new block will replace B as A's successor and
-     * A as B's predecessor. A and B will no longer be directly connected.
-     * If B is listed as a successor multiple times, all references
-     * are replaced.
-     *
-     * @param other current successor (B)
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public SsaBasicBlock insertNewSuccessor(SsaBasicBlock other) {
-        SsaBasicBlock newSucc = parent.makeNewGotoBlock();
-
-        if (!successors.get(other.index)) {
-            throw new RuntimeException("Block " + other.getRopLabelString()
-                    + " not successor of " + getRopLabelString());
-        }
-
-        // Update the new block.
-        newSucc.predecessors.set(this.index);
-        newSucc.successors.set(other.index) ;
-        newSucc.successorList.add(other.index);
-        newSucc.primarySuccessor = other.index;
-
-        // Update us.
-        for (int i = successorList.size() - 1 ;  i >= 0; i--) {
-            if (successorList.get(i) == other.index) {
-                successorList.set(i, newSucc.index);
-            }
-        }
-
-        if (primarySuccessor == other.index) {
-            primarySuccessor = newSucc.index;
-        }
-        successors.clear(other.index);
-        successors.set(newSucc.index);
-
-        // Update "other".
-        other.predecessors.set(newSucc.index);
-        other.predecessors.set(index, successors.get(other.index));
-
-        return newSucc;
-    }
-
-    /**
-     * Replaces an old successor with a new successor. This will throw
-     * RuntimeException if {@code oldIndex} was not a successor.
-     *
-     * @param oldIndex index of old successor block
-     * @param newIndex index of new successor block
-     */
-    public void replaceSuccessor(int oldIndex, int newIndex) {
-        if (oldIndex == newIndex) {
-            return;
-        }
-
-        // Update us.
-        successors.set(newIndex);
-
-        if (primarySuccessor == oldIndex) {
-            primarySuccessor = newIndex;
-        }
-
-        for (int i = successorList.size() - 1 ;  i >= 0; i--) {
-            if (successorList.get(i) == oldIndex) {
-                successorList.set(i, newIndex);
-            }
-        }
-
-        successors.clear(oldIndex);
-
-        // Update new successor.
-        parent.getBlocks().get(newIndex).predecessors.set(index);
-
-        // Update old successor.
-        parent.getBlocks().get(oldIndex).predecessors.clear(index);
-    }
-
-    /**
-     * Removes a successor from this block's successor list.
-     *
-     * @param oldIndex index of successor block to remove
-     */
-    public void removeSuccessor(int oldIndex) {
-        int removeIndex = 0;
-
-        for (int i = successorList.size() - 1; i >= 0; i--) {
-            if (successorList.get(i) == oldIndex) {
-                removeIndex = i;
-            } else {
-                primarySuccessor = successorList.get(i);
-            }
-        }
-
-        successorList.removeIndex(removeIndex);
-        successors.clear(oldIndex);
-        parent.getBlocks().get(oldIndex).predecessors.clear(index);
-    }
-
-    /**
-     * Attaches block to an exit block if necessary. If this block
-     * is not an exit predecessor or is the exit block, this block does
-     * nothing. For use by {@link com.android.jack.dx.ssa.SsaMethod#makeExitBlock}
-     *
-     * @param exitBlock {@code non-null;} exit block
-     */
-    public void exitBlockFixup(SsaBasicBlock exitBlock) {
-        if (this == exitBlock) {
-            return;
-        }
-
-        if (successorList.size() == 0) {
-            /*
-             * This is an exit predecessor.
-             * Set the successor to the exit block
-             */
-            successors.set(exitBlock.index);
-            successorList.add(exitBlock.index);
-            primarySuccessor = exitBlock.index;
-            exitBlock.predecessors.set(this.index);
-        }
-    }
-
-    /**
-     * Adds a move instruction to the end of this basic block, just
-     * before the last instruction. If the result of the final instruction
-     * is the source in question, then the move is placed at the beginning of
-     * the primary successor block. This is for unversioned registers.
-     *
-     * @param result move destination
-     * @param source move source
-     */
-    public void addMoveToEnd(RegisterSpec result, RegisterSpec source) {
-
-        if (result.getReg() == source.getReg()) {
-            // Sometimes we end up with no-op moves. Ignore them here.
-            return;
-        }
+      /*
+       * If there are no circular dependencies, then there exists
+       * n instructions where n > 1 whose result is not used as a source.
+       */
+      for (int i = insertPlace; i < sz; i++) {
+        SsaInsn insn = toSchedule.get(i);
 
         /*
-         * The last Insn has to be a normal SSA insn: a phi can't branch
-         * or return or cause an exception, etc.
+         * Move these n registers to the front, since they overwrite
+         * nothing.
          */
-        NormalSsaInsn lastInsn;
-        lastInsn = (NormalSsaInsn)insns.get(insns.size()-1);
+        if (!checkRegUsed(regsUsedAsSources, insn.getResult())) {
+          Collections.swap(toSchedule, i, insertPlace++);
+        }
+      }
 
-        if (lastInsn.getResult() != null || lastInsn.getSources().size() > 0) {
+      /*
+       * If we've made no progress in this iteration, there's a
+       * circular dependency. Split it using the temp reg.
+       */
+      if (oldInsertPlace == insertPlace) {
+
+        SsaInsn insnToSplit = null;
+
+        // Find an insn whose result is used as a source.
+        for (int i = insertPlace; i < sz; i++) {
+          SsaInsn insn = toSchedule.get(i);
+          if (checkRegUsed(regsUsedAsSources, insn.getResult())
+              && checkRegUsed(regsUsedAsResults, insn.getSources().get(0))) {
+
+            insnToSplit = insn;
             /*
-             * The final insn in this block has a source or result
-             * register, and the moves we may need to place and
-             * schedule may interfere. We need to insert this
-             * instruction at the beginning of the primary successor
-             * block instead. We know this is safe, because when we
-             * edge-split earlier, we ensured that each successor has
-             * only us as a predecessor.
+             * We're going to split this insn; move it to the
+             * front.
              */
+            Collections.swap(toSchedule, insertPlace, i);
+            break;
+          }
+        }
 
-            for (int i = successors.nextSetBit(0)
-                    ; i >= 0
-                    ; i = successors.nextSetBit(i + 1)) {
+        // At least one insn will be set above.
 
-                SsaBasicBlock succ;
+        RegisterSpec result = insnToSplit.getResult();
+        RegisterSpec tempSpec = result.withReg(parent.borrowSpareRegister(result.getCategory()));
 
-                succ = parent.getBlocks().get(i);
-                succ.addMoveToBeginning(result, source);
-            }
+        NormalSsaInsn toAdd = new NormalSsaInsn(new PlainInsn(Rops.opMove(result.getType()),
+            SourcePosition.NO_INFO, tempSpec, insnToSplit.getSources()), this);
+
+        toSchedule.add(insertPlace++, toAdd);
+
+        RegisterSpecList newSources = RegisterSpecList.make(tempSpec);
+
+        NormalSsaInsn toReplace = new NormalSsaInsn(new PlainInsn(Rops.opMove(result.getType()),
+            SourcePosition.NO_INFO, result, newSources), this);
+
+        toSchedule.set(insertPlace, toReplace);
+
+        // The size changed.
+        sz = toSchedule.size();
+      }
+
+      regsUsedAsSources.clear();
+      regsUsedAsResults.clear();
+    }
+  }
+
+  /**
+   * Adds {@code regV} to the live-out list for this block. This is called
+   * by the liveness analyzer.
+   *
+   * @param regV register that is live-out for this block.
+   */
+  public void addLiveOut(int regV) {
+    if (liveOut == null) {
+      liveOut = SetFactory.makeLivenessSet(parent.getRegCount());
+    }
+
+    liveOut.add(regV);
+  }
+
+  /**
+   * Adds {@code regV} to the live-in list for this block. This is
+   * called by the liveness analyzer.
+   *
+   * @param regV register that is live-in for this block.
+   */
+  public void addLiveIn(int regV) {
+    if (liveIn == null) {
+      liveIn = SetFactory.makeLivenessSet(parent.getRegCount());
+    }
+
+    liveIn.add(regV);
+  }
+
+  /**
+   * Returns the set of live-in registers. Valid after register
+   * interference graph has been generated, otherwise empty.
+   *
+   * @return {@code non-null;} live-in register set.
+   */
+  public IntSet getLiveInRegs() {
+    if (liveIn == null) {
+      liveIn = SetFactory.makeLivenessSet(parent.getRegCount());
+    }
+    return liveIn;
+  }
+
+  /**
+   * Returns the set of live-out registers. Valid after register
+   * interference graph has been generated, otherwise empty.
+   *
+   * @return {@code non-null;} live-out register set
+   */
+  public IntSet getLiveOutRegs() {
+    if (liveOut == null) {
+      liveOut = SetFactory.makeLivenessSet(parent.getRegCount());
+    }
+    return liveOut;
+  }
+
+  /**
+   * @return true if this is the one-and-only exit block for this method
+   */
+  public boolean isExitBlock() {
+    return index == parent.getExitBlockIndex();
+  }
+
+  /**
+   * Returns true if this block was last calculated to be reachable.
+   * Recalculates reachability if value has never been computed.
+   *
+   * @return {@code true} if reachable
+   */
+  public boolean isReachable() {
+    if (reachable == -1) {
+      parent.computeReachability();
+    }
+    return (reachable == 1);
+  }
+
+  /**
+   * Sets reachability of block to specified value
+   *
+   * @param reach new value of reachability for block
+   */
+  public void setReachable(int reach) {
+    reachable = reach;
+  }
+
+  /**
+   * Sorts move instructions added via {@code addMoveToEnd} during
+   * phi removal so that results don't overwrite sources that are used.
+   * For use after all phis have been removed and all calls to
+   * addMoveToEnd() have been made.<p>
+   *
+   * This is necessary because copy-propogation may have left us in a state
+   * where the same basic block has the same register as a phi operand
+   * and a result. In this case, the register in the phi operand always
+   * refers value before any other phis have executed.
+   */
+  public void scheduleMovesFromPhis() {
+    if (movesFromPhisAtBeginning > 1) {
+      List<SsaInsn> toSchedule;
+
+      toSchedule = insns.subList(0, movesFromPhisAtBeginning);
+
+      scheduleUseBeforeAssigned(toSchedule);
+
+      SsaInsn firstNonPhiMoveInsn = insns.get(movesFromPhisAtBeginning);
+
+      /*
+       * TODO(dx team): It's actually possible that this case never happens,
+       * because a move-exception block, having only one predecessor
+       * in SSA form, perhaps is never on a dominance frontier.
+       */
+      if (firstNonPhiMoveInsn.isMoveException()) {
+        if (!enablePhisBeforeMoveException) {
+          /*
+           * We've yet to observe this case, and if it can
+           * occur the code written to handle it probably
+           * does not work.
+           */
+          throw new RuntimeException("Unexpected: moves from " + "phis before move-exception");
         } else {
-            /*
-             * We can safely add a move to the end of the block just
-             * before the last instruction, because the final insn does
-             * not assign to anything.
-             */
-            RegisterSpecList sources = RegisterSpecList.make(source);
-            NormalSsaInsn toAdd = new NormalSsaInsn(
-                    new PlainInsn(Rops.opMove(result.getType()),
-                            SourcePosition.NO_INFO, result, sources), this);
+          /*
+           * A move-exception insn must be placed first in this block
+           * We need to move it there, and deal with possible
+           * interference.
+           */
+          boolean moveExceptionInterferes = false;
 
-            insns.add(insns.size() - 1, toAdd);
+          int moveExceptionResult = firstNonPhiMoveInsn.getResult().getReg();
 
-            movesFromPhisAtEnd++;
-        }
-    }
-
-    /**
-     * Adds a move instruction after the phi insn block.
-     *
-     * @param result move destination
-     * @param source move source
-     */
-    public void addMoveToBeginning (RegisterSpec result, RegisterSpec source) {
-        if (result.getReg() == source.getReg()) {
-            // Sometimes we end up with no-op moves. Ignore them here.
-            return;
-        }
-
-        RegisterSpecList sources = RegisterSpecList.make(source);
-        NormalSsaInsn toAdd = new NormalSsaInsn(
-                new PlainInsn(Rops.opMove(result.getType()),
-                        SourcePosition.NO_INFO, result, sources), this);
-
-        insns.add(getCountPhiInsns(), toAdd);
-        movesFromPhisAtBeginning++;
-    }
-
-    /**
-     * Sets the register as used in a bitset, taking into account its
-     * category/width.
-     *
-     * @param regsUsed set, indexed by register number
-     * @param rs register to mark as used
-     */
-    private static void setRegsUsed (BitSet regsUsed, RegisterSpec rs) {
-        regsUsed.set(rs.getReg());
-        if (rs.getCategory() > 1) {
-            regsUsed.set(rs.getReg() + 1);
-        }
-    }
-
-    /**
-     * Checks to see if the register is used in a bitset, taking
-     * into account its category/width.
-     *
-     * @param regsUsed set, indexed by register number
-     * @param rs register to mark as used
-     * @return true if register is fully or partially (for the case of wide
-     * registers) used.
-     */
-    private static boolean checkRegUsed (BitSet regsUsed, RegisterSpec rs) {
-        int reg = rs.getReg();
-        int category = rs.getCategory();
-
-        return regsUsed.get(reg)
-                || (category == 2 ? regsUsed.get(reg + 1) : false);
-    }
-
-    /**
-     * Ensures that all move operations in this block occur such that
-     * reads of any register happen before writes to that register.
-     * NOTE: caller is expected to returnSpareRegisters()!
-     *
-     * TODO: See Briggs, et al "Practical Improvements to the Construction and
-     * Destruction of Static Single Assignment Form" section 5. a) This can
-     * be done in three passes.
-     *
-     * @param toSchedule List of instructions. Must consist only of moves.
-     */
-    private void scheduleUseBeforeAssigned(List<SsaInsn> toSchedule) {
-        BitSet regsUsedAsSources = new BitSet(parent.getRegCount());
-
-        // TODO: Get rid of this.
-        BitSet regsUsedAsResults = new BitSet(parent.getRegCount());
-
-        int sz = toSchedule.size();
-
-        int insertPlace = 0;
-
-        while (insertPlace < sz) {
-            int oldInsertPlace = insertPlace;
-
-            // Record all registers used as sources in this block.
-            for (int i = insertPlace; i < sz; i++) {
-                setRegsUsed(regsUsedAsSources,
-                        toSchedule.get(i).getSources().get(0));
-
-                setRegsUsed(regsUsedAsResults,
-                        toSchedule.get(i).getResult());
+          /*
+           * Does the move-exception result reg interfere with the
+           * phi moves?
+           */
+          for (SsaInsn insn : toSchedule) {
+            if (insn.isResultReg(moveExceptionResult) || insn.isRegASource(moveExceptionResult)) {
+              moveExceptionInterferes = true;
+              break;
             }
+          }
+
+          if (!moveExceptionInterferes) {
+            // This is the easy case.
+            insns.remove(movesFromPhisAtBeginning);
+            insns.add(0, firstNonPhiMoveInsn);
+          } else {
+            /*
+             * We need to move the result to a spare reg
+             * and move it back.
+             */
+            RegisterSpec originalResultSpec = firstNonPhiMoveInsn.getResult();
+            int spareRegister = parent.borrowSpareRegister(originalResultSpec.getCategory());
+
+            // We now move it to a spare register.
+            firstNonPhiMoveInsn.changeResultReg(spareRegister);
+            RegisterSpec tempSpec = firstNonPhiMoveInsn.getResult();
+
+            insns.add(0, firstNonPhiMoveInsn);
+
+            // And here we move it back.
+
+            NormalSsaInsn toAdd = new NormalSsaInsn(new PlainInsn(Rops.opMove(tempSpec.getType()),
+                SourcePosition.NO_INFO, originalResultSpec, RegisterSpecList.make(tempSpec)), this);
+
 
             /*
-             * If there are no circular dependencies, then there exists
-             * n instructions where n > 1 whose result is not used as a source.
+             * Place it immediately after the phi-moves,
+             * overwriting the move-exception that was there.
              */
-            for (int i = insertPlace; i <sz; i++) {
-                SsaInsn insn = toSchedule.get(i);
-
-                /*
-                 * Move these n registers to the front, since they overwrite
-                 * nothing.
-                 */
-                if (!checkRegUsed(regsUsedAsSources, insn.getResult())) {
-                    Collections.swap(toSchedule, i, insertPlace++);
-                }
-            }
-
-            /*
-             * If we've made no progress in this iteration, there's a
-             * circular dependency. Split it using the temp reg.
-             */
-            if (oldInsertPlace == insertPlace) {
-
-                SsaInsn insnToSplit = null;
-
-                // Find an insn whose result is used as a source.
-                for (int i = insertPlace; i < sz; i++) {
-                    SsaInsn insn = toSchedule.get(i);
-                    if (checkRegUsed(regsUsedAsSources, insn.getResult())
-                            && checkRegUsed(regsUsedAsResults,
-                                insn.getSources().get(0))) {
-
-                        insnToSplit = insn;
-                        /*
-                         * We're going to split this insn; move it to the
-                         * front.
-                         */
-                        Collections.swap(toSchedule, insertPlace, i);
-                        break;
-                    }
-                }
-
-                // At least one insn will be set above.
-
-                RegisterSpec result = insnToSplit.getResult();
-                RegisterSpec tempSpec = result.withReg(
-                        parent.borrowSpareRegister(result.getCategory()));
-
-                NormalSsaInsn toAdd = new NormalSsaInsn(
-                        new PlainInsn(Rops.opMove(result.getType()),
-                                SourcePosition.NO_INFO,
-                                tempSpec,
-                                insnToSplit.getSources()), this);
-
-                toSchedule.add(insertPlace++, toAdd);
-
-                RegisterSpecList newSources = RegisterSpecList.make(tempSpec);
-
-                NormalSsaInsn toReplace = new NormalSsaInsn(
-                        new PlainInsn(Rops.opMove(result.getType()),
-                                SourcePosition.NO_INFO,
-                                result,
-                                newSources), this);
-
-                toSchedule.set(insertPlace, toReplace);
-
-                // The size changed.
-                sz = toSchedule.size();
-            }
-
-            regsUsedAsSources.clear();
-            regsUsedAsResults.clear();
+            insns.set(movesFromPhisAtBeginning + 1, toAdd);
+          }
         }
+      }
     }
 
+    if (movesFromPhisAtEnd > 1) {
+      scheduleUseBeforeAssigned(
+          insns.subList(insns.size() - movesFromPhisAtEnd - 1, insns.size() - 1));
+    }
+
+    // Return registers borrowed here and in scheduleUseBeforeAssigned().
+    parent.returnSpareRegisters();
+
+  }
+
+  /**
+   * Visits all insns in this block.
+   *
+   * @param visitor {@code non-null;} callback interface
+   */
+  public void forEachInsn(SsaInsn.Visitor visitor) {
+    // This gets called a LOT, and not using an iterator
+    // saves a lot of allocations and reduces memory usage
+    int len = insns.size();
+    for (int i = 0; i < len; i++) {
+      insns.get(i).accept(visitor);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    return "{" + index + ":" + Hex.u2(ropLabel) + '}';
+  }
+
+  /**
+   * Visitor interface for basic blocks.
+   */
+  public interface Visitor {
     /**
-     * Adds {@code regV} to the live-out list for this block. This is called
-     * by the liveness analyzer.
+     * Indicates a block has been visited by an iterator method.
      *
-     * @param regV register that is live-out for this block.
+     * @param v {@code non-null;} block visited
+     * @param parent {@code null-ok;} parent node if applicable
      */
-    public void addLiveOut (int regV) {
-        if (liveOut == null) {
-            liveOut = SetFactory.makeLivenessSet(parent.getRegCount());
-        }
+    void visitBlock(SsaBasicBlock v, SsaBasicBlock parent);
+  }
 
-        liveOut.add(regV);
-    }
-
-    /**
-     * Adds {@code regV} to the live-in list for this block. This is
-     * called by the liveness analyzer.
-     *
-     * @param regV register that is live-in for this block.
-     */
-    public void addLiveIn (int regV) {
-        if (liveIn == null) {
-            liveIn = SetFactory.makeLivenessSet(parent.getRegCount());
-        }
-
-        liveIn.add(regV);
-    }
-
-    /**
-     * Returns the set of live-in registers. Valid after register
-     * interference graph has been generated, otherwise empty.
-     *
-     * @return {@code non-null;} live-in register set.
-     */
-    public IntSet getLiveInRegs() {
-        if (liveIn == null) {
-            liveIn = SetFactory.makeLivenessSet(parent.getRegCount());
-        }
-        return liveIn;
-    }
-
-    /**
-     * Returns the set of live-out registers. Valid after register
-     * interference graph has been generated, otherwise empty.
-     *
-     * @return {@code non-null;} live-out register set
-     */
-    public IntSet getLiveOutRegs() {
-        if (liveOut == null) {
-            liveOut = SetFactory.makeLivenessSet(parent.getRegCount());
-        }
-        return liveOut;
-    }
-
-    /**
-     * @return true if this is the one-and-only exit block for this method
-     */
-    public boolean isExitBlock() {
-        return index == parent.getExitBlockIndex();
-    }
-
-    /**
-     * Returns true if this block was last calculated to be reachable.
-     * Recalculates reachability if value has never been computed.
-     *
-     * @return {@code true} if reachable
-     */
-    public boolean isReachable() {
-        if (reachable == -1) {
-            parent.computeReachability();
-        }
-        return (reachable == 1);
-    }
-
-    /**
-     * Sets reachability of block to specified value
-     *
-     * @param reach new value of reachability for block
-     */
-    public void setReachable(int reach) {
-        reachable = reach;
-    }
-
-    /**
-     * Sorts move instructions added via {@code addMoveToEnd} during
-     * phi removal so that results don't overwrite sources that are used.
-     * For use after all phis have been removed and all calls to
-     * addMoveToEnd() have been made.<p>
-     *
-     * This is necessary because copy-propogation may have left us in a state
-     * where the same basic block has the same register as a phi operand
-     * and a result. In this case, the register in the phi operand always
-     * refers value before any other phis have executed.
-     */
-    public void scheduleMovesFromPhis() {
-        if (movesFromPhisAtBeginning > 1) {
-            List<SsaInsn> toSchedule;
-
-            toSchedule = insns.subList(0, movesFromPhisAtBeginning);
-
-            scheduleUseBeforeAssigned(toSchedule);
-
-            SsaInsn firstNonPhiMoveInsn = insns.get(movesFromPhisAtBeginning);
-
-            /*
-             * TODO: It's actually possible that this case never happens,
-             * because a move-exception block, having only one predecessor
-             * in SSA form, perhaps is never on a dominance frontier.
-             */
-            if (firstNonPhiMoveInsn.isMoveException()) {
-                if (true) {
-                    /*
-                     * We've yet to observe this case, and if it can
-                     * occur the code written to handle it probably
-                     * does not work.
-                     */
-                    throw new RuntimeException(
-                            "Unexpected: moves from "
-                                    +"phis before move-exception");
-                } else {
-                    /*
-                     * A move-exception insn must be placed first in this block
-                     * We need to move it there, and deal with possible
-                     * interference.
-                     */
-                    boolean moveExceptionInterferes = false;
-
-                    int moveExceptionResult
-                            = firstNonPhiMoveInsn.getResult().getReg();
-
-                    /*
-                     * Does the move-exception result reg interfere with the
-                     * phi moves?
-                     */
-                    for (SsaInsn insn : toSchedule) {
-                        if (insn.isResultReg(moveExceptionResult)
-                                || insn.isRegASource(moveExceptionResult)) {
-                            moveExceptionInterferes = true;
-                            break;
-                        }
-                    }
-
-                    if (!moveExceptionInterferes) {
-                        // This is the easy case.
-                        insns.remove(movesFromPhisAtBeginning);
-                        insns.add(0, firstNonPhiMoveInsn);
-                    } else {
-                        /*
-                         * We need to move the result to a spare reg
-                         * and move it back.
-                         */
-                        RegisterSpec originalResultSpec
-                            = firstNonPhiMoveInsn.getResult();
-                        int spareRegister = parent.borrowSpareRegister(
-                                originalResultSpec.getCategory());
-
-                        // We now move it to a spare register.
-                        firstNonPhiMoveInsn.changeResultReg(spareRegister);
-                        RegisterSpec tempSpec =
-                            firstNonPhiMoveInsn.getResult();
-
-                        insns.add(0, firstNonPhiMoveInsn);
-
-                        // And here we move it back.
-
-                        NormalSsaInsn toAdd = new NormalSsaInsn(
-                                new PlainInsn(
-                                        Rops.opMove(tempSpec.getType()),
-                                        SourcePosition.NO_INFO,
-                                        originalResultSpec,
-                                        RegisterSpecList.make(tempSpec)),
-                                this);
-
-
-                        /*
-                         * Place it immediately after the phi-moves,
-                         * overwriting the move-exception that was there.
-                         */
-                        insns.set(movesFromPhisAtBeginning + 1, toAdd);
-                    }
-                }
-            }
-        }
-
-        if (movesFromPhisAtEnd > 1) {
-            scheduleUseBeforeAssigned(
-                    insns.subList(insns.size() - movesFromPhisAtEnd - 1,
-                                insns.size() - 1));
-        }
-
-        // Return registers borrowed here and in scheduleUseBeforeAssigned().
-        parent.returnSpareRegisters();
-
-    }
-
-    /**
-     * Visits all insns in this block.
-     *
-     * @param visitor {@code non-null;} callback interface
-     */
-    public void forEachInsn(SsaInsn.Visitor visitor) {
-        // This gets called a LOT, and not using an iterator
-        // saves a lot of allocations and reduces memory usage
-        int len = insns.size();
-        for (int i = 0; i < len; i++) {
-            insns.get(i).accept(visitor);
-        }
-    }
-
+  /**
+   * Label comparator.
+   */
+  public static final class LabelComparator implements Comparator<SsaBasicBlock> {
     /** {@inheritDoc} */
     @Override
-    public String toString() {
-        return "{" + index + ":" + Hex.u2(ropLabel) + '}';
-    }
+    public int compare(SsaBasicBlock b1, SsaBasicBlock b2) {
+      int label1 = b1.ropLabel;
+      int label2 = b2.ropLabel;
 
-    /**
-     * Visitor interface for basic blocks.
-     */
-    public interface Visitor {
-        /**
-         * Indicates a block has been visited by an iterator method.
-         *
-         * @param v {@code non-null;} block visited
-         * @param parent {@code null-ok;} parent node if applicable
-         */
-        void visitBlock (SsaBasicBlock v, SsaBasicBlock parent);
+      if (label1 < label2) {
+        return -1;
+      } else if (label1 > label2) {
+        return 1;
+      } else {
+        return 0;
+      }
     }
-
-    /**
-     * Label comparator.
-     */
-    public static final class LabelComparator
-            implements Comparator<SsaBasicBlock> {
-        /** {@inheritDoc} */
-        public int compare(SsaBasicBlock b1, SsaBasicBlock b2) {
-            int label1 = b1.ropLabel;
-            int label2 = b2.ropLabel;
-
-            if (label1 < label2) {
-                return -1;
-            } else if (label1 > label2) {
-                return 1;
-            } else {
-                return 0;
-            }
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SsaConverter.java b/dx/src/com/android/jack/dx/ssa/SsaConverter.java
index 89dd19d..0c6862d 100644
--- a/dx/src/com/android/jack/dx/ssa/SsaConverter.java
+++ b/dx/src/com/android/jack/dx/ssa/SsaConverter.java
@@ -27,365 +27,354 @@
  * Converts ROP methods to SSA Methods
  */
 public class SsaConverter {
-    public static final boolean DEBUG = false;
+  public static final boolean DEBUG = false;
 
-    /**
-     * Returns an SSA representation, edge-split and with phi
-     * functions placed.
-     *
-     * @param rmeth input
-     * @param paramWidth the total width, in register-units, of the method's
-     * parameters
-     * @param isStatic {@code true} if this method has no {@code this}
-     * pointer argument
-     * @return output in SSA form
+  /**
+   * Returns an SSA representation, edge-split and with phi
+   * functions placed.
+   *
+   * @param rmeth input
+   * @param paramWidth the total width, in register-units, of the method's
+   * parameters
+   * @param isStatic {@code true} if this method has no {@code this}
+   * pointer argument
+   * @return output in SSA form
+   */
+  public static SsaMethod convertToSsaMethod(RopMethod rmeth, int paramWidth, boolean isStatic) {
+    SsaMethod result = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
+
+    edgeSplit(result);
+
+    LocalVariableInfo localInfo = LocalVariableExtractor.extract(result);
+
+    placePhiFunctions(result, localInfo, 0);
+    new SsaRenamer(result).run();
+
+    /*
+     * The exit block, added here, is not considered for edge splitting
+     * or phi placement since no actual control flows to it.
      */
-    public static SsaMethod convertToSsaMethod(RopMethod rmeth,
-            int paramWidth, boolean isStatic) {
-        SsaMethod result
-            = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
+    result.makeExitBlock();
 
-        edgeSplit(result);
+    return result;
+  }
 
-        LocalVariableInfo localInfo = LocalVariableExtractor.extract(result);
+  /**
+   * Updates an SSA representation, placing phi functions and renaming all
+   * registers above a certain threshold number.
+   *
+   * @param ssaMeth input
+   * @param threshold registers below this number are unchanged
+   */
+  public static void updateSsaMethod(SsaMethod ssaMeth, int threshold) {
+    LocalVariableInfo localInfo = LocalVariableExtractor.extract(ssaMeth);
+    placePhiFunctions(ssaMeth, localInfo, threshold);
+    new SsaRenamer(ssaMeth, threshold).run();
+  }
 
-        placePhiFunctions(result, localInfo, 0);
-        new SsaRenamer(result).run();
+  /**
+   * Returns an SSA represention with only the edge-splitter run.
+   *
+   * @param rmeth method to process
+   * @param paramWidth width of all arguments in the method
+   * @param isStatic {@code true} if this method has no {@code this}
+   * pointer argument
+   * @return an SSA represention with only the edge-splitter run
+   */
+  public static SsaMethod testEdgeSplit(RopMethod rmeth, int paramWidth, boolean isStatic) {
+    SsaMethod result;
 
-        /*
-         * The exit block, added here, is not considered for edge splitting
-         * or phi placement since no actual control flows to it.
-         */
-        result.makeExitBlock();
+    result = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
 
-        return result;
+    edgeSplit(result);
+    return result;
+  }
+
+  /**
+   * Returns an SSA represention with only the steps through the
+   * phi placement run.
+   *
+   * @param rmeth method to process
+   * @param paramWidth width of all arguments in the method
+   * @param isStatic {@code true} if this method has no {@code this}
+   * pointer argument
+   * @return an SSA represention with only the edge-splitter run
+   */
+  public static SsaMethod testPhiPlacement(RopMethod rmeth, int paramWidth, boolean isStatic) {
+    SsaMethod result;
+
+    result = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
+
+    edgeSplit(result);
+
+    LocalVariableInfo localInfo = LocalVariableExtractor.extract(result);
+
+    placePhiFunctions(result, localInfo, 0);
+    return result;
+  }
+
+  /**
+   * See Appel section 19.1:
+   *
+   * Converts CFG into "edge-split" form, such that each node either a
+   * unique successor or unique predecessor.<p>
+   *
+   * In addition, the SSA form we use enforces a further constraint,
+   * requiring each block with a final instruction that returns a
+   * value to have a primary successor that has no other
+   * predecessor. This ensures move statements can always be
+   * inserted correctly when phi statements are removed.
+   *
+   * @param result method to process
+   */
+  private static void edgeSplit(SsaMethod result) {
+    edgeSplitPredecessors(result);
+    edgeSplitMoveExceptionsAndResults(result);
+    edgeSplitSuccessors(result);
+  }
+
+  /**
+   * Inserts Z nodes as new predecessors for every node that has multiple
+   * successors and multiple predecessors.
+   *
+   * @param result {@code non-null;} method to process
+   */
+  private static void edgeSplitPredecessors(SsaMethod result) {
+    ArrayList<SsaBasicBlock> blocks = result.getBlocks();
+
+    /*
+     * New blocks are added to the end of the block list during
+     * this iteration.
+     */
+    for (int i = blocks.size() - 1; i >= 0; i--) {
+      SsaBasicBlock block = blocks.get(i);
+      if (nodeNeedsUniquePredecessor(block)) {
+        block.insertNewPredecessor();
+      }
+    }
+  }
+
+  /**
+   * @param block {@code non-null;} block in question
+   * @return {@code true} if this node needs to have a unique
+   * predecessor created for it
+   */
+  private static boolean nodeNeedsUniquePredecessor(SsaBasicBlock block) {
+    /*
+     * Any block with that has both multiple successors and multiple
+     * predecessors needs a new predecessor node.
+     */
+
+int countPredecessors = block.getPredecessors().cardinality();
+    int countSuccessors = block.getSuccessors().cardinality();
+
+    return (countPredecessors > 1 && countSuccessors > 1);
+  }
+
+  /**
+   * In ROP form, move-exception must occur as the first insn in a block
+   * immediately succeeding the insn that could thrown an exception.
+   * We may need room to insert move insns later, so make sure to split
+   * any block that starts with a move-exception such that there is a
+   * unique move-exception block for each predecessor.
+   *
+   * @param ssaMeth method to process
+   */
+  private static void edgeSplitMoveExceptionsAndResults(SsaMethod ssaMeth) {
+    ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
+
+    /*
+     * New blocks are added to the end of the block list during
+     * this iteration.
+     */
+    for (int i = blocks.size() - 1; i >= 0; i--) {
+      SsaBasicBlock block = blocks.get(i);
+
+      /*
+       * Any block that starts with a move-exception and has more than
+       * one predecessor...
+       */
+      if (!block.isExitBlock() && block.getPredecessors().cardinality() > 1
+          && block.getInsns().get(0).isMoveException()) {
+
+        // block.getPredecessors() is changed in the loop below.
+        BitSet preds = (BitSet) block.getPredecessors().clone();
+        for (int j = preds.nextSetBit(0); j >= 0; j = preds.nextSetBit(j + 1)) {
+          SsaBasicBlock predecessor = blocks.get(j);
+          SsaBasicBlock zNode = predecessor.insertNewSuccessor(block);
+
+          /*
+           * Make sure to place the move-exception as the
+           * first insn.
+           */
+          zNode.getInsns().add(0, block.getInsns().get(0).clone());
+        }
+
+        // Remove the move-exception from the original block.
+        block.getInsns().remove(0);
+      }
+    }
+  }
+
+  /**
+   * Inserts Z nodes for every node that needs a new
+   * successor.
+   *
+   * @param result {@code non-null;} method to process
+   */
+  private static void edgeSplitSuccessors(SsaMethod result) {
+    ArrayList<SsaBasicBlock> blocks = result.getBlocks();
+
+    /*
+     * New blocks are added to the end of the block list during
+     * this iteration.
+     */
+    for (int i = blocks.size() - 1; i >= 0; i--) {
+      SsaBasicBlock block = blocks.get(i);
+
+      // Successors list is modified in loop below.
+      BitSet successors = (BitSet) block.getSuccessors().clone();
+      for (int j = successors.nextSetBit(0); j >= 0; j = successors.nextSetBit(j + 1)) {
+
+        SsaBasicBlock succ = blocks.get(j);
+
+        if (needsNewSuccessor(block, succ)) {
+          block.insertNewSuccessor(succ);
+        }
+      }
+    }
+  }
+
+  /**
+   * Returns {@code true} if block and successor need a Z-node
+   * between them. Presently, this is {@code true} if the final
+   * instruction has any sources or results and the current
+   * successor block has more than one predecessor.
+   *
+   * @param block predecessor node
+   * @param succ successor node
+   * @return {@code true} if a Z node is needed
+   */
+  private static boolean needsNewSuccessor(SsaBasicBlock block, SsaBasicBlock succ) {
+    ArrayList<SsaInsn> insns = block.getInsns();
+    SsaInsn lastInsn = insns.get(insns.size() - 1);
+
+    return ((lastInsn.getResult() != null) || (lastInsn.getSources().size() > 0))
+        && succ.getPredecessors().cardinality() > 1;
+  }
+
+  /**
+   * See Appel algorithm 19.6:
+   *
+   * Place Phi functions in appropriate locations.
+   *
+   * @param ssaMeth {@code non-null;} method to process.
+   * Modifications are made in-place.
+   * @param localInfo {@code non-null;} local variable info, used
+   * when placing phis
+   * @param threshold registers below this number are ignored
+   */
+  private static void placePhiFunctions(SsaMethod ssaMeth, LocalVariableInfo localInfo,
+      int threshold) {
+    ArrayList<SsaBasicBlock> ssaBlocks;
+    int regCount;
+    int blockCount;
+
+    ssaBlocks = ssaMeth.getBlocks();
+    blockCount = ssaBlocks.size();
+    regCount = ssaMeth.getRegCount() - threshold;
+
+    DomFront df = new DomFront(ssaMeth);
+    DomFront.DomInfo[] domInfos = df.run();
+
+    // Bit set of registers vs block index "definition sites"
+    BitSet[] defsites = new BitSet[regCount];
+
+    // Bit set of registers vs block index "phi placement sites"
+    BitSet[] phisites = new BitSet[regCount];
+
+    for (int i = 0; i < regCount; i++) {
+      defsites[i] = new BitSet(blockCount);
+      phisites[i] = new BitSet(blockCount);
     }
 
-    /**
-     * Updates an SSA representation, placing phi functions and renaming all
-     * registers above a certain threshold number.
-     *
-     * @param ssaMeth input
-     * @param threshold registers below this number are unchanged
+    /*
+     * For each register, build a set of all basic blocks where
+     * containing an assignment to that register.
      */
-    public static void updateSsaMethod(SsaMethod ssaMeth, int threshold) {
-        LocalVariableInfo localInfo = LocalVariableExtractor.extract(ssaMeth);
-        placePhiFunctions(ssaMeth, localInfo, threshold);
-        new SsaRenamer(ssaMeth, threshold).run();
+    for (int bi = 0, s = ssaBlocks.size(); bi < s; bi++) {
+      SsaBasicBlock b = ssaBlocks.get(bi);
+
+      for (SsaInsn insn : b.getInsns()) {
+        RegisterSpec rs = insn.getResult();
+
+        if (rs != null && rs.getReg() - threshold >= 0) {
+          defsites[rs.getReg() - threshold].set(bi);
+        }
+      }
     }
 
-    /**
-     * Returns an SSA represention with only the edge-splitter run.
-     *
-     * @param rmeth method to process
-     * @param paramWidth width of all arguments in the method
-     * @param isStatic {@code true} if this method has no {@code this}
-     * pointer argument
-     * @return an SSA represention with only the edge-splitter run
-     */
-    public static SsaMethod testEdgeSplit (RopMethod rmeth, int paramWidth,
-            boolean isStatic) {
-        SsaMethod result;
+    if (DEBUG) {
+      System.out.println("defsites");
 
-        result = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
-
-        edgeSplit(result);
-        return result;
+      for (int i = 0; i < regCount; i++) {
+        StringBuilder sb = new StringBuilder();
+        sb.append('v').append(i).append(": ");
+        sb.append(defsites[i].toString());
+        System.out.println(sb);
+      }
     }
 
-    /**
-     * Returns an SSA represention with only the steps through the
-     * phi placement run.
-     *
-     * @param rmeth method to process
-     * @param paramWidth width of all arguments in the method
-     * @param isStatic {@code true} if this method has no {@code this}
-     * pointer argument
-     * @return an SSA represention with only the edge-splitter run
+    BitSet worklist;
+
+    /*
+     * For each register, compute all locations for phi placement
+     * based on dominance-frontier algorithm.
      */
-    public static SsaMethod testPhiPlacement (RopMethod rmeth, int paramWidth,
-            boolean isStatic) {
-        SsaMethod result;
+    for (int reg = 0, s = regCount; reg < s; reg++) {
+      int workBlockIndex;
 
-        result = SsaMethod.newFromRopMethod(rmeth, paramWidth, isStatic);
+      /* Worklist set starts out with each node where reg is assigned. */
 
-        edgeSplit(result);
+worklist =
+          (BitSet) (defsites[reg].clone());
 
-        LocalVariableInfo localInfo = LocalVariableExtractor.extract(result);
+      while (0 <= (workBlockIndex = worklist.nextSetBit(0))) {
+        worklist.clear(workBlockIndex);
+        IntIterator dfIterator = domInfos[workBlockIndex].dominanceFrontiers.iterator();
 
-        placePhiFunctions(result, localInfo, 0);
-        return result;
-    }
+        while (dfIterator.hasNext()) {
+          int dfBlockIndex = dfIterator.next();
 
-    /**
-     * See Appel section 19.1:
-     *
-     * Converts CFG into "edge-split" form, such that each node either a
-     * unique successor or unique predecessor.<p>
-     *
-     * In addition, the SSA form we use enforces a further constraint,
-     * requiring each block with a final instruction that returns a
-     * value to have a primary successor that has no other
-     * predecessor. This ensures move statements can always be
-     * inserted correctly when phi statements are removed.
-     *
-     * @param result method to process
-     */
-    private static void edgeSplit(SsaMethod result) {
-        edgeSplitPredecessors(result);
-        edgeSplitMoveExceptionsAndResults(result);
-        edgeSplitSuccessors(result);
-    }
+          if (!phisites[reg].get(dfBlockIndex)) {
+            phisites[reg].set(dfBlockIndex);
 
-    /**
-     * Inserts Z nodes as new predecessors for every node that has multiple
-     * successors and multiple predecessors.
-     *
-     * @param result {@code non-null;} method to process
-     */
-    private static void edgeSplitPredecessors(SsaMethod result) {
-        ArrayList<SsaBasicBlock> blocks = result.getBlocks();
+            int tReg = reg + threshold;
+            RegisterSpec rs = localInfo.getStarts(dfBlockIndex).get(tReg);
 
-        /*
-         * New blocks are added to the end of the block list during
-         * this iteration.
-         */
-        for (int i = blocks.size() - 1; i >= 0; i-- ) {
-            SsaBasicBlock block = blocks.get(i);
-            if (nodeNeedsUniquePredecessor(block)) {
-                block.insertNewPredecessor();
+            if (rs == null) {
+              ssaBlocks.get(dfBlockIndex).addPhiInsnForReg(tReg);
+            } else {
+              ssaBlocks.get(dfBlockIndex).addPhiInsnForReg(rs);
             }
+
+            if (!defsites[reg].get(dfBlockIndex)) {
+              worklist.set(dfBlockIndex);
+            }
+          }
         }
+      }
     }
 
-    /**
-     * @param block {@code non-null;} block in question
-     * @return {@code true} if this node needs to have a unique
-     * predecessor created for it
-     */
-    private static boolean nodeNeedsUniquePredecessor(SsaBasicBlock block) {
-        /*
-         * Any block with that has both multiple successors and multiple
-         * predecessors needs a new predecessor node.
-         */
+    if (DEBUG) {
+      System.out.println("phisites");
 
-        int countPredecessors = block.getPredecessors().cardinality();
-        int countSuccessors = block.getSuccessors().cardinality();
-
-        return  (countPredecessors > 1 && countSuccessors > 1);
+      for (int i = 0; i < regCount; i++) {
+        StringBuilder sb = new StringBuilder();
+        sb.append('v').append(i).append(": ");
+        sb.append(phisites[i].toString());
+        System.out.println(sb);
+      }
     }
-
-    /**
-     * In ROP form, move-exception must occur as the first insn in a block
-     * immediately succeeding the insn that could thrown an exception.
-     * We may need room to insert move insns later, so make sure to split
-     * any block that starts with a move-exception such that there is a
-     * unique move-exception block for each predecessor.
-     *
-     * @param ssaMeth method to process
-     */
-    private static void edgeSplitMoveExceptionsAndResults(SsaMethod ssaMeth) {
-        ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
-
-        /*
-         * New blocks are added to the end of the block list during
-         * this iteration.
-         */
-        for (int i = blocks.size() - 1; i >= 0; i-- ) {
-            SsaBasicBlock block = blocks.get(i);
-
-            /*
-             * Any block that starts with a move-exception and has more than
-             * one predecessor...
-             */
-            if (!block.isExitBlock()
-                    && block.getPredecessors().cardinality() > 1
-                    && block.getInsns().get(0).isMoveException()) {
-
-                // block.getPredecessors() is changed in the loop below.
-                BitSet preds = (BitSet)block.getPredecessors().clone();
-                for (int j = preds.nextSetBit(0); j >= 0;
-                     j = preds.nextSetBit(j + 1)) {
-                    SsaBasicBlock predecessor = blocks.get(j);
-                    SsaBasicBlock zNode
-                        = predecessor.insertNewSuccessor(block);
-
-                    /*
-                     * Make sure to place the move-exception as the
-                     * first insn.
-                     */
-                    zNode.getInsns().add(0, block.getInsns().get(0).clone());
-                }
-
-                // Remove the move-exception from the original block.
-                block.getInsns().remove(0);
-            }
-        }
-    }
-
-    /**
-     * Inserts Z nodes for every node that needs a new
-     * successor.
-     *
-     * @param result {@code non-null;} method to process
-     */
-    private static void edgeSplitSuccessors(SsaMethod result) {
-        ArrayList<SsaBasicBlock> blocks = result.getBlocks();
-
-        /*
-         * New blocks are added to the end of the block list during
-         * this iteration.
-         */
-        for (int i = blocks.size() - 1; i >= 0; i-- ) {
-            SsaBasicBlock block = blocks.get(i);
-
-            // Successors list is modified in loop below.
-            BitSet successors = (BitSet)block.getSuccessors().clone();
-            for (int j = successors.nextSetBit(0);
-                 j >= 0; j = successors.nextSetBit(j+1)) {
-
-                SsaBasicBlock succ = blocks.get(j);
-
-                if (needsNewSuccessor(block, succ)) {
-                    block.insertNewSuccessor(succ);
-                }
-            }
-        }
-    }
-
-    /**
-     * Returns {@code true} if block and successor need a Z-node
-     * between them. Presently, this is {@code true} if the final
-     * instruction has any sources or results and the current
-     * successor block has more than one predecessor.
-     *
-     * @param block predecessor node
-     * @param succ successor node
-     * @return {@code true} if a Z node is needed
-     */
-    private static boolean needsNewSuccessor(SsaBasicBlock block,
-            SsaBasicBlock succ) {
-        ArrayList<SsaInsn> insns = block.getInsns();
-        SsaInsn lastInsn = insns.get(insns.size() - 1);
-
-        return ((lastInsn.getResult() != null)
-                    || (lastInsn.getSources().size() > 0))
-                && succ.getPredecessors().cardinality() > 1;
-    }
-
-    /**
-     * See Appel algorithm 19.6:
-     *
-     * Place Phi functions in appropriate locations.
-     *
-     * @param ssaMeth {@code non-null;} method to process.
-     * Modifications are made in-place.
-     * @param localInfo {@code non-null;} local variable info, used
-     * when placing phis
-     * @param threshold registers below this number are ignored
-     */
-    private static void placePhiFunctions (SsaMethod ssaMeth,
-            LocalVariableInfo localInfo, int threshold) {
-        ArrayList<SsaBasicBlock> ssaBlocks;
-        int regCount;
-        int blockCount;
-
-        ssaBlocks = ssaMeth.getBlocks();
-        blockCount = ssaBlocks.size();
-        regCount = ssaMeth.getRegCount() - threshold;
-
-        DomFront df = new DomFront(ssaMeth);
-        DomFront.DomInfo[] domInfos = df.run();
-
-        // Bit set of registers vs block index "definition sites"
-        BitSet[] defsites = new BitSet[regCount];
-
-        // Bit set of registers vs block index "phi placement sites"
-        BitSet[] phisites = new BitSet[regCount];
-
-        for (int i = 0; i < regCount; i++) {
-            defsites[i] = new BitSet(blockCount);
-            phisites[i] = new BitSet(blockCount);
-        }
-
-        /*
-         * For each register, build a set of all basic blocks where
-         * containing an assignment to that register.
-         */
-        for (int bi = 0, s = ssaBlocks.size(); bi < s; bi++) {
-            SsaBasicBlock b = ssaBlocks.get(bi);
-
-            for (SsaInsn insn : b.getInsns()) {
-                RegisterSpec rs = insn.getResult();
-
-                if (rs != null && rs.getReg() - threshold >= 0) {
-                    defsites[rs.getReg() - threshold].set(bi);
-                }
-            }
-        }
-
-        if (DEBUG) {
-            System.out.println("defsites");
-
-            for (int i = 0; i < regCount; i++) {
-                StringBuilder sb = new StringBuilder();
-                sb.append('v').append(i).append(": ");
-                sb.append(defsites[i].toString());
-                System.out.println(sb);
-            }
-        }
-
-        BitSet worklist;
-
-        /*
-         * For each register, compute all locations for phi placement
-         * based on dominance-frontier algorithm.
-         */
-        for (int reg = 0, s = regCount; reg < s; reg++) {
-            int workBlockIndex;
-
-            /* Worklist set starts out with each node where reg is assigned. */
-
-            worklist = (BitSet) (defsites[reg].clone());
-
-            while (0 <= (workBlockIndex = worklist.nextSetBit(0))) {
-                worklist.clear(workBlockIndex);
-                IntIterator dfIterator
-                    = domInfos[workBlockIndex].dominanceFrontiers.iterator();
-
-                while (dfIterator.hasNext()) {
-                    int dfBlockIndex = dfIterator.next();
-
-                    if (!phisites[reg].get(dfBlockIndex)) {
-                        phisites[reg].set(dfBlockIndex);
-
-                        int tReg = reg + threshold;
-                        RegisterSpec rs
-                            = localInfo.getStarts(dfBlockIndex).get(tReg);
-
-                        if (rs == null) {
-                            ssaBlocks.get(dfBlockIndex).addPhiInsnForReg(tReg);
-                        } else {
-                            ssaBlocks.get(dfBlockIndex).addPhiInsnForReg(rs);
-                        }
-
-                        if (!defsites[reg].get(dfBlockIndex)) {
-                            worklist.set(dfBlockIndex);
-                        }
-                    }
-                }
-            }
-        }
-
-        if (DEBUG) {
-            System.out.println("phisites");
-
-            for (int i = 0; i < regCount; i++) {
-                StringBuilder sb = new StringBuilder();
-                sb.append('v').append(i).append(": ");
-                sb.append(phisites[i].toString());
-                System.out.println(sb);
-            }
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SsaInsn.java b/dx/src/com/android/jack/dx/ssa/SsaInsn.java
index bf76db2..403e56d 100644
--- a/dx/src/com/android/jack/dx/ssa/SsaInsn.java
+++ b/dx/src/com/android/jack/dx/ssa/SsaInsn.java
@@ -16,274 +16,276 @@
 
 package com.android.jack.dx.ssa;
 
-import com.android.jack.dx.rop.code.*;
+import com.android.jack.dx.rop.code.Insn;
+import com.android.jack.dx.rop.code.LocalItem;
+import com.android.jack.dx.rop.code.RegisterSpec;
+import com.android.jack.dx.rop.code.RegisterSpecList;
+import com.android.jack.dx.rop.code.Rop;
 import com.android.jack.dx.util.ToHuman;
 
 /**
  * An instruction in SSA form
  */
 public abstract class SsaInsn implements ToHuman, Cloneable {
-    /** {@code non-null;} the block that contains this instance */
-    private final SsaBasicBlock block;
+  /** {@code non-null;} the block that contains this instance */
+  private final SsaBasicBlock block;
 
-    /** {@code null-ok;} result register */
-    private RegisterSpec result;
+  /** {@code null-ok;} result register */
+  private RegisterSpec result;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param result {@code null-ok;} initial result register. May be changed.
-     * @param block {@code non-null;} block containing this insn. Can
-     * never change.
-     */
-    protected SsaInsn(RegisterSpec result, SsaBasicBlock block) {
-        if (block == null) {
-            throw new NullPointerException("block == null");
-        }
-
-        this.block = block;
-        this.result = result;
+  /**
+   * Constructs an instance.
+   *
+   * @param result {@code null-ok;} initial result register. May be changed.
+   * @param block {@code non-null;} block containing this insn. Can
+   * never change.
+   */
+  protected SsaInsn(RegisterSpec result, SsaBasicBlock block) {
+    if (block == null) {
+      throw new NullPointerException("block == null");
     }
 
-    /**
-     * Makes a new SSA insn form a rop insn.
-     *
-     * @param insn {@code non-null;} rop insn
-     * @param block {@code non-null;} owning block
-     * @return {@code non-null;} an appropriately constructed instance
-     */
-    public static SsaInsn makeFromRop(Insn insn, SsaBasicBlock block) {
-        return new NormalSsaInsn(insn, block);
+    this.block = block;
+    this.result = result;
+  }
+
+  /**
+   * Makes a new SSA insn form a rop insn.
+   *
+   * @param insn {@code non-null;} rop insn
+   * @param block {@code non-null;} owning block
+   * @return {@code non-null;} an appropriately constructed instance
+   */
+  public static SsaInsn makeFromRop(Insn insn, SsaBasicBlock block) {
+    return new NormalSsaInsn(insn, block);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public SsaInsn clone() {
+    try {
+      return (SsaInsn) super.clone();
+    } catch (CloneNotSupportedException ex) {
+      throw new RuntimeException("unexpected", ex);
+    }
+  }
+
+  /**
+   * Like {@link com.android.jack.dx.rop.code.Insn getResult()}.
+   *
+   * @return result register
+   */
+  public RegisterSpec getResult() {
+    return result;
+  }
+
+  /**
+   * Set the result register.
+   *
+   * @param result {@code non-null;} the new result register
+   */
+  protected void setResult(RegisterSpec result) {
+    if (result == null) {
+      throw new NullPointerException("result == null");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public SsaInsn clone() {
-        try {
-            return (SsaInsn)super.clone();
-        } catch (CloneNotSupportedException ex) {
-            throw new RuntimeException ("unexpected", ex);
-        }
+    this.result = result;
+  }
+
+  /**
+   * Like {@link com.android.jack.dx.rop.code.Insn getSources()}.
+   *
+   * @return {@code non-null;} sources list
+   */
+  public abstract RegisterSpecList getSources();
+
+  /**
+   * Gets the block to which this insn instance belongs.
+   *
+   * @return owning block
+   */
+  public SsaBasicBlock getBlock() {
+    return block;
+  }
+
+  /**
+   * Returns whether or not the specified reg is the result reg.
+   *
+   * @param reg register to test
+   * @return true if there is a result and it is stored in the specified
+   * register
+   */
+  public boolean isResultReg(int reg) {
+    return result != null && result.getReg() == reg;
+  }
+
+
+  /**
+   * Changes the result register if this insn has a result. This is used
+   * during renaming.
+   *
+   * @param reg new result register
+   */
+  public void changeResultReg(int reg) {
+    if (result != null) {
+      result = result.withReg(reg);
+    }
+  }
+
+  /**
+   * Sets the local association for the result of this insn. This is
+   * sometimes updated during the SsaRenamer process.
+   *
+   * @param local {@code null-ok;} new debug/local variable info
+   */
+  public final void setResultLocal(LocalItem local) {
+    LocalItem oldItem = result.getLocalItem();
+
+    if (local != oldItem && (local == null || !local.equals(result.getLocalItem()))) {
+      result = RegisterSpec.makeLocalOptional(result.getReg(), result.getType(), local);
+    }
+  }
+
+  /**
+   * Map registers after register allocation.
+   *
+   * @param mapper {@code non-null;} mapping from old to new registers
+   */
+  public final void mapRegisters(RegisterMapper mapper) {
+    RegisterSpec oldResult = result;
+
+    result = mapper.map(result);
+    block.getParent().updateOneDefinition(this, oldResult);
+    mapSourceRegisters(mapper);
+  }
+
+  /**
+   * Maps only source registers.
+   *
+   * @param mapper new mapping
+   */
+  public abstract void mapSourceRegisters(RegisterMapper mapper);
+
+  /**
+   * Returns the Rop opcode for this insn, or null if this is a phi insn.
+   *
+   * TODO(dx team): Move this up into NormalSsaInsn.
+   *
+   * @return {@code null-ok;} Rop opcode if there is one.
+   */
+  public abstract Rop getOpcode();
+
+  /**
+   * Returns the original Rop insn for this insn, or null if this is
+   * a phi insn.
+   *
+   * TODO(dx team): Move this up into NormalSsaInsn.
+   *
+   * @return {@code null-ok;} Rop insn if there is one.
+   */
+  public abstract Insn getOriginalRopInsn();
+
+  /**
+   * Gets the spec of a local variable assignment that occurs at this
+   * instruction, or null if no local variable assignment occurs. This
+   * may be the result register, or for {@code mark-local} insns
+   * it may be the source.
+   *
+   * @see com.android.jack.dx.rop.code.Insn#getLocalAssignment()
+   *
+   * @return {@code null-ok;} a local-associated register spec or null
+   */
+  public RegisterSpec getLocalAssignment() {
+    if (result != null && result.getLocalItem() != null) {
+      return result;
     }
 
+    return null;
+  }
+
+  /**
+   * Indicates whether the specified register is amongst the registers
+   * used as sources for this instruction.
+   *
+   * @param reg the register in question
+   * @return true if the reg is a source
+   */
+  public boolean isRegASource(int reg) {
+    return null != getSources().specForRegister(reg);
+  }
+
+  /**
+   * Transform back to ROP form.
+   *
+   * TODO(dx team): Move this up into NormalSsaInsn.
+   *
+   * @return {@code non-null;} a ROP representation of this instruction, with
+   * updated registers.
+   */
+  public abstract Insn toRopInsn();
+
+  /**
+   * @return true if this is a PhiInsn or a normal move insn
+   */
+  public abstract boolean isPhiOrMove();
+
+  /**
+   * Returns true if this insn is considered to have a side effect beyond
+   * that of assigning to the result reg.
+   *
+   * @return true if this insn is considered to have a side effect beyond
+   * that of assigning to the result reg.
+   */
+  public abstract boolean hasSideEffect();
+
+  /**
+   * @return true if this is a move (but not a move-operand or
+   * move-exception) instruction
+   */
+  public boolean isNormalMoveInsn() {
+    return false;
+  }
+
+  /**
+   * @return true if this is a move-exception instruction.
+   * These instructions must immediately follow a preceeding invoke*
+   */
+  public boolean isMoveException() {
+    return false;
+  }
+
+  /**
+   * @return true if this instruction can throw.
+   */
+  public abstract boolean canThrow();
+
+  /**
+   * Accepts a visitor.
+   *
+   * @param v {@code non-null} the visitor
+   */
+  public abstract void accept(Visitor v);
+
+  /**
+   * Visitor interface for this class.
+   */
+  public static interface Visitor {
     /**
-     * Like {@link com.android.jack.dx.rop.code.Insn getResult()}.
-     *
-     * @return result register
+     * Any non-phi move instruction
+     * @param insn {@code non-null;} the instruction to visit
      */
-    public RegisterSpec getResult() {
-        return result;
-    }
+    public void visitMoveInsn(NormalSsaInsn insn);
 
     /**
-     * Set the result register.
-     *
-     * @param result {@code non-null;} the new result register
+     * Any phi insn
+     * @param insn {@code non-null;} the instruction to visit
      */
-    protected void setResult(RegisterSpec result) {
-        if (result == null) {
-            throw new NullPointerException("result == null");
-        }
-
-        this.result = result;
-    }
+    public void visitPhiInsn(PhiInsn insn);
 
     /**
-     * Like {@link com.android.jack.dx.rop.code.Insn getSources()}.
-     *
-     * @return {@code non-null;} sources list
+     * Any insn that isn't a move or a phi (which is also a move).
+     * @param insn {@code non-null;} the instruction to visit
      */
-    abstract public RegisterSpecList getSources();
-
-    /**
-     * Gets the block to which this insn instance belongs.
-     *
-     * @return owning block
-     */
-    public SsaBasicBlock getBlock() {
-        return block;
-    }
-
-    /**
-     * Returns whether or not the specified reg is the result reg.
-     *
-     * @param reg register to test
-     * @return true if there is a result and it is stored in the specified
-     * register
-     */
-    public boolean isResultReg(int reg) {
-        return result != null && result.getReg() == reg;
-    }
-
-
-    /**
-     * Changes the result register if this insn has a result. This is used
-     * during renaming.
-     *
-     * @param reg new result register
-     */
-    public void changeResultReg(int reg) {
-        if (result != null) {
-            result = result.withReg(reg);
-        }
-    }
-
-    /**
-     * Sets the local association for the result of this insn. This is
-     * sometimes updated during the SsaRenamer process.
-     *
-     * @param local {@code null-ok;} new debug/local variable info
-     */
-    public final void setResultLocal(LocalItem local) {
-        LocalItem oldItem = result.getLocalItem();
-
-        if (local != oldItem && (local == null
-                || !local.equals(result.getLocalItem()))) {
-            result = RegisterSpec.makeLocalOptional(
-                    result.getReg(), result.getType(), local);
-        }
-    }
-
-    /**
-     * Map registers after register allocation.
-     *
-     * @param mapper {@code non-null;} mapping from old to new registers
-     */
-    public final void mapRegisters(RegisterMapper mapper) {
-        RegisterSpec oldResult = result;
-
-        result = mapper.map(result);
-        block.getParent().updateOneDefinition(this, oldResult);
-        mapSourceRegisters(mapper);
-    }
-
-    /**
-     * Maps only source registers.
-     *
-     * @param mapper new mapping
-     */
-    abstract public void mapSourceRegisters(RegisterMapper mapper);
-
-    /**
-     * Returns the Rop opcode for this insn, or null if this is a phi insn.
-     *
-     * TODO: Move this up into NormalSsaInsn.
-     *
-     * @return {@code null-ok;} Rop opcode if there is one.
-     */
-    abstract public Rop getOpcode();
-
-    /**
-     * Returns the original Rop insn for this insn, or null if this is
-     * a phi insn.
-     *
-     * TODO: Move this up into NormalSsaInsn.
-     *
-     * @return {@code null-ok;} Rop insn if there is one.
-     */
-    abstract public Insn getOriginalRopInsn();
-
-    /**
-     * Gets the spec of a local variable assignment that occurs at this
-     * instruction, or null if no local variable assignment occurs. This
-     * may be the result register, or for {@code mark-local} insns
-     * it may be the source.
-     *
-     * @see com.android.jack.dx.rop.code.Insn#getLocalAssignment()
-     *
-     * @return {@code null-ok;} a local-associated register spec or null
-     */
-    public RegisterSpec getLocalAssignment() {
-        if (result != null && result.getLocalItem() != null) {
-            return result;
-        }
-
-        return null;
-    }
-
-    /**
-     * Indicates whether the specified register is amongst the registers
-     * used as sources for this instruction.
-     *
-     * @param reg the register in question
-     * @return true if the reg is a source
-     */
-    public boolean isRegASource(int reg) {
-        return null != getSources().specForRegister(reg);
-    }
-
-    /**
-     * Transform back to ROP form.
-     *
-     * TODO: Move this up into NormalSsaInsn.
-     *
-     * @return {@code non-null;} a ROP representation of this instruction, with
-     * updated registers.
-     */
-    public abstract Insn toRopInsn();
-
-    /**
-     * @return true if this is a PhiInsn or a normal move insn
-     */
-    public abstract boolean isPhiOrMove();
-
-    /**
-     * Returns true if this insn is considered to have a side effect beyond
-     * that of assigning to the result reg.
-     *
-     * @return true if this insn is considered to have a side effect beyond
-     * that of assigning to the result reg.
-     */
-    public abstract boolean hasSideEffect();
-
-    /**
-     * @return true if this is a move (but not a move-operand or
-     * move-exception) instruction
-     */
-    public boolean isNormalMoveInsn() {
-        return false;
-    }
-
-    /**
-     * @return true if this is a move-exception instruction.
-     * These instructions must immediately follow a preceeding invoke*
-     */
-    public boolean isMoveException() {
-        return false;
-    }
-
-    /**
-     * @return true if this instruction can throw.
-     */
-    abstract public boolean canThrow();
-
-    /**
-     * Accepts a visitor.
-     *
-     * @param v {@code non-null} the visitor
-     */
-    public abstract void accept(Visitor v);
-
-    /**
-     * Visitor interface for this class.
-     */
-    public static interface Visitor {
-        /**
-         * Any non-phi move instruction
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitMoveInsn(NormalSsaInsn insn);
-
-        /**
-         * Any phi insn
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitPhiInsn(PhiInsn insn);
-
-        /**
-         * Any insn that isn't a move or a phi (which is also a move).
-         * @param insn {@code non-null;} the instruction to visit
-         */
-        public void visitNonMoveInsn(NormalSsaInsn insn);
-    }
+    public void visitNonMoveInsn(NormalSsaInsn insn);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SsaMethod.java b/dx/src/com/android/jack/dx/ssa/SsaMethod.java
index f0166df..314bddb 100644
--- a/dx/src/com/android/jack/dx/ssa/SsaMethod.java
+++ b/dx/src/com/android/jack/dx/ssa/SsaMethod.java
@@ -39,835 +39,839 @@
  * A method in SSA form.
  */
 public final class SsaMethod {
-    /** basic blocks, indexed by block index */
-    private ArrayList<SsaBasicBlock> blocks;
+  /** basic blocks, indexed by block index */
+  private ArrayList<SsaBasicBlock> blocks;
 
-    /** Index of first executed block in method */
-    private int entryBlockIndex;
+  /** Index of first executed block in method */
+  private int entryBlockIndex;
 
-    /**
-     * Index of exit block, which exists only in SSA form,
-     * or or {@code -1} if there is none
-     */
-    private int exitBlockIndex;
+  /**
+   * Index of exit block, which exists only in SSA form,
+   * or or {@code -1} if there is none
+   */
+  private int exitBlockIndex;
 
-    /** total number of registers required */
-    private int registerCount;
+  /** total number of registers required */
+  private int registerCount;
 
-    /** first register number to use for any temporary "spares" */
-    private int spareRegisterBase;
+  /** first register number to use for any temporary "spares" */
+  private int spareRegisterBase;
 
-    /** current count of spare registers used */
-    private int borrowedSpareRegisters;
+  /** current count of spare registers used */
+  private int borrowedSpareRegisters;
 
-    /** really one greater than the max label */
-    private int maxLabel;
+  /** really one greater than the max label */
+  private int maxLabel;
 
-    /** the total width, in register-units, of the method's parameters */
-    private final int paramWidth;
+  /** the total width, in register-units, of the method's parameters */
+  private final int paramWidth;
 
-    /** true if this method has no {@code this} pointer argument */
-    private final boolean isStatic;
+  /** true if this method has no {@code this} pointer argument */
+  private final boolean isStatic;
 
-    /**
-     * indexed by register: the insn where said register is defined or null
-     * if undefined. null until (lazily) created.
-     */
-    private SsaInsn[] definitionList;
+  /**
+   * indexed by register: the insn where said register is defined or null
+   * if undefined. null until (lazily) created.
+   */
+  private SsaInsn[] definitionList;
 
-    /** indexed by register: the list of all insns that use a register */
-    private ArrayList<SsaInsn>[] useList;
+  /** indexed by register: the list of all insns that use a register */
+  private ArrayList<SsaInsn>[] useList;
 
-    /** A version of useList with each List unmodifiable */
-    private List<SsaInsn>[] unmodifiableUseList;
+  /** A version of useList with each List unmodifiable */
+  private List<SsaInsn>[] unmodifiableUseList;
 
-    /**
-     * "back-convert mode". Set during back-conversion when registers
-     * are about to be mapped into a non-SSA namespace. When true,
-     * use and def lists are unavailable.
-     *
-     * TODO: Remove this mode, and place the functionality elsewhere
-     */
-    private boolean backMode;
+  /**
+   * "back-convert mode". Set during back-conversion when registers
+   * are about to be mapped into a non-SSA namespace. When true,
+   * use and def lists are unavailable.
+   *
+   * TODO(dx team): Remove this mode, and place the functionality elsewhere
+   */
+  private boolean backMode;
 
-    /**
-     * @param ropMethod rop-form method to convert from
-     * @param paramWidth the total width, in register-units, of the
-     * method's parameters
-     * @param isStatic {@code true} if this method has no {@code this}
-     * pointer argument
-     */
-    public static SsaMethod newFromRopMethod(RopMethod ropMethod,
-            int paramWidth, boolean isStatic) {
-        SsaMethod result = new SsaMethod(ropMethod, paramWidth, isStatic);
+  /**
+   * @param ropMethod rop-form method to convert from
+   * @param paramWidth the total width, in register-units, of the
+   * method's parameters
+   * @param isStatic {@code true} if this method has no {@code this}
+   * pointer argument
+   */
+  public static SsaMethod newFromRopMethod(RopMethod ropMethod, int paramWidth, boolean isStatic) {
+    SsaMethod result = new SsaMethod(ropMethod, paramWidth, isStatic);
 
-        result.convertRopToSsaBlocks(ropMethod);
+    result.convertRopToSsaBlocks(ropMethod);
 
-        return result;
+    return result;
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param ropMethod {@code non-null;} the original rop-form method that
+   * this instance is based on
+   * @param paramWidth the total width, in register-units, of the
+   * method's parameters
+   * @param isStatic {@code true} if this method has no {@code this}
+   * pointer argument
+   */
+  private SsaMethod(RopMethod ropMethod, int paramWidth, boolean isStatic) {
+    this.paramWidth = paramWidth;
+    this.isStatic = isStatic;
+    this.backMode = false;
+    this.maxLabel = ropMethod.getBlocks().getMaxLabel();
+    this.registerCount = ropMethod.getBlocks().getRegCount();
+    this.spareRegisterBase = registerCount;
+  }
+
+  /**
+   * Builds a BitSet of block indices from a basic block list and a list
+   * of labels taken from Rop form.
+   *
+   * @param blocks Rop blocks
+   * @param labelList list of rop block labels
+   * @return BitSet of block indices
+   */
+  static BitSet bitSetFromLabelList(BasicBlockList blocks, IntList labelList) {
+    BitSet result = new BitSet(blocks.size());
+
+    for (int i = 0, sz = labelList.size(); i < sz; i++) {
+      result.set(blocks.indexOfLabel(labelList.get(i)));
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ropMethod {@code non-null;} the original rop-form method that
-     * this instance is based on
-     * @param paramWidth the total width, in register-units, of the
-     * method's parameters
-     * @param isStatic {@code true} if this method has no {@code this}
-     * pointer argument
-     */
-    private SsaMethod(RopMethod ropMethod, int paramWidth, boolean isStatic) {
-        this.paramWidth = paramWidth;
-        this.isStatic = isStatic;
-        this.backMode = false;
-        this.maxLabel = ropMethod.getBlocks().getMaxLabel();
-        this.registerCount = ropMethod.getBlocks().getRegCount();
-        this.spareRegisterBase = registerCount;
+    return result;
+  }
+
+  /**
+   * Builds an IntList of block indices from a basic block list and a list
+   * of labels taken from Rop form.
+   *
+   * @param ropBlocks Rop blocks
+   * @param labelList list of rop block labels
+   * @return IntList of block indices
+   */
+  public static IntList indexListFromLabelList(BasicBlockList ropBlocks, IntList labelList) {
+
+    IntList result = new IntList(labelList.size());
+
+    for (int i = 0, sz = labelList.size(); i < sz; i++) {
+      result.add(ropBlocks.indexOfLabel(labelList.get(i)));
     }
 
-    /**
-     * Builds a BitSet of block indices from a basic block list and a list
-     * of labels taken from Rop form.
-     *
-     * @param blocks Rop blocks
-     * @param labelList list of rop block labels
-     * @return BitSet of block indices
-     */
-    static BitSet bitSetFromLabelList(BasicBlockList blocks,
-            IntList labelList) {
-        BitSet result = new BitSet(blocks.size());
+    return result;
+  }
 
-        for (int i = 0, sz = labelList.size(); i < sz; i++) {
-            result.set(blocks.indexOfLabel(labelList.get(i)));
+  private void convertRopToSsaBlocks(RopMethod rmeth) {
+    BasicBlockList ropBlocks = rmeth.getBlocks();
+    int sz = ropBlocks.size();
+
+    blocks = new ArrayList<SsaBasicBlock>(sz + 2);
+
+    for (int i = 0; i < sz; i++) {
+      SsaBasicBlock sbb = SsaBasicBlock.newFromRop(rmeth, i, this);
+      blocks.add(sbb);
+    }
+
+    // Add an no-op entry block.
+    int origEntryBlockIndex = rmeth.getBlocks().indexOfLabel(rmeth.getFirstLabel());
+
+    SsaBasicBlock entryBlock = blocks.get(origEntryBlockIndex).insertNewPredecessor();
+
+    entryBlockIndex = entryBlock.getIndex();
+    exitBlockIndex = -1; // This gets made later.
+  }
+
+  /**
+   * Creates an exit block and attaches it to the CFG if this method
+   * exits. Methods that never exit will not have an exit block. This
+   * is called after edge-splitting and phi insertion, since the edges
+   * going into the exit block should not be considered in those steps.
+   */
+  /*package*/void makeExitBlock() {
+    if (exitBlockIndex >= 0) {
+      throw new RuntimeException("must be called at most once");
+    }
+
+    exitBlockIndex = blocks.size();
+    SsaBasicBlock exitBlock = new SsaBasicBlock(exitBlockIndex, maxLabel++, this);
+
+    blocks.add(exitBlock);
+
+    for (SsaBasicBlock block : blocks) {
+      block.exitBlockFixup(exitBlock);
+    }
+
+    if (exitBlock.getPredecessors().cardinality() == 0) {
+      // In cases where there is no exit...
+      blocks.remove(exitBlockIndex);
+      exitBlockIndex = -1;
+      maxLabel--;
+    }
+  }
+
+  /**
+   * Gets a new {@code GOTO} insn.
+   *
+   * @param block block to which this GOTO will be added
+   * (not it's destination!)
+   * @return an appropriately-constructed instance.
+   */
+  private static SsaInsn getGoto(SsaBasicBlock block) {
+    return new NormalSsaInsn(
+        new PlainInsn(Rops.GOTO, SourcePosition.NO_INFO, null, RegisterSpecList.EMPTY), block);
+  }
+
+  /**
+   * Makes a new basic block for this method, which is empty besides
+   * a single {@code GOTO}. Successors and predecessors are not yet
+   * set.
+   *
+   * @return new block
+   */
+  public SsaBasicBlock makeNewGotoBlock() {
+    int newIndex = blocks.size();
+    SsaBasicBlock newBlock = new SsaBasicBlock(newIndex, maxLabel++, this);
+
+    newBlock.getInsns().add(getGoto(newBlock));
+    blocks.add(newBlock);
+
+    return newBlock;
+  }
+
+  /**
+   * @return block index of first execution block
+   */
+  public int getEntryBlockIndex() {
+    return entryBlockIndex;
+  }
+
+  /**
+   * @return first execution block
+   */
+  public SsaBasicBlock getEntryBlock() {
+    return blocks.get(entryBlockIndex);
+  }
+
+  /**
+   * @return block index of exit block or {@code -1} if there is none
+   */
+  public int getExitBlockIndex() {
+    return exitBlockIndex;
+  }
+
+  /**
+   * @return {@code null-ok;} block of exit block or {@code null} if
+   * there is none
+   */
+  public SsaBasicBlock getExitBlock() {
+    return exitBlockIndex < 0 ? null : blocks.get(exitBlockIndex);
+  }
+
+  /**
+   * @param bi block index or {@code -1} for none
+   * @return rop label or {code -1} if {@code bi} was {@code -1}
+   */
+  public int blockIndexToRopLabel(int bi) {
+    if (bi < 0) {
+      return -1;
+    }
+    return blocks.get(bi).getRopLabel();
+  }
+
+  /**
+   * @return count of registers used in this method
+   */
+  public int getRegCount() {
+    return registerCount;
+  }
+
+  /**
+   * @return the total width, in register units, of the method's
+   * parameters
+   */
+  public int getParamWidth() {
+    return paramWidth;
+  }
+
+  /**
+   * Returns {@code true} if this is a static method.
+   *
+   * @return {@code true} if this is a static method
+   */
+  public boolean isStatic() {
+    return isStatic;
+  }
+
+  /**
+   * Borrows a register to use as a temp. Used in the phi removal process.
+   * Call returnSpareRegisters() when done.
+   *
+   * @param category width (1 or 2) of the register
+   * @return register number to use
+   */
+  public int borrowSpareRegister(int category) {
+    int result = spareRegisterBase + borrowedSpareRegisters;
+
+    borrowedSpareRegisters += category;
+    registerCount = Math.max(registerCount, result + category);
+
+    return result;
+  }
+
+  /**
+   * Returns all borrowed registers.
+   */
+  public void returnSpareRegisters() {
+    borrowedSpareRegisters = 0;
+  }
+
+  /**
+   * @return {@code non-null;} basic block list. Do not modify.
+   */
+  public ArrayList<SsaBasicBlock> getBlocks() {
+    return blocks;
+  }
+
+  /**
+   * Returns the count of reachable blocks in this method: blocks that have
+   * predecessors (or are the start block)
+   *
+   * @return {@code >= 0;} number of reachable basic blocks
+   */
+  public int getCountReachableBlocks() {
+    int ret = 0;
+
+    for (SsaBasicBlock b : blocks) {
+      // Blocks that have been disconnected don't count.
+      if (b.isReachable()) {
+        ret++;
+      }
+    }
+
+    return ret;
+  }
+
+  /**
+   * Computes reachability for all blocks in the method. First clears old
+   * values from all blocks, then starts with the entry block and walks down
+   * the control flow graph, marking all blocks it finds as reachable.
+   */
+  public void computeReachability() {
+    for (SsaBasicBlock block : blocks) {
+      block.setReachable(0);
+    }
+
+    ArrayList<SsaBasicBlock> blockList = new ArrayList<SsaBasicBlock>();
+    blockList.add(this.getEntryBlock());
+
+    while (!blockList.isEmpty()) {
+      SsaBasicBlock block = blockList.remove(0);
+      if (block.isReachable()) {
+        continue;
+      }
+
+      block.setReachable(1);
+      BitSet succs = block.getSuccessors();
+      for (int i = succs.nextSetBit(0); i >= 0; i = succs.nextSetBit(i + 1)) {
+        blockList.add(blocks.get(i));
+      }
+    }
+  }
+
+  /**
+   * Remaps unversioned registers.
+   *
+   * @param mapper maps old registers to new.
+   */
+  public void mapRegisters(RegisterMapper mapper) {
+    for (SsaBasicBlock block : getBlocks()) {
+      for (SsaInsn insn : block.getInsns()) {
+        insn.mapRegisters(mapper);
+      }
+    }
+
+    registerCount = mapper.getNewRegisterCount();
+    spareRegisterBase = registerCount;
+  }
+
+  /**
+   * Returns the insn that defines the given register
+   * @param reg register in question
+   * @return insn (actual instance from code) that defined this reg or null
+   * if reg is not defined.
+   */
+  public SsaInsn getDefinitionForRegister(int reg) {
+    if (backMode) {
+      throw new RuntimeException("No def list in back mode");
+    }
+
+    if (definitionList != null) {
+      return definitionList[reg];
+    }
+
+    definitionList = new SsaInsn[getRegCount()];
+
+    forEachInsn(new SsaInsn.Visitor() {
+      @Override
+      public void visitMoveInsn(NormalSsaInsn insn) {
+        definitionList[insn.getResult().getReg()] = insn;
+      }
+
+      @Override
+      public void visitPhiInsn(PhiInsn phi) {
+        definitionList[phi.getResult().getReg()] = phi;
+      }
+
+      @Override
+      public void visitNonMoveInsn(NormalSsaInsn insn) {
+        RegisterSpec result = insn.getResult();
+        if (result != null) {
+          definitionList[insn.getResult().getReg()] = insn;
         }
+      }
+    });
 
-        return result;
+    return definitionList[reg];
+  }
+
+  /**
+   * Builds useList and unmodifiableUseList.
+   */
+  @SuppressWarnings("unchecked")
+  private void buildUseList() {
+    if (backMode) {
+      throw new RuntimeException("No use list in back mode");
     }
 
-    /**
-     * Builds an IntList of block indices from a basic block list and a list
-     * of labels taken from Rop form.
-     *
-     * @param ropBlocks Rop blocks
-     * @param labelList list of rop block labels
-     * @return IntList of block indices
-     */
-    public static IntList indexListFromLabelList(BasicBlockList ropBlocks,
-            IntList labelList) {
+    useList = new ArrayList[registerCount];
 
-        IntList result = new IntList(labelList.size());
-
-        for (int i = 0, sz = labelList.size(); i < sz; i++) {
-            result.add(ropBlocks.indexOfLabel(labelList.get(i)));
-        }
-
-        return result;
+    for (int i = 0; i < registerCount; i++) {
+      useList[i] = new ArrayList<SsaInsn>();
     }
 
-    private void convertRopToSsaBlocks(RopMethod rmeth) {
-        BasicBlockList ropBlocks = rmeth.getBlocks();
-        int sz = ropBlocks.size();
+    forEachInsn(new SsaInsn.Visitor() {
+      /** {@inheritDoc} */
+      @Override
+      public void visitMoveInsn(NormalSsaInsn insn) {
+        addToUses(insn);
+      }
 
-        blocks = new ArrayList<SsaBasicBlock>(sz + 2);
+      /** {@inheritDoc} */
+      @Override
+      public void visitPhiInsn(PhiInsn phi) {
+        addToUses(phi);
+      }
+
+      /** {@inheritDoc} */
+      @Override
+      public void visitNonMoveInsn(NormalSsaInsn insn) {
+        addToUses(insn);
+      }
+
+      /**
+       * Adds specified insn to the uses list for all of its sources.
+       * @param insn {@code non-null;} insn to process
+       */
+      private void addToUses(SsaInsn insn) {
+        RegisterSpecList rl = insn.getSources();
+        int sz = rl.size();
 
         for (int i = 0; i < sz; i++) {
-            SsaBasicBlock sbb = SsaBasicBlock.newFromRop(rmeth, i, this);
-            blocks.add(sbb);
+          useList[rl.get(i).getReg()].add(insn);
         }
+      }
+    });
 
-        // Add an no-op entry block.
-        int origEntryBlockIndex = rmeth.getBlocks()
-                .indexOfLabel(rmeth.getFirstLabel());
+    unmodifiableUseList = new List[registerCount];
 
-        SsaBasicBlock entryBlock
-                = blocks.get(origEntryBlockIndex).insertNewPredecessor();
+    for (int i = 0; i < registerCount; i++) {
+      unmodifiableUseList[i] = Collections.unmodifiableList(useList[i]);
+    }
+  }
 
-        entryBlockIndex = entryBlock.getIndex();
-        exitBlockIndex = -1; // This gets made later.
+  /**
+   * Updates the use list for a single change in source register.
+   *
+   * @param insn {@code non-null;} insn being changed
+   * @param oldSource {@code null-ok;} The source that was used, if
+   * applicable
+   * @param newSource {@code non-null;} the new source being used
+   */
+  /*package*/void onSourceChanged(SsaInsn insn, RegisterSpec oldSource, RegisterSpec newSource) {
+    if (useList == null) {
+      return;
     }
 
-    /**
-     * Creates an exit block and attaches it to the CFG if this method
-     * exits. Methods that never exit will not have an exit block. This
-     * is called after edge-splitting and phi insertion, since the edges
-     * going into the exit block should not be considered in those steps.
-     */
-    /*package*/ void makeExitBlock() {
-        if (exitBlockIndex >= 0) {
-            throw new RuntimeException("must be called at most once");
+    if (oldSource != null) {
+      int reg = oldSource.getReg();
+      useList[reg].remove(insn);
+    }
+
+    int reg = newSource.getReg();
+    if (useList.length <= reg) {
+      useList = null;
+      return;
+    }
+    useList[reg].add(insn);
+  }
+
+  /**
+   * Updates the use list for a source list change.
+   *
+   * @param insn {@code insn non-null;} insn being changed.
+   * {@code insn.getSources()} must return the new source list.
+   * @param oldSources {@code null-ok;} list of sources that were
+   * previously used
+   */
+  /*package*/void onSourcesChanged(SsaInsn insn, RegisterSpecList oldSources) {
+    if (useList == null) {
+      return;
+    }
+
+    if (oldSources != null) {
+      removeFromUseList(insn, oldSources);
+    }
+
+    RegisterSpecList sources = insn.getSources();
+    int szNew = sources.size();
+
+    for (int i = 0; i < szNew; i++) {
+      int reg = sources.get(i).getReg();
+      useList[reg].add(insn);
+    }
+  }
+
+  /**
+   * Removes a given {@code insn} from the use lists for the given
+   * {@code oldSources} (rather than the sources currently
+   * returned by insn.getSources()).
+   *
+   * @param insn {@code non-null;} insn in question
+   * @param oldSources {@code null-ok;} registers whose use lists
+   * {@code insn} should be removed form
+   */
+  private void removeFromUseList(SsaInsn insn, RegisterSpecList oldSources) {
+    if (oldSources == null) {
+      return;
+    }
+
+    int szNew = oldSources.size();
+    for (int i = 0; i < szNew; i++) {
+      if (!useList[oldSources.get(i).getReg()].remove(insn)) {
+        throw new RuntimeException("use not found");
+      }
+    }
+  }
+
+  /**
+   * Adds an insn to both the use and def lists. For use when adding
+   * a new insn to the method.
+   *
+   * @param insn {@code non-null;} insn to add
+   */
+  /*package*/void onInsnAdded(SsaInsn insn) {
+    onSourcesChanged(insn, null);
+    updateOneDefinition(insn, null);
+  }
+
+  /**
+   * Removes an instruction from use and def lists. For use during
+   * instruction removal.
+   *
+   * @param insn {@code non-null;} insn to remove
+   */
+  /*package*/void onInsnRemoved(SsaInsn insn) {
+    if (useList != null) {
+      removeFromUseList(insn, insn.getSources());
+    }
+
+    RegisterSpec resultReg = insn.getResult();
+    if (definitionList != null && resultReg != null) {
+      definitionList[resultReg.getReg()] = null;
+    }
+  }
+
+  /**
+   * Indicates that the instruction list has changed or the SSA register
+   * count has increased, so that internal datastructures that rely on
+   * it should be rebuild. In general, the various other on* methods
+   * should be called in preference when changes occur if they are
+   * applicable.
+   */
+  public void onInsnsChanged() {
+    // Definition list will need to be recomputed
+    definitionList = null;
+
+    // Use list will need to be recomputed
+    useList = null;
+    unmodifiableUseList = null;
+  }
+
+  /**
+   * Updates a single definition.
+   *
+   * @param insn {@code non-null;} insn who's result should be recorded as
+   * a definition
+   * @param oldResult {@code null-ok;} a previous result that should
+   * be no longer considered a definition by this insn
+   */
+  /*package*/void updateOneDefinition(SsaInsn insn, RegisterSpec oldResult) {
+    if (definitionList == null) {
+      return;
+    }
+
+    if (oldResult != null) {
+      int reg = oldResult.getReg();
+      definitionList[reg] = null;
+    }
+
+    RegisterSpec resultReg = insn.getResult();
+
+    if (resultReg != null) {
+      int reg = resultReg.getReg();
+
+      if (definitionList[reg] != null) {
+        throw new RuntimeException("Duplicate add of insn");
+      } else {
+        definitionList[resultReg.getReg()] = insn;
+      }
+    }
+  }
+
+  /**
+   * Returns the list of all source uses (not results) for a register.
+   *
+   * @param reg register in question
+   * @return unmodifiable instruction list
+   */
+  public List<SsaInsn> getUseListForRegister(int reg) {
+
+    if (unmodifiableUseList == null) {
+      buildUseList();
+    }
+
+    return unmodifiableUseList[reg];
+  }
+
+  /**
+   * Returns a modifiable copy of the register use list.
+   *
+   * @return modifiable copy of the use-list, indexed by register
+   */
+  public ArrayList<SsaInsn>[] getUseListCopy() {
+    if (useList == null) {
+      buildUseList();
+    }
+
+    @SuppressWarnings("unchecked")
+    ArrayList<SsaInsn>[] useListCopy = new ArrayList[registerCount];
+
+    for (int i = 0; i < registerCount; i++) {
+      useListCopy[i] = new ArrayList<SsaInsn>(useList[i]);
+    }
+
+    return useListCopy;
+  }
+
+  /**
+   * Checks to see if the given SSA reg is ever associated with a local
+   * local variable. Each SSA reg may be associated with at most one
+   * local var.
+   *
+   * @param spec {@code non-null;} ssa reg
+   * @return true if reg is ever associated with a local
+   */
+  public boolean isRegALocal(RegisterSpec spec) {
+    SsaInsn defn = getDefinitionForRegister(spec.getReg());
+
+    if (defn == null) {
+      // version 0 registers are never used as locals
+      return false;
+    }
+
+    // Does the definition have a local associated with it?
+    if (defn.getLocalAssignment() != null) {
+      return true;
+    }
+
+    // If not, is there a mark-local insn?
+    for (SsaInsn use : getUseListForRegister(spec.getReg())) {
+      Insn insn = use.getOriginalRopInsn();
+
+      if (insn != null && insn.getOpcode().getOpcode() == RegOps.MARK_LOCAL) {
+        return true;
+      }
+    }
+
+    return false;
+  }
+
+  /**
+   * Sets the new register count after renaming.
+   *
+   * @param newRegCount new register count
+   */
+  /*package*/void setNewRegCount(int newRegCount) {
+    registerCount = newRegCount;
+    spareRegisterBase = registerCount;
+    onInsnsChanged();
+  }
+
+  /**
+   * Makes a new SSA register. For use after renaming has completed.
+   *
+   * @return {@code >=0;} new SSA register.
+   */
+  public int makeNewSsaReg() {
+    int reg = registerCount++;
+    spareRegisterBase = registerCount;
+    onInsnsChanged();
+    return reg;
+  }
+
+  /**
+   * Visits all insns in this method.
+   *
+   * @param visitor {@code non-null;} callback interface
+   */
+  public void forEachInsn(SsaInsn.Visitor visitor) {
+    for (SsaBasicBlock block : blocks) {
+      block.forEachInsn(visitor);
+    }
+  }
+
+  /**
+   * Visits each phi insn in this method
+   * @param v {@code non-null;} callback.
+   *
+   */
+  public void forEachPhiInsn(PhiInsn.Visitor v) {
+    for (SsaBasicBlock block : blocks) {
+      block.forEachPhiInsn(v);
+    }
+  }
+
+
+  /**
+   * Walks the basic block tree in depth-first order, calling the visitor
+   * method once for every block. This depth-first walk may be run forward
+   * from the method entry point or backwards from the method exit points.
+   *
+   * @param reverse true if this should walk backwards from the exit points
+   * @param v {@code non-null;} callback interface. {@code parent} is set
+   * unless this is the root node
+   */
+  public void forEachBlockDepthFirst(boolean reverse, SsaBasicBlock.Visitor v) {
+    BitSet visited = new BitSet(blocks.size());
+
+    // We push the parent first, then the child on the stack.
+    Stack<SsaBasicBlock> stack = new Stack<SsaBasicBlock>();
+
+    SsaBasicBlock rootBlock = reverse ? getExitBlock() : getEntryBlock();
+
+    if (rootBlock == null) {
+      // in the case there's no exit block
+      return;
+    }
+
+    stack.add(null); // Start with null parent.
+    stack.add(rootBlock);
+
+    while (stack.size() > 0) {
+      SsaBasicBlock cur = stack.pop();
+      SsaBasicBlock parent = stack.pop();
+
+      if (!visited.get(cur.getIndex())) {
+        BitSet children = reverse ? cur.getPredecessors() : cur.getSuccessors();
+        for (int i = children.nextSetBit(0); i >= 0; i = children.nextSetBit(i + 1)) {
+          stack.add(cur);
+          stack.add(blocks.get(i));
         }
+        visited.set(cur.getIndex());
+        v.visitBlock(cur, parent);
+      }
+    }
+  }
 
-        exitBlockIndex = blocks.size();
-        SsaBasicBlock exitBlock
-                = new SsaBasicBlock(exitBlockIndex, maxLabel++, this);
+  /**
+   * Visits blocks in dom-tree order, starting at the current node.
+   * The {@code parent} parameter of the Visitor.visitBlock callback
+   * is currently always set to null.
+   *
+   * @param v {@code non-null;} callback interface
+   */
+  public void forEachBlockDepthFirstDom(SsaBasicBlock.Visitor v) {
+    BitSet visited = new BitSet(getBlocks().size());
+    Stack<SsaBasicBlock> stack = new Stack<SsaBasicBlock>();
 
-        blocks.add(exitBlock);
+    stack.add(getEntryBlock());
 
-        for (SsaBasicBlock block : blocks) {
-            block.exitBlockFixup(exitBlock);
+    while (stack.size() > 0) {
+      SsaBasicBlock cur = stack.pop();
+      ArrayList<SsaBasicBlock> curDomChildren = cur.getDomChildren();
+
+      if (!visited.get(cur.getIndex())) {
+        // We walk the tree this way for historical reasons...
+        for (int i = curDomChildren.size() - 1; i >= 0; i--) {
+          SsaBasicBlock child = curDomChildren.get(i);
+          stack.add(child);
         }
+        visited.set(cur.getIndex());
+        v.visitBlock(cur, null);
+      }
+    }
+  }
 
-        if (exitBlock.getPredecessors().cardinality() == 0) {
-            // In cases where there is no exit...
-            blocks.remove(exitBlockIndex);
-            exitBlockIndex = -1;
-            maxLabel--;
+  /**
+   * Deletes all insns in the set from this method.
+   *
+   * @param deletedInsns {@code non-null;} insns to delete
+   */
+  public void deleteInsns(Set<SsaInsn> deletedInsns) {
+    for (SsaBasicBlock block : getBlocks()) {
+      ArrayList<SsaInsn> insns = block.getInsns();
+
+      for (int i = insns.size() - 1; i >= 0; i--) {
+        SsaInsn insn = insns.get(i);
+
+        if (deletedInsns.contains(insn)) {
+          onInsnRemoved(insn);
+          insns.remove(i);
         }
-    }
+      }
 
-    /**
-     * Gets a new {@code GOTO} insn.
-     *
-     * @param block block to which this GOTO will be added
-     * (not it's destination!)
-     * @return an appropriately-constructed instance.
-     */
-    private static SsaInsn getGoto(SsaBasicBlock block) {
-        return new NormalSsaInsn (
-                new PlainInsn(Rops.GOTO, SourcePosition.NO_INFO,
-                    null, RegisterSpecList.EMPTY), block);
-    }
+      // Check to see if we need to add a GOTO
 
-    /**
-     * Makes a new basic block for this method, which is empty besides
-     * a single {@code GOTO}. Successors and predecessors are not yet
-     * set.
-     *
-     * @return new block
-     */
-    public SsaBasicBlock makeNewGotoBlock() {
-        int newIndex = blocks.size();
-        SsaBasicBlock newBlock = new SsaBasicBlock(newIndex, maxLabel++, this);
+      int insnsSz = insns.size();
+      SsaInsn lastInsn = (insnsSz == 0) ? null : insns.get(insnsSz - 1);
 
-        newBlock.getInsns().add(getGoto(newBlock));
-        blocks.add(newBlock);
+      if (block != getExitBlock() && (insnsSz == 0 || lastInsn.getOriginalRopInsn() == null
+          || lastInsn.getOriginalRopInsn().getOpcode().getBranchingness() == Rop.BRANCH_NONE)) {
+        // We managed to eat a throwable insn
 
-        return newBlock;
-    }
+        Insn gotoInsn =
+            new PlainInsn(Rops.GOTO, SourcePosition.NO_INFO, null, RegisterSpecList.EMPTY);
+        insns.add(SsaInsn.makeFromRop(gotoInsn, block));
 
-    /**
-     * @return block index of first execution block
-     */
-    public int getEntryBlockIndex() {
-        return entryBlockIndex;
-    }
-
-    /**
-     * @return first execution block
-     */
-    public SsaBasicBlock getEntryBlock() {
-        return blocks.get(entryBlockIndex);
-    }
-
-    /**
-     * @return block index of exit block or {@code -1} if there is none
-     */
-    public int getExitBlockIndex() {
-        return exitBlockIndex;
-    }
-
-    /**
-     * @return {@code null-ok;} block of exit block or {@code null} if
-     * there is none
-     */
-    public SsaBasicBlock getExitBlock() {
-        return exitBlockIndex < 0 ? null : blocks.get(exitBlockIndex);
-    }
-
-    /**
-     * @param bi block index or {@code -1} for none
-     * @return rop label or {code -1} if {@code bi} was {@code -1}
-     */
-    public int blockIndexToRopLabel(int bi) {
-        if (bi < 0) {
-            return -1;
+        // Remove secondary successors from this block
+        BitSet succs = block.getSuccessors();
+        for (int i = succs.nextSetBit(0); i >= 0; i = succs.nextSetBit(i + 1)) {
+          if (i != block.getPrimarySuccessorIndex()) {
+            block.removeSuccessor(i);
+          }
         }
-        return blocks.get(bi).getRopLabel();
+      }
     }
+  }
 
-    /**
-     * @return count of registers used in this method
-     */
-    public int getRegCount() {
-        return registerCount;
-    }
-
-    /**
-     * @return the total width, in register units, of the method's
-     * parameters
-     */
-    public int getParamWidth() {
-        return paramWidth;
-    }
-
-    /**
-     * Returns {@code true} if this is a static method.
-     *
-     * @return {@code true} if this is a static method
-     */
-    public boolean isStatic() {
-        return isStatic;
-    }
-
-    /**
-     * Borrows a register to use as a temp. Used in the phi removal process.
-     * Call returnSpareRegisters() when done.
-     *
-     * @param category width (1 or 2) of the register
-     * @return register number to use
-     */
-    public int borrowSpareRegister(int category) {
-        int result = spareRegisterBase + borrowedSpareRegisters;
-
-        borrowedSpareRegisters += category;
-        registerCount = Math.max(registerCount, result + category);
-
-        return result;
-    }
-
-    /**
-     * Returns all borrowed registers.
-     */
-    public void returnSpareRegisters() {
-        borrowedSpareRegisters = 0;
-    }
-
-    /**
-     * @return {@code non-null;} basic block list. Do not modify.
-     */
-    public ArrayList<SsaBasicBlock> getBlocks() {
-        return blocks;
-    }
-
-    /**
-     * Returns the count of reachable blocks in this method: blocks that have
-     * predecessors (or are the start block)
-     *
-     * @return {@code >= 0;} number of reachable basic blocks
-     */
-    public int getCountReachableBlocks() {
-        int ret = 0;
-
-        for (SsaBasicBlock b : blocks) {
-            // Blocks that have been disconnected don't count.
-            if (b.isReachable()) {
-                ret++;
-            }
-        }
-
-        return ret;
-    }
-
-    /**
-     * Computes reachability for all blocks in the method. First clears old
-     * values from all blocks, then starts with the entry block and walks down
-     * the control flow graph, marking all blocks it finds as reachable.
-     */
-    public void computeReachability() {
-        for (SsaBasicBlock block : blocks) {
-            block.setReachable(0);
-        }
-
-        ArrayList<SsaBasicBlock> blockList = new ArrayList<SsaBasicBlock>();
-        blockList.add(this.getEntryBlock());
-
-        while (!blockList.isEmpty()) {
-            SsaBasicBlock block = blockList.remove(0);
-            if (block.isReachable()) continue;
-
-            block.setReachable(1);
-            BitSet succs = block.getSuccessors();
-            for (int i = succs.nextSetBit(0); i >= 0;
-                     i = succs.nextSetBit(i + 1)) {
-                blockList.add(blocks.get(i));
-            }
-        }
-    }
-
-    /**
-     * Remaps unversioned registers.
-     *
-     * @param mapper maps old registers to new.
-     */
-    public void mapRegisters(RegisterMapper mapper) {
-        for (SsaBasicBlock block : getBlocks()) {
-            for (SsaInsn insn : block.getInsns()) {
-                insn.mapRegisters(mapper);
-            }
-        }
-
-        registerCount = mapper.getNewRegisterCount();
-        spareRegisterBase = registerCount;
-    }
-
-    /**
-     * Returns the insn that defines the given register
-     * @param reg register in question
-     * @return insn (actual instance from code) that defined this reg or null
-     * if reg is not defined.
-     */
-    public SsaInsn getDefinitionForRegister(int reg) {
-        if (backMode) {
-            throw new RuntimeException("No def list in back mode");
-        }
-
-        if (definitionList != null) {
-            return definitionList[reg];
-        }
-
-        definitionList = new SsaInsn[getRegCount()];
-
-        forEachInsn(new SsaInsn.Visitor() {
-            public void visitMoveInsn (NormalSsaInsn insn) {
-                definitionList[insn.getResult().getReg()] = insn;
-            }
-            public void visitPhiInsn (PhiInsn phi) {
-                definitionList[phi.getResult().getReg()] = phi;
-            }
-            public void visitNonMoveInsn (NormalSsaInsn insn) {
-                RegisterSpec result = insn.getResult();
-                if (result != null) {
-                    definitionList[insn.getResult().getReg()] = insn;
-                }
-            }
-        });
-
-        return definitionList[reg];
-    }
-
-    /**
-     * Builds useList and unmodifiableUseList.
-     */
-    private void buildUseList() {
-        if (backMode) {
-            throw new RuntimeException("No use list in back mode");
-        }
-
-        useList = new ArrayList[registerCount];
-
-        for (int i = 0; i < registerCount; i++) {
-            useList[i] = new ArrayList();
-        }
-
-        forEachInsn(new SsaInsn.Visitor() {
-            /** {@inheritDoc} */
-            public void visitMoveInsn (NormalSsaInsn insn) {
-                addToUses(insn);
-            }
-            /** {@inheritDoc} */
-            public void visitPhiInsn (PhiInsn phi) {
-                addToUses(phi);
-            }
-            /** {@inheritDoc} */
-            public void visitNonMoveInsn (NormalSsaInsn insn) {
-                addToUses(insn);
-            }
-            /**
-             * Adds specified insn to the uses list for all of its sources.
-             * @param insn {@code non-null;} insn to process
-             */
-            private void addToUses(SsaInsn insn) {
-                RegisterSpecList rl = insn.getSources();
-                int sz = rl.size();
-
-                for (int i = 0; i < sz; i++) {
-                    useList[rl.get(i).getReg()].add(insn);
-                }
-            }
-        });
-
-        unmodifiableUseList = new List[registerCount];
-
-        for (int i = 0; i < registerCount; i++) {
-            unmodifiableUseList[i] = Collections.unmodifiableList(useList[i]);
-        }
-    }
-
-    /**
-     * Updates the use list for a single change in source register.
-     *
-     * @param insn {@code non-null;} insn being changed
-     * @param oldSource {@code null-ok;} The source that was used, if
-     * applicable
-     * @param newSource {@code non-null;} the new source being used
-     */
-    /*package*/ void onSourceChanged(SsaInsn insn,
-            RegisterSpec oldSource, RegisterSpec newSource) {
-        if (useList == null) return;
-
-        if (oldSource != null) {
-            int reg = oldSource.getReg();
-            useList[reg].remove(insn);
-        }
-
-        int reg = newSource.getReg();
-        if (useList.length <= reg) {
-            useList = null;
-            return;
-        }
-        useList[reg].add(insn);
-    }
-
-    /**
-     * Updates the use list for a source list change.
-     *
-     * @param insn {@code insn non-null;} insn being changed.
-     * {@code insn.getSources()} must return the new source list.
-     * @param oldSources {@code null-ok;} list of sources that were
-     * previously used
-     */
-    /*package*/ void onSourcesChanged(SsaInsn insn,
-            RegisterSpecList oldSources) {
-        if (useList == null) return;
-
-        if (oldSources != null) {
-            removeFromUseList(insn, oldSources);
-        }
-
-        RegisterSpecList sources = insn.getSources();
-        int szNew = sources.size();
-
-        for (int i = 0; i < szNew; i++) {
-            int reg = sources.get(i).getReg();
-            useList[reg].add(insn);
-        }
-    }
-
-    /**
-     * Removes a given {@code insn} from the use lists for the given
-     * {@code oldSources} (rather than the sources currently
-     * returned by insn.getSources()).
-     *
-     * @param insn {@code non-null;} insn in question
-     * @param oldSources {@code null-ok;} registers whose use lists
-     * {@code insn} should be removed form
-     */
-    private void removeFromUseList(SsaInsn insn, RegisterSpecList oldSources) {
-        if (oldSources == null) {
-            return;
-        }
-
-        int szNew = oldSources.size();
-        for (int i = 0; i < szNew; i++) {
-            if (!useList[oldSources.get(i).getReg()].remove(insn)) {
-                throw new RuntimeException("use not found");
-            }
-        }
-    }
-
-    /**
-     * Adds an insn to both the use and def lists. For use when adding
-     * a new insn to the method.
-     *
-     * @param insn {@code non-null;} insn to add
-     */
-    /*package*/ void onInsnAdded(SsaInsn insn) {
-        onSourcesChanged(insn, null);
-        updateOneDefinition(insn, null);
-    }
-
-    /**
-     * Removes an instruction from use and def lists. For use during
-     * instruction removal.
-     *
-     * @param insn {@code non-null;} insn to remove
-     */
-    /*package*/ void onInsnRemoved(SsaInsn insn) {
-        if (useList != null) {
-            removeFromUseList(insn, insn.getSources());
-        }
-
-        RegisterSpec resultReg = insn.getResult();
-        if (definitionList != null && resultReg != null) {
-            definitionList[resultReg.getReg()] = null;
-        }
-    }
-
-    /**
-     * Indicates that the instruction list has changed or the SSA register
-     * count has increased, so that internal datastructures that rely on
-     * it should be rebuild. In general, the various other on* methods
-     * should be called in preference when changes occur if they are
-     * applicable.
-     */
-    public void onInsnsChanged() {
-        // Definition list will need to be recomputed
-        definitionList = null;
-
-        // Use list will need to be recomputed
-        useList = null;
-        unmodifiableUseList = null;
-    }
-
-    /**
-     * Updates a single definition.
-     *
-     * @param insn {@code non-null;} insn who's result should be recorded as
-     * a definition
-     * @param oldResult {@code null-ok;} a previous result that should
-     * be no longer considered a definition by this insn
-     */
-    /*package*/ void updateOneDefinition(SsaInsn insn,
-            RegisterSpec oldResult) {
-        if (definitionList == null) return;
-
-        if (oldResult != null) {
-            int reg = oldResult.getReg();
-            definitionList[reg] = null;
-        }
-
-        RegisterSpec resultReg = insn.getResult();
-
-        if (resultReg != null) {
-            int reg = resultReg.getReg();
-
-            if (definitionList[reg] != null) {
-                throw new RuntimeException("Duplicate add of insn");
-            } else {
-                definitionList[resultReg.getReg()] = insn;
-            }
-        }
-    }
-
-    /**
-     * Returns the list of all source uses (not results) for a register.
-     *
-     * @param reg register in question
-     * @return unmodifiable instruction list
-     */
-    public List<SsaInsn> getUseListForRegister(int reg) {
-
-        if (unmodifiableUseList == null) {
-            buildUseList();
-        }
-
-        return unmodifiableUseList[reg];
-    }
-
-    /**
-     * Returns a modifiable copy of the register use list.
-     *
-     * @return modifiable copy of the use-list, indexed by register
-     */
-    public ArrayList<SsaInsn>[] getUseListCopy() {
-        if (useList == null) {
-            buildUseList();
-        }
-
-        ArrayList<SsaInsn>[] useListCopy
-                = (ArrayList<SsaInsn>[])(new ArrayList[registerCount]);
-
-        for (int i = 0; i < registerCount; i++) {
-            useListCopy[i] = (ArrayList<SsaInsn>)(new ArrayList(useList[i]));
-        }
-
-        return useListCopy;
-    }
-
-    /**
-     * Checks to see if the given SSA reg is ever associated with a local
-     * local variable. Each SSA reg may be associated with at most one
-     * local var.
-     *
-     * @param spec {@code non-null;} ssa reg
-     * @return true if reg is ever associated with a local
-     */
-    public boolean isRegALocal(RegisterSpec spec) {
-        SsaInsn defn = getDefinitionForRegister(spec.getReg());
-
-        if (defn == null) {
-            // version 0 registers are never used as locals
-            return false;
-        }
-
-        // Does the definition have a local associated with it?
-        if (defn.getLocalAssignment() != null) return true;
-
-        // If not, is there a mark-local insn?
-        for (SsaInsn use : getUseListForRegister(spec.getReg())) {
-            Insn insn = use.getOriginalRopInsn();
-
-            if (insn != null
-                    && insn.getOpcode().getOpcode() == RegOps.MARK_LOCAL) {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    /**
-     * Sets the new register count after renaming.
-     *
-     * @param newRegCount new register count
-     */
-    /*package*/ void setNewRegCount(int newRegCount) {
-        registerCount = newRegCount;
-        spareRegisterBase = registerCount;
-        onInsnsChanged();
-    }
-
-    /**
-     * Makes a new SSA register. For use after renaming has completed.
-     *
-     * @return {@code >=0;} new SSA register.
-     */
-    public int makeNewSsaReg() {
-        int reg = registerCount++;
-        spareRegisterBase = registerCount;
-        onInsnsChanged();
-        return reg;
-    }
-
-    /**
-     * Visits all insns in this method.
-     *
-     * @param visitor {@code non-null;} callback interface
-     */
-    public void forEachInsn(SsaInsn.Visitor visitor) {
-        for (SsaBasicBlock block : blocks) {
-            block.forEachInsn(visitor);
-        }
-    }
-
-    /**
-     * Visits each phi insn in this method
-     * @param v {@code non-null;} callback.
-     *
-     */
-    public void forEachPhiInsn(PhiInsn.Visitor v) {
-        for (SsaBasicBlock block : blocks) {
-            block.forEachPhiInsn(v);
-        }
-    }
-
-
-    /**
-     * Walks the basic block tree in depth-first order, calling the visitor
-     * method once for every block. This depth-first walk may be run forward
-     * from the method entry point or backwards from the method exit points.
-     *
-     * @param reverse true if this should walk backwards from the exit points
-     * @param v {@code non-null;} callback interface. {@code parent} is set
-     * unless this is the root node
-     */
-    public void forEachBlockDepthFirst(boolean reverse,
-            SsaBasicBlock.Visitor v) {
-        BitSet visited = new BitSet(blocks.size());
-
-        // We push the parent first, then the child on the stack.
-        Stack<SsaBasicBlock> stack = new Stack<SsaBasicBlock>();
-
-        SsaBasicBlock rootBlock = reverse ? getExitBlock() : getEntryBlock();
-
-        if (rootBlock == null) {
-            // in the case there's no exit block
-            return;
-        }
-
-        stack.add(null);    // Start with null parent.
-        stack.add(rootBlock);
-
-        while (stack.size() > 0) {
-            SsaBasicBlock cur = stack.pop();
-            SsaBasicBlock parent = stack.pop();
-
-            if (!visited.get(cur.getIndex())) {
-                BitSet children
-                    = reverse ? cur.getPredecessors() : cur.getSuccessors();
-                for (int i = children.nextSetBit(0); i >= 0
-                        ; i = children.nextSetBit(i + 1)) {
-                    stack.add(cur);
-                    stack.add(blocks.get(i));
-                }
-                visited.set(cur.getIndex());
-                v.visitBlock(cur, parent);
-            }
-        }
-    }
-
-    /**
-     * Visits blocks in dom-tree order, starting at the current node.
-     * The {@code parent} parameter of the Visitor.visitBlock callback
-     * is currently always set to null.
-     *
-     * @param v {@code non-null;} callback interface
-     */
-    public void forEachBlockDepthFirstDom(SsaBasicBlock.Visitor v) {
-        BitSet visited = new BitSet(getBlocks().size());
-        Stack<SsaBasicBlock> stack = new Stack<SsaBasicBlock>();
-
-        stack.add(getEntryBlock());
-
-        while (stack.size() > 0) {
-            SsaBasicBlock cur = stack.pop();
-            ArrayList<SsaBasicBlock> curDomChildren = cur.getDomChildren();
-
-            if (!visited.get(cur.getIndex())) {
-                // We walk the tree this way for historical reasons...
-                for (int i = curDomChildren.size() - 1; i >= 0; i--) {
-                    SsaBasicBlock child = curDomChildren.get(i);
-                    stack.add(child);
-                }
-                visited.set(cur.getIndex());
-                v.visitBlock(cur, null);
-            }
-        }
-    }
-
-    /**
-     * Deletes all insns in the set from this method.
-     *
-     * @param deletedInsns {@code non-null;} insns to delete
-     */
-    public void deleteInsns(Set<SsaInsn> deletedInsns) {
-        for (SsaBasicBlock block : getBlocks()) {
-            ArrayList<SsaInsn> insns = block.getInsns();
-
-            for (int i = insns.size() - 1; i >= 0; i--) {
-                SsaInsn insn = insns.get(i);
-
-                if (deletedInsns.contains(insn)) {
-                    onInsnRemoved(insn);
-                    insns.remove(i);
-                }
-            }
-
-            // Check to see if we need to add a GOTO
-
-            int insnsSz = insns.size();
-            SsaInsn lastInsn = (insnsSz == 0) ? null : insns.get(insnsSz - 1);
-
-            if (block != getExitBlock() && (insnsSz == 0
-                    || lastInsn.getOriginalRopInsn() == null
-                    || lastInsn.getOriginalRopInsn().getOpcode()
-                        .getBranchingness() == Rop.BRANCH_NONE)) {
-                // We managed to eat a throwable insn
-
-                Insn gotoInsn = new PlainInsn(Rops.GOTO,
-                        SourcePosition.NO_INFO, null, RegisterSpecList.EMPTY);
-                insns.add(SsaInsn.makeFromRop(gotoInsn, block));
-
-                // Remove secondary successors from this block
-                BitSet succs = block.getSuccessors();
-                for (int i = succs.nextSetBit(0); i >= 0;
-                         i = succs.nextSetBit(i + 1)) {
-                    if (i != block.getPrimarySuccessorIndex()) {
-                        block.removeSuccessor(i);
-                    }
-                }
-            }
-        }
-    }
-
-    /**
-     * Sets "back-convert mode". Set during back-conversion when registers
-     * are about to be mapped into a non-SSA namespace. When true,
-     * use and def lists are unavailable.
-     */
-    public void setBackMode() {
-        backMode = true;
-        useList = null;
-        definitionList = null;
-    }
+  /**
+   * Sets "back-convert mode". Set during back-conversion when registers
+   * are about to be mapped into a non-SSA namespace. When true,
+   * use and def lists are unavailable.
+   */
+  public void setBackMode() {
+    backMode = true;
+    useList = null;
+    definitionList = null;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/SsaRenamer.java b/dx/src/com/android/jack/dx/ssa/SsaRenamer.java
index be9c51b..e1c5d78 100644
--- a/dx/src/com/android/jack/dx/ssa/SsaRenamer.java
+++ b/dx/src/com/android/jack/dx/ssa/SsaRenamer.java
@@ -60,603 +60,595 @@
  * and used as the initial state for child blocks.<p>
  */
 public class SsaRenamer implements Runnable {
-    /** debug flag */
-    private static final boolean DEBUG = false;
+  /** debug flag */
+  private static final boolean DEBUG = false;
 
-    /** method we're processing */
-    private final SsaMethod ssaMeth;
+  /** method we're processing */
+  private final SsaMethod ssaMeth;
 
-    /** next available SSA register */
-    private int nextSsaReg;
+  /** next available SSA register */
+  private int nextSsaReg;
 
-    /** the number of original rop registers */
-    private final int ropRegCount;
+  /** the number of original rop registers */
+  private final int ropRegCount;
 
-    /** work only on registers above this value */
-    private int threshold;
+  /** work only on registers above this value */
+  private int threshold;
 
-    /**
-     * indexed by block index; register version state for each block start.
-     * This list is updated by each dom parent for its children. The only
-     * sub-arrays that exist at any one time are the start states for blocks
-     * yet to be processed by a {@code BlockRenamer} instance.
+  /**
+   * indexed by block index; register version state for each block start.
+   * This list is updated by each dom parent for its children. The only
+   * sub-arrays that exist at any one time are the start states for blocks
+   * yet to be processed by a {@code BlockRenamer} instance.
+   */
+  private final RegisterSpec[][] startsForBlocks;
+
+  /** map of SSA register number to debug (local var names) or null of n/a */
+  private final ArrayList<LocalItem> ssaRegToLocalItems;
+
+  /**
+   * maps SSA registers back to the original rop number. Used for
+   * debug only.
+   */
+  private IntList ssaRegToRopReg;
+
+  /**
+   * Constructs an instance of the renamer
+   *
+   * @param ssaMeth {@code non-null;} un-renamed SSA method that will
+   * be renamed.
+   */
+  public SsaRenamer(SsaMethod ssaMeth) {
+    ropRegCount = ssaMeth.getRegCount();
+
+    this.ssaMeth = ssaMeth;
+
+    /*
+     * Reserve the first N registers in the SSA register space for
+     * "version 0" registers.
      */
-    private final RegisterSpec[][] startsForBlocks;
+    nextSsaReg = ropRegCount;
+    threshold = 0;
+    startsForBlocks = new RegisterSpec[ssaMeth.getBlocks().size()][];
 
-    /** map of SSA register number to debug (local var names) or null of n/a */
-    private final ArrayList<LocalItem> ssaRegToLocalItems;
+    ssaRegToLocalItems = new ArrayList<LocalItem>();
 
-    /**
-     * maps SSA registers back to the original rop number. Used for
-     * debug only.
-     */
-    private IntList ssaRegToRopReg;
+    if (DEBUG) {
+      ssaRegToRopReg = new IntList(ropRegCount);
+    }
 
-    /**
-     * Constructs an instance of the renamer
+    /*
+     * Appel 19.7
      *
-     * @param ssaMeth {@code non-null;} un-renamed SSA method that will
-     * be renamed.
+     * Initialization:
+     *   for each variable a        // register i
+     *      Count[a] <- 0           // nextSsaReg, flattened
+     *      Stack[a] <- 0           // versionStack
+     *      push 0 onto Stack[a]
+     *
      */
-    public SsaRenamer(SsaMethod ssaMeth) {
-        ropRegCount = ssaMeth.getRegCount();
 
-        this.ssaMeth = ssaMeth;
+// top entry for the version stack is version 0
+    RegisterSpec[] initialRegMapping = new RegisterSpec[ropRegCount];
+    for (int i = 0; i < ropRegCount; i++) {
+      // everyone starts with a version 0 register
+      initialRegMapping[i] = RegisterSpec.make(i, Type.VOID);
 
-        /*
-         * Reserve the first N registers in the SSA register space for
-         * "version 0" registers.
-         */
-        nextSsaReg = ropRegCount;
-        threshold = 0;
-        startsForBlocks = new RegisterSpec[ssaMeth.getBlocks().size()][];
+      if (DEBUG) {
+        ssaRegToRopReg.add(i);
+      }
+    }
 
-        ssaRegToLocalItems = new ArrayList<LocalItem>();
+    // Initial state for entry block
+    startsForBlocks[ssaMeth.getEntryBlockIndex()] = initialRegMapping;
+  }
 
+  /**
+  * Constructs an instance of the renamer with threshold set
+  *
+  * @param ssaMeth {@code non-null;} un-renamed SSA method that will
+  * be renamed.
+  * @param thresh registers below this number are unchanged
+  */
+  public SsaRenamer(SsaMethod ssaMeth, int thresh) {
+    this(ssaMeth);
+    threshold = thresh;
+  }
+
+  /**
+   * Performs renaming transformation, modifying the method's instructions
+   * in-place.
+   */
+  @Override
+  public void run() {
+    // Rename each block in dom-tree DFS order.
+    ssaMeth.forEachBlockDepthFirstDom(new SsaBasicBlock.Visitor() {
+      @Override
+      public void visitBlock(SsaBasicBlock block, SsaBasicBlock unused) {
+        new BlockRenamer(block).process();
+      }
+    });
+
+    ssaMeth.setNewRegCount(nextSsaReg);
+    ssaMeth.onInsnsChanged();
+
+    if (DEBUG) {
+      System.out.println("SSA\tRop");
+      /*
+       * We're going to compute the version of the rop register
+       * by keeping a running total of how many times the rop
+       * register has been mapped.
+       */
+      int[] versions = new int[ropRegCount];
+
+      int sz = ssaRegToRopReg.size();
+      for (int i = 0; i < sz; i++) {
+        int ropReg = ssaRegToRopReg.get(i);
+        System.out.println(i + "\t" + ropReg + "[" + versions[ropReg] + "]");
+        versions[ropReg]++;
+      }
+    }
+  }
+
+  /**
+   * Duplicates a RegisterSpec array.
+   *
+   * @param orig {@code non-null;} array to duplicate
+   * @return {@code non-null;} new instance
+   */
+  private static RegisterSpec[] dupArray(RegisterSpec[] orig) {
+    RegisterSpec[] copy = new RegisterSpec[orig.length];
+
+    System.arraycopy(orig, 0, copy, 0, orig.length);
+
+    return copy;
+  }
+
+  /**
+   * Gets a local variable item for a specified register.
+   *
+   * @param ssaReg register in SSA name space
+   * @return {@code null-ok;} Local variable name or null if none
+   */
+  private LocalItem getLocalForNewReg(int ssaReg) {
+    if (ssaReg < ssaRegToLocalItems.size()) {
+      return ssaRegToLocalItems.get(ssaReg);
+    } else {
+      return null;
+    }
+  }
+
+  /**
+   * Records a debug (local variable) name for a specified register.
+   *
+   * @param ssaReg non-null named register spec in SSA name space
+   */
+  private void setNameForSsaReg(RegisterSpec ssaReg) {
+    int reg = ssaReg.getReg();
+    LocalItem local = ssaReg.getLocalItem();
+
+    ssaRegToLocalItems.ensureCapacity(reg + 1);
+    while (ssaRegToLocalItems.size() <= reg) {
+      ssaRegToLocalItems.add(null);
+    }
+
+    ssaRegToLocalItems.set(reg, local);
+  }
+
+  /**
+   * Returns true if this SSA register is below the specified threshold.
+   * Used when most code is already in SSA form, and renaming is needed only
+   * for registers above a certain threshold.
+   *
+   * @param ssaReg the SSA register in question
+   * @return {@code true} if its register number is below the threshold
+   */
+  private boolean isBelowThresholdRegister(int ssaReg) {
+    return ssaReg < threshold;
+  }
+
+  /**
+   * Returns true if this SSA register is a "version 0"
+   * register. All version 0 registers are assigned the first N register
+   * numbers, where N is the count of original rop registers.
+   *
+   * @param ssaReg the SSA register in question
+   * @return true if it is a version 0 register.
+   */
+  private boolean isVersionZeroRegister(int ssaReg) {
+    return ssaReg < ropRegCount;
+  }
+
+  /**
+   * Returns true if a and b are equal or are both null.
+   *
+   * @param a null-ok
+   * @param b null-ok
+   * @return Returns true if a and b are equal or are both null
+   */
+  private static boolean equalsHandlesNulls(Object a, Object b) {
+    return a == b || (a != null && a.equals(b));
+  }
+
+  /**
+   * Processes all insns in a block and renames their registers
+   * as appropriate.
+   */
+  private class BlockRenamer implements SsaInsn.Visitor {
+    /** {@code non-null;} block we're processing. */
+    private final SsaBasicBlock block;
+
+    /**
+     * {@code non-null;} indexed by old register name. The current
+     * top of the version stack as seen by this block. It's
+     * initialized from the ending state of its dom parent,
+     * updated as the block's instructions are processed, and then
+     * copied to each one of its dom children.
+     */
+    private final RegisterSpec[] currentMapping;
+
+    /**
+     * contains the set of moves we need to keep to preserve local
+     * var info. All other moves will be deleted.
+     */
+    private final HashSet<SsaInsn> movesToKeep;
+
+    /**
+     * maps the set of insns to replace after renaming is finished
+     * on the block.
+     */
+    private final HashMap<SsaInsn, SsaInsn> insnsToReplace;
+
+    private final RenamingMapper mapper;
+
+    /**
+     * Constructs a block renamer instance. Call {@code process}
+     * to process.
+     *
+     * @param block {@code non-null;} block to process
+     */
+    BlockRenamer(final SsaBasicBlock block) {
+      this.block = block;
+      currentMapping = startsForBlocks[block.getIndex()];
+      movesToKeep = new HashSet<SsaInsn>();
+      insnsToReplace = new HashMap<SsaInsn, SsaInsn>();
+      mapper = new RenamingMapper();
+
+      // We don't need our own start state anymore
+      startsForBlocks[block.getIndex()] = null;
+    }
+
+    /**
+     * Provides a register mapping between the old register space
+     * and the current renaming mapping. The mapping is updated
+     * as the current block's instructions are processed.
+     */
+    private class RenamingMapper extends RegisterMapper {
+      public RenamingMapper() {
+        // This space intentionally left blank.
+      }
+
+      /** {@inheritDoc} */
+      @Override
+      public int getNewRegisterCount() {
+        return nextSsaReg;
+      }
+
+      /** {@inheritDoc} */
+      @Override
+      public RegisterSpec map(RegisterSpec registerSpec) {
+        if (registerSpec == null) {
+          return null;
+        }
+
+        int reg = registerSpec.getReg();
+
+        // For debugging: assert that the mapped types are compatible.
         if (DEBUG) {
-            ssaRegToRopReg = new IntList(ropRegCount);
+          RegisterSpec newVersion = currentMapping[reg];
+          if (newVersion.getBasicType() != Type.BT_VOID
+              && registerSpec.getBasicFrameType() != newVersion.getBasicFrameType()) {
+
+            throw new RuntimeException("mapping registers of incompatible types! " + registerSpec
+                + " " + currentMapping[reg]);
+          }
         }
 
+        return registerSpec.withReg(currentMapping[reg].getReg());
+      }
+    }
+
+    /**
+     * Renames all the variables in this block and inserts appriopriate
+     * phis in successor blocks.
+     */
+    public void process() {
+      /*
+       * From Appel:
+       *
+       * Rename(n) =
+       *   for each statement S in block n   // 'statement' in 'block'
+       */
+
+block.forEachInsn(this);
+
+      updateSuccessorPhis();
+
+      // Delete all move insns in this block.
+      ArrayList<SsaInsn> insns = block.getInsns();
+      int szInsns = insns.size();
+
+      for (int i = szInsns - 1; i >= 0; i--) {
+        SsaInsn insn = insns.get(i);
+        SsaInsn replaceInsn;
+
+        replaceInsn = insnsToReplace.get(insn);
+
+        if (replaceInsn != null) {
+          insns.set(i, replaceInsn);
+        } else if (insn.isNormalMoveInsn() && !movesToKeep.contains(insn)) {
+          insns.remove(i);
+        }
+      }
+
+      // Store the start states for our dom children.
+      boolean first = true;
+      for (SsaBasicBlock child : block.getDomChildren()) {
+        if (child != block) {
+          // Don't bother duplicating the array for the first child.
+          RegisterSpec[] childStart = first ? currentMapping : dupArray(currentMapping);
+
+          startsForBlocks[child.getIndex()] = childStart;
+          first = false;
+        }
+      }
+
+      // currentMapping is owned by a child now.
+    }
+
+    /**
+     * Enforces a few contraints when a register mapping is added.
+     *
+     * <ol>
+     * <li> Ensures that all new SSA registers specs in the mapping
+     * table with the same register number are identical. In effect, once
+     * an SSA register spec has received or lost a local variable name,
+     * then every old-namespace register that maps to it should gain or
+     * lose its local variable name as well.
+     * <li> Records the local name associated with the
+     * register so that a register is never associated with more than one
+     * local.
+     * <li> ensures that only one SSA register
+     * at a time is considered to be associated with a local variable. When
+     * {@code currentMapping} is updated and the newly added element
+     * is named, strip that name from any other SSA registers.
+     * </ol>
+     *
+     * @param ropReg {@code >= 0;} rop register number
+     * @param ssaReg {@code non-null;} an SSA register that has just
+     * been added to {@code currentMapping}
+     */
+    private void addMapping(int ropReg, RegisterSpec ssaReg) {
+      int ssaRegNum = ssaReg.getReg();
+      LocalItem ssaRegLocal = ssaReg.getLocalItem();
+
+      currentMapping[ropReg] = ssaReg;
+
+      /*
+       * Ensure all SSA register specs with the same reg are identical.
+       */
+      for (int i = currentMapping.length - 1; i >= 0; i--) {
+        RegisterSpec cur = currentMapping[i];
+
+        if (ssaRegNum == cur.getReg()) {
+          currentMapping[i] = ssaReg;
+        }
+      }
+
+      // All further steps are for registers with local information.
+      if (ssaRegLocal == null) {
+        return;
+      }
+
+      // Record that this SSA reg has been associated with a local.
+      setNameForSsaReg(ssaReg);
+
+      // Ensure that no other SSA regs are associated with this local.
+      for (int i = currentMapping.length - 1; i >= 0; i--) {
+        RegisterSpec cur = currentMapping[i];
+
+        if (ssaRegNum != cur.getReg() && ssaRegLocal.equals(cur.getLocalItem())) {
+          currentMapping[i] = cur.withLocalItem(null);
+        }
+      }
+    }
+
+    /**
+     * {@inheritDoc}
+     *
+     * Phi insns have their result registers renamed.
+     */
+    @Override
+    public void visitPhiInsn(PhiInsn phi) {
+      /* don't process sources for phi's */
+      processResultReg(phi);
+    }
+
+    /**
+     * {@inheritDoc}
+     *
+     * Move insns are treated as a simple mapping operation, and
+     * will later be removed unless they represent a local variable
+     * assignment. If they represent a local variable assignement, they
+     * are preserved.
+     */
+    @Override
+    public void visitMoveInsn(NormalSsaInsn insn) {
+      /*
+       * For moves: copy propogate the move if we can, but don't
+       * if we need to preserve local variable info and the
+       * result has a different name than the source.
+       */
+
+RegisterSpec ropResult = insn.getResult();
+      int ropResultReg = ropResult.getReg();
+      int ropSourceReg = insn.getSources().get(0).getReg();
+
+      insn.mapSourceRegisters(mapper);
+      int ssaSourceReg = insn.getSources().get(0).getReg();
+
+      LocalItem sourceLocal = currentMapping[ropSourceReg].getLocalItem();
+      LocalItem resultLocal = ropResult.getLocalItem();
+
+      /*
+       * A move from a register that's currently associated with a local
+       * to one that will not be associated with a local does not need
+       * to be preserved, but the local association should remain.
+       * Hence, we inherit the sourceLocal where the resultLocal is null.
+       */
+
+LocalItem newLocal = (resultLocal == null) ? sourceLocal : resultLocal;
+      LocalItem associatedLocal = getLocalForNewReg(ssaSourceReg);
+
+      /*
+       * If we take the new local, will only one local have ever
+       * been associated with this SSA reg?
+       */
+      boolean onlyOneAssociatedLocal =
+          associatedLocal == null || newLocal == null || newLocal.equals(associatedLocal);
+
+      /*
+       * If we're going to copy-propogate, then the ssa register
+       * spec that's going to go into the mapping is made up of
+       * the source register number mapped from above, the type
+       * of the result, and the name either from the result (if
+       * specified) or inherited from the existing mapping.
+       *
+       * The move source has incomplete type information in null
+       * object cases, so the result type is used.
+       */
+      RegisterSpec ssaReg =
+          RegisterSpec.makeLocalOptional(ssaSourceReg, ropResult.getType(), newLocal);
+
+      if (!Optimizer.getPreserveLocals()
+          || (onlyOneAssociatedLocal && equalsHandlesNulls(newLocal, sourceLocal))
+          && threshold == 0) {
         /*
-         * Appel 19.7
-         *
-         * Initialization:
-         *   for each variable a        // register i
-         *      Count[a] <- 0           // nextSsaReg, flattened
-         *      Stack[a] <- 0           // versionStack
-         *      push 0 onto Stack[a]
-         *
+         * We don't have to keep this move to preserve local
+         * information. Either the name is the same, or the result
+         * register spec is unnamed.
          */
 
-        // top entry for the version stack is version 0
-        RegisterSpec[] initialRegMapping = new RegisterSpec[ropRegCount];
-        for (int i = 0; i < ropRegCount; i++) {
-            // everyone starts with a version 0 register
-            initialRegMapping[i] = RegisterSpec.make(i, Type.VOID);
+addMapping(ropResultReg, ssaReg);
+      } else if (onlyOneAssociatedLocal && sourceLocal == null && threshold == 0) {
+        /*
+         * The register was previously unnamed. This means that a
+         * local starts after it's first assignment in SSA form
+         */
 
-            if (DEBUG) {
-                ssaRegToRopReg.add(i);
-            }
-        }
+RegisterSpecList ssaSources =
+            RegisterSpecList.make(RegisterSpec.make(ssaReg.getReg(), ssaReg.getType(), newLocal));
 
-        // Initial state for entry block
-        startsForBlocks[ssaMeth.getEntryBlockIndex()] = initialRegMapping;
+        SsaInsn newInsn = SsaInsn.makeFromRop(
+            new PlainInsn(Rops.opMarkLocal(ssaReg), SourcePosition.NO_INFO, null, ssaSources),
+            block);
+
+        insnsToReplace.put(insn, newInsn);
+
+        // Just map as above.
+        addMapping(ropResultReg, ssaReg);
+      } else {
+        /*
+         * Do not copy-propogate, since the two registers have
+         * two different local-variable names.
+         */
+        processResultReg(insn);
+
+        movesToKeep.add(insn);
+      }
     }
 
     /**
-    * Constructs an instance of the renamer with threshold set
-    *
-    * @param ssaMeth {@code non-null;} un-renamed SSA method that will
-    * be renamed.
-    * @param thresh registers below this number are unchanged
-    */
-   public SsaRenamer(SsaMethod ssaMeth, int thresh) {
-       this(ssaMeth);
-       threshold = thresh;
-   }
-
-    /**
-     * Performs renaming transformation, modifying the method's instructions
-     * in-place.
-     */
-    public void run() {
-        // Rename each block in dom-tree DFS order.
-        ssaMeth.forEachBlockDepthFirstDom(new SsaBasicBlock.Visitor() {
-            public void visitBlock (SsaBasicBlock block,
-                    SsaBasicBlock unused) {
-                new BlockRenamer(block).process();
-            }
-        });
-
-        ssaMeth.setNewRegCount(nextSsaReg);
-        ssaMeth.onInsnsChanged();
-
-        if (DEBUG) {
-            System.out.println("SSA\tRop");
-            /*
-             * We're going to compute the version of the rop register
-             * by keeping a running total of how many times the rop
-             * register has been mapped.
-             */
-            int[] versions = new int[ropRegCount];
-
-            int sz = ssaRegToRopReg.size();
-            for (int i = 0; i < sz; i++) {
-                int ropReg = ssaRegToRopReg.get(i);
-                System.out.println(i + "\t" + ropReg + "["
-                        + versions[ropReg] + "]");
-                versions[ropReg]++;
-            }
-        }
-    }
-
-    /**
-     * Duplicates a RegisterSpec array.
+     * {@inheritDoc}
      *
-     * @param orig {@code non-null;} array to duplicate
-     * @return {@code non-null;} new instance
+     * All insns that are not move or phi insns have their source registers
+     * mapped ot the current mapping. Their result registers are then
+     * renamed to a new SSA register which is then added to the current
+     * register mapping.
      */
-    private static  RegisterSpec[] dupArray(RegisterSpec[] orig) {
-        RegisterSpec[] copy = new RegisterSpec[orig.length];
+    @Override
+    public void visitNonMoveInsn(NormalSsaInsn insn) {
+      /* for each use of some variable X in S */
+      insn.mapSourceRegisters(mapper);
 
-        System.arraycopy(orig, 0, copy, 0, orig.length);
-
-        return copy;
+      processResultReg(insn);
     }
 
     /**
-     * Gets a local variable item for a specified register.
+     * Renames the result register of this insn and updates the
+     * current register mapping. Does nothing if this insn has no result.
+     * Applied to all non-move insns.
      *
-     * @param ssaReg register in SSA name space
-     * @return {@code null-ok;} Local variable name or null if none
+     * @param insn insn to process.
      */
-    private LocalItem getLocalForNewReg(int ssaReg) {
-        if (ssaReg < ssaRegToLocalItems.size()) {
-            return ssaRegToLocalItems.get(ssaReg);
-        } else {
-            return null;
-        }
+    void processResultReg(SsaInsn insn) {
+      RegisterSpec ropResult = insn.getResult();
+
+      if (ropResult == null) {
+        return;
+      }
+
+      int ropReg = ropResult.getReg();
+      if (isBelowThresholdRegister(ropReg)) {
+        return;
+      }
+
+      insn.changeResultReg(nextSsaReg);
+      addMapping(ropReg, insn.getResult());
+
+      if (DEBUG) {
+        ssaRegToRopReg.add(ropReg);
+      }
+
+      nextSsaReg++;
     }
 
     /**
-     * Records a debug (local variable) name for a specified register.
-     *
-     * @param ssaReg non-null named register spec in SSA name space
+     * Updates the phi insns in successor blocks with operands based
+     * on the current mapping of the rop register the phis represent.
      */
-    private void setNameForSsaReg(RegisterSpec ssaReg) {
-        int reg = ssaReg.getReg();
-        LocalItem local = ssaReg.getLocalItem();
+    private void updateSuccessorPhis() {
+      PhiInsn.Visitor visitor = new PhiInsn.Visitor() {
+        @Override
+        public void visitPhiInsn(PhiInsn insn) {
+          int ropReg;
 
-        ssaRegToLocalItems.ensureCapacity(reg + 1);
-        while (ssaRegToLocalItems.size() <= reg) {
-            ssaRegToLocalItems.add(null);
+          ropReg = insn.getRopResultReg();
+          if (isBelowThresholdRegister(ropReg)) {
+            return;
+          }
+
+          /*
+           * Never add a version 0 register as a phi
+           * operand. Version 0 registers represent the
+           * initial register state, and thus are never
+           * significant. Furthermore, the register liveness
+           * algorithm doesn't properly count them as "live
+           * in" at the beginning of the method.
+           */
+
+RegisterSpec stackTop = currentMapping[ropReg];
+          if (!isVersionZeroRegister(stackTop.getReg())) {
+            insn.addPhiOperand(stackTop, block);
+          }
         }
+      };
 
-        ssaRegToLocalItems.set(reg, local);
+      BitSet successors = block.getSuccessors();
+      for (int i = successors.nextSetBit(0); i >= 0; i = successors.nextSetBit(i + 1)) {
+        SsaBasicBlock successor = ssaMeth.getBlocks().get(i);
+        successor.forEachPhiInsn(visitor);
+      }
     }
-
-    /**
-     * Returns true if this SSA register is below the specified threshold.
-     * Used when most code is already in SSA form, and renaming is needed only
-     * for registers above a certain threshold.
-     *
-     * @param ssaReg the SSA register in question
-     * @return {@code true} if its register number is below the threshold
-     */
-    private boolean isBelowThresholdRegister(int ssaReg) {
-        return ssaReg < threshold;
-    }
-
-    /**
-     * Returns true if this SSA register is a "version 0"
-     * register. All version 0 registers are assigned the first N register
-     * numbers, where N is the count of original rop registers.
-     *
-     * @param ssaReg the SSA register in question
-     * @return true if it is a version 0 register.
-     */
-    private boolean isVersionZeroRegister(int ssaReg) {
-        return ssaReg < ropRegCount;
-    }
-
-    /**
-     * Returns true if a and b are equal or are both null.
-     *
-     * @param a null-ok
-     * @param b null-ok
-     * @return Returns true if a and b are equal or are both null
-     */
-    private static boolean equalsHandlesNulls(Object a, Object b) {
-        return a == b ||  (a != null && a.equals(b));
-    }
-
-    /**
-     * Processes all insns in a block and renames their registers
-     * as appropriate.
-     */
-    private class BlockRenamer implements SsaInsn.Visitor{
-        /** {@code non-null;} block we're processing. */
-        private final SsaBasicBlock block;
-
-        /**
-         * {@code non-null;} indexed by old register name. The current
-         * top of the version stack as seen by this block. It's
-         * initialized from the ending state of its dom parent,
-         * updated as the block's instructions are processed, and then
-         * copied to each one of its dom children.
-         */
-        private final RegisterSpec[] currentMapping;
-
-        /**
-         * contains the set of moves we need to keep to preserve local
-         * var info. All other moves will be deleted.
-         */
-        private final HashSet<SsaInsn> movesToKeep;
-
-        /**
-         * maps the set of insns to replace after renaming is finished
-         * on the block.
-         */
-        private final HashMap<SsaInsn, SsaInsn> insnsToReplace;
-
-        private final RenamingMapper mapper;
-
-        /**
-         * Constructs a block renamer instance. Call {@code process}
-         * to process.
-         *
-         * @param block {@code non-null;} block to process
-         */
-        BlockRenamer(final SsaBasicBlock block) {
-            this.block = block;
-            currentMapping = startsForBlocks[block.getIndex()];
-            movesToKeep = new HashSet<SsaInsn>();
-            insnsToReplace = new HashMap<SsaInsn, SsaInsn>();
-            mapper =  new RenamingMapper();
-
-            // We don't need our own start state anymore
-            startsForBlocks[block.getIndex()] = null;
-        }
-
-        /**
-         * Provides a register mapping between the old register space
-         * and the current renaming mapping. The mapping is updated
-         * as the current block's instructions are processed.
-         */
-        private class RenamingMapper extends RegisterMapper {
-            public RenamingMapper() {
-                // This space intentionally left blank.
-            }
-
-            /** {@inheritDoc} */
-            @Override
-            public int getNewRegisterCount() {
-                return nextSsaReg;
-            }
-
-            /** {@inheritDoc} */
-            @Override
-            public RegisterSpec map(RegisterSpec registerSpec) {
-                if (registerSpec == null) return null;
-
-                int reg = registerSpec.getReg();
-
-                // For debugging: assert that the mapped types are compatible.
-                if (DEBUG) {
-                    RegisterSpec newVersion = currentMapping[reg];
-                    if (newVersion.getBasicType() != Type.BT_VOID
-                            && registerSpec.getBasicFrameType()
-                                != newVersion.getBasicFrameType()) {
-
-                        throw new RuntimeException(
-                                "mapping registers of incompatible types! "
-                                + registerSpec
-                                + " " + currentMapping[reg]);
-                    }
-                }
-
-                return registerSpec.withReg(currentMapping[reg].getReg());
-            }
-        }
-
-        /**
-         * Renames all the variables in this block and inserts appriopriate
-         * phis in successor blocks.
-         */
-        public void process() {
-            /*
-             * From Appel:
-             *
-             * Rename(n) =
-             *   for each statement S in block n   // 'statement' in 'block'
-             */
-
-            block.forEachInsn(this);
-
-            updateSuccessorPhis();
-
-            // Delete all move insns in this block.
-            ArrayList<SsaInsn> insns = block.getInsns();
-            int szInsns = insns.size();
-
-            for (int i = szInsns - 1; i >= 0 ; i--) {
-                SsaInsn insn = insns.get(i);
-                SsaInsn replaceInsn;
-
-                replaceInsn = insnsToReplace.get(insn);
-
-                if (replaceInsn != null) {
-                    insns.set(i, replaceInsn);
-                } else if (insn.isNormalMoveInsn()
-                        && !movesToKeep.contains(insn)) {
-                    insns.remove(i);
-                }
-            }
-
-            // Store the start states for our dom children.
-            boolean first = true;
-            for (SsaBasicBlock child : block.getDomChildren()) {
-                if (child != block) {
-                    // Don't bother duplicating the array for the first child.
-                    RegisterSpec[] childStart = first ? currentMapping
-                        : dupArray(currentMapping);
-
-                    startsForBlocks[child.getIndex()] = childStart;
-                    first = false;
-                }
-            }
-
-            // currentMapping is owned by a child now.
-        }
-
-        /**
-         * Enforces a few contraints when a register mapping is added.
-         *
-         * <ol>
-         * <li> Ensures that all new SSA registers specs in the mapping
-         * table with the same register number are identical. In effect, once
-         * an SSA register spec has received or lost a local variable name,
-         * then every old-namespace register that maps to it should gain or
-         * lose its local variable name as well.
-         * <li> Records the local name associated with the
-         * register so that a register is never associated with more than one
-         * local.
-         * <li> ensures that only one SSA register
-         * at a time is considered to be associated with a local variable. When
-         * {@code currentMapping} is updated and the newly added element
-         * is named, strip that name from any other SSA registers.
-         * </ol>
-         *
-         * @param ropReg {@code >= 0;} rop register number
-         * @param ssaReg {@code non-null;} an SSA register that has just
-         * been added to {@code currentMapping}
-         */
-        private void addMapping(int ropReg, RegisterSpec ssaReg) {
-            int ssaRegNum = ssaReg.getReg();
-            LocalItem ssaRegLocal = ssaReg.getLocalItem();
-
-            currentMapping[ropReg] = ssaReg;
-
-            /*
-             * Ensure all SSA register specs with the same reg are identical.
-             */
-            for (int i = currentMapping.length - 1; i >= 0; i--) {
-                RegisterSpec cur = currentMapping[i];
-
-                if (ssaRegNum == cur.getReg()) {
-                    currentMapping[i] = ssaReg;
-                }
-            }
-
-            // All further steps are for registers with local information.
-            if (ssaRegLocal == null) {
-                return;
-            }
-
-            // Record that this SSA reg has been associated with a local.
-            setNameForSsaReg(ssaReg);
-
-            // Ensure that no other SSA regs are associated with this local.
-            for (int i = currentMapping.length - 1; i >= 0; i--) {
-                RegisterSpec cur = currentMapping[i];
-
-                if (ssaRegNum != cur.getReg()
-                        && ssaRegLocal.equals(cur.getLocalItem())) {
-                    currentMapping[i] = cur.withLocalItem(null);
-                }
-            }
-        }
-
-        /**
-         * {@inheritDoc}
-         *
-         * Phi insns have their result registers renamed.
-         */
-        public void visitPhiInsn(PhiInsn phi) {
-            /* don't process sources for phi's */
-            processResultReg(phi);
-        }
-
-        /**
-         * {@inheritDoc}
-         *
-         * Move insns are treated as a simple mapping operation, and
-         * will later be removed unless they represent a local variable
-         * assignment. If they represent a local variable assignement, they
-         * are preserved.
-         */
-        public void visitMoveInsn(NormalSsaInsn insn) {
-            /*
-             * For moves: copy propogate the move if we can, but don't
-             * if we need to preserve local variable info and the
-             * result has a different name than the source.
-             */
-
-            RegisterSpec ropResult = insn.getResult();
-            int ropResultReg = ropResult.getReg();
-            int ropSourceReg = insn.getSources().get(0).getReg();
-
-            insn.mapSourceRegisters(mapper);
-            int ssaSourceReg = insn.getSources().get(0).getReg();
-
-            LocalItem sourceLocal
-                = currentMapping[ropSourceReg].getLocalItem();
-            LocalItem resultLocal = ropResult.getLocalItem();
-
-            /*
-             * A move from a register that's currently associated with a local
-             * to one that will not be associated with a local does not need
-             * to be preserved, but the local association should remain.
-             * Hence, we inherit the sourceLocal where the resultLocal is null.
-             */
-
-            LocalItem newLocal
-                = (resultLocal == null) ? sourceLocal : resultLocal;
-            LocalItem associatedLocal = getLocalForNewReg(ssaSourceReg);
-
-            /*
-             * If we take the new local, will only one local have ever
-             * been associated with this SSA reg?
-             */
-            boolean onlyOneAssociatedLocal
-                    = associatedLocal == null || newLocal == null
-                    || newLocal.equals(associatedLocal);
-
-            /*
-             * If we're going to copy-propogate, then the ssa register
-             * spec that's going to go into the mapping is made up of
-             * the source register number mapped from above, the type
-             * of the result, and the name either from the result (if
-             * specified) or inherited from the existing mapping.
-             *
-             * The move source has incomplete type information in null
-             * object cases, so the result type is used.
-             */
-            RegisterSpec ssaReg
-                    = RegisterSpec.makeLocalOptional(
-                        ssaSourceReg, ropResult.getType(), newLocal);
-
-            if (!Optimizer.getPreserveLocals() || (onlyOneAssociatedLocal
-                    && equalsHandlesNulls(newLocal, sourceLocal)) &&
-                    threshold == 0) {
-                /*
-                 * We don't have to keep this move to preserve local
-                 * information. Either the name is the same, or the result
-                 * register spec is unnamed.
-                 */
-
-                addMapping(ropResultReg, ssaReg);
-            } else if (onlyOneAssociatedLocal && sourceLocal == null &&
-                    threshold == 0) {
-                /*
-                 * The register was previously unnamed. This means that a
-                 * local starts after it's first assignment in SSA form
-                 */
-
-                RegisterSpecList ssaSources = RegisterSpecList.make(
-                        RegisterSpec.make(ssaReg.getReg(),
-                                ssaReg.getType(), newLocal));
-
-                SsaInsn newInsn
-                        = SsaInsn.makeFromRop(
-                            new PlainInsn(Rops.opMarkLocal(ssaReg),
-                            SourcePosition.NO_INFO, null, ssaSources),block);
-
-                insnsToReplace.put(insn, newInsn);
-
-                // Just map as above.
-                addMapping(ropResultReg, ssaReg);
-            } else {
-                /*
-                 * Do not copy-propogate, since the two registers have
-                 * two different local-variable names.
-                 */
-                processResultReg(insn);
-
-                movesToKeep.add(insn);
-            }
-        }
-
-        /**
-         * {@inheritDoc}
-         *
-         * All insns that are not move or phi insns have their source registers
-         * mapped ot the current mapping. Their result registers are then
-         * renamed to a new SSA register which is then added to the current
-         * register mapping.
-         */
-        public void visitNonMoveInsn(NormalSsaInsn insn) {
-            /* for each use of some variable X in S */
-            insn.mapSourceRegisters(mapper);
-
-            processResultReg(insn);
-        }
-
-        /**
-         * Renames the result register of this insn and updates the
-         * current register mapping. Does nothing if this insn has no result.
-         * Applied to all non-move insns.
-         *
-         * @param insn insn to process.
-         */
-        void processResultReg(SsaInsn insn) {
-            RegisterSpec ropResult = insn.getResult();
-
-            if (ropResult == null) {
-                return;
-            }
-
-            int ropReg = ropResult.getReg();
-            if (isBelowThresholdRegister(ropReg)) {
-                return;
-            }
-
-            insn.changeResultReg(nextSsaReg);
-            addMapping(ropReg, insn.getResult());
-
-            if (DEBUG) {
-                ssaRegToRopReg.add(ropReg);
-            }
-
-            nextSsaReg++;
-        }
-
-        /**
-         * Updates the phi insns in successor blocks with operands based
-         * on the current mapping of the rop register the phis represent.
-         */
-        private void updateSuccessorPhis() {
-            PhiInsn.Visitor visitor = new PhiInsn.Visitor() {
-                public void visitPhiInsn (PhiInsn insn) {
-                    int ropReg;
-
-                    ropReg = insn.getRopResultReg();
-                    if (isBelowThresholdRegister(ropReg)) {
-                        return;
-                    }
-
-                    /*
-                     * Never add a version 0 register as a phi
-                     * operand. Version 0 registers represent the
-                     * initial register state, and thus are never
-                     * significant. Furthermore, the register liveness
-                     * algorithm doesn't properly count them as "live
-                     * in" at the beginning of the method.
-                     */
-
-                    RegisterSpec stackTop = currentMapping[ropReg];
-                    if (!isVersionZeroRegister(stackTop.getReg())) {
-                        insn.addPhiOperand(stackTop, block);
-                    }
-                }
-            };
-
-            BitSet successors = block.getSuccessors();
-            for (int i = successors.nextSetBit(0); i >= 0;
-                    i = successors.nextSetBit(i + 1)) {
-                SsaBasicBlock successor = ssaMeth.getBlocks().get(i);
-                successor.forEachPhiInsn(visitor);
-            }
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/FirstFitAllocator.java b/dx/src/com/android/jack/dx/ssa/back/FirstFitAllocator.java
index 4fed8f2..3795077 100644
--- a/dx/src/com/android/jack/dx/ssa/back/FirstFitAllocator.java
+++ b/dx/src/com/android/jack/dx/ssa/back/FirstFitAllocator.java
@@ -26,7 +26,6 @@
 import com.android.jack.dx.util.IntSet;
 
 import java.util.BitSet;
-import java.util.ArrayList;
 
 /**
  * Allocates registers via a naive n^2 register allocator.
@@ -34,118 +33,112 @@
  * intelligently with different size register uses.
  */
 public class FirstFitAllocator extends RegisterAllocator {
-    /**
-     * If true, allocator places parameters at the top of the frame
-     * in calling-convention order.
-     */
-    private static final boolean PRESLOT_PARAMS = true;
+  /**
+   * If true, allocator places parameters at the top of the frame
+   * in calling-convention order.
+   */
+  private static final boolean PRESLOT_PARAMS = true;
 
-    /** indexed by old reg; the set of old regs we've mapped */
-    private final BitSet mapped;
+  /** indexed by old reg; the set of old regs we've mapped */
+  private final BitSet mapped;
 
-    /** {@inheritDoc} */
-    public FirstFitAllocator(
-            final SsaMethod ssaMeth, final InterferenceGraph interference) {
-        super(ssaMeth, interference);
+  /** {@inheritDoc} */
+  public FirstFitAllocator(final SsaMethod ssaMeth, final InterferenceGraph interference) {
+    super(ssaMeth, interference);
 
-        mapped = new BitSet(ssaMeth.getRegCount());
+    mapped = new BitSet(ssaMeth.getRegCount());
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean wantsParamsMovedHigh() {
+    return PRESLOT_PARAMS;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public RegisterMapper allocateRegisters() {
+    int oldRegCount = ssaMeth.getRegCount();
+
+    BasicRegisterMapper mapper = new BasicRegisterMapper(oldRegCount);
+
+    int nextNewRegister = 0;
+
+    if (PRESLOT_PARAMS) {
+      /*
+       * Reserve space for the params at the bottom of the register
+       * space. Later, we'll flip the params to the end of the register
+       * space.
+       */
+
+nextNewRegister = ssaMeth.getParamWidth();
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean wantsParamsMovedHigh() {
-        return PRESLOT_PARAMS;
-    }
+    for (int i = 0; i < oldRegCount; i++) {
+      if (mapped.get(i)) {
+        // we already got this one
+        continue;
+      }
 
-    /** {@inheritDoc} */
-    @Override
-    public RegisterMapper allocateRegisters() {
-        int oldRegCount = ssaMeth.getRegCount();
+      int maxCategory = getCategoryForSsaReg(i);
+      IntSet current = new BitIntSet(oldRegCount);
 
-        BasicRegisterMapper mapper
-                = new BasicRegisterMapper(oldRegCount);
+      interference.mergeInterferenceSet(i, current);
 
-        int nextNewRegister = 0;
+      boolean isPreslotted = false;
+      int newReg = 0;
 
-        if (PRESLOT_PARAMS) {
-            /*
-             * Reserve space for the params at the bottom of the register
-             * space. Later, we'll flip the params to the end of the register
-             * space.
-             */
+      if (PRESLOT_PARAMS && isDefinitionMoveParam(i)) {
+        // Any move-param definition must be a NormalSsaInsn
+        NormalSsaInsn defInsn = (NormalSsaInsn) ssaMeth.getDefinitionForRegister(i);
 
-            nextNewRegister = ssaMeth.getParamWidth();
+        newReg = paramNumberFromMoveParam(defInsn);
+
+        mapper.addMapping(i, newReg, maxCategory);
+        isPreslotted = true;
+      } else {
+        mapper.addMapping(i, nextNewRegister, maxCategory);
+        newReg = nextNewRegister;
+      }
+
+      for (int j = i + 1; j < oldRegCount; j++) {
+        if (mapped.get(j) || isDefinitionMoveParam(j)) {
+          continue;
         }
 
-        for (int i = 0; i < oldRegCount; i++) {
-            if (mapped.get(i)) {
-                // we already got this one
-                continue;
-            }
+        /*
+         * If reg j doesn't interfere with the current mapping.
+         * Also, if this is a pre-slotted method parameter, we
+         * can't use more than the original param width.
+         */
+        if (!current.has(j) && !(isPreslotted && (maxCategory < getCategoryForSsaReg(j)))) {
 
-            int maxCategory = getCategoryForSsaReg(i);
-            IntSet current = new BitIntSet(oldRegCount);
+          interference.mergeInterferenceSet(j, current);
 
-            interference.mergeInterferenceSet(i, current);
+          maxCategory = Math.max(maxCategory, getCategoryForSsaReg(j));
 
-            boolean isPreslotted = false;
-            int newReg = 0;
-
-            if (PRESLOT_PARAMS && isDefinitionMoveParam(i)) {
-                // Any move-param definition must be a NormalSsaInsn
-                NormalSsaInsn defInsn = (NormalSsaInsn)
-                       ssaMeth.getDefinitionForRegister(i);
-
-                newReg = paramNumberFromMoveParam(defInsn);
-
-                mapper.addMapping(i, newReg, maxCategory);
-                isPreslotted = true;
-            } else {
-                mapper.addMapping(i, nextNewRegister, maxCategory);
-                newReg = nextNewRegister;
-            }
-
-            for (int j = i + 1; j < oldRegCount; j++) {
-                if (mapped.get(j) || isDefinitionMoveParam(j)) {
-                    continue;
-                }
-
-                /*
-                 * If reg j doesn't interfere with the current mapping.
-                 * Also, if this is a pre-slotted method parameter, we
-                 * can't use more than the original param width.
-                 */
-                if (!current.has(j)
-                        && !(isPreslotted
-                            && (maxCategory < getCategoryForSsaReg(j)))) {
-
-                    interference.mergeInterferenceSet(j, current);
-
-                    maxCategory = Math.max(maxCategory,
-                            getCategoryForSsaReg(j));
-
-                    mapper.addMapping(j, newReg, maxCategory);
-                    mapped.set(j);
-                }
-            }
-
-            mapped.set(i);
-            if (!isPreslotted) {
-                nextNewRegister += maxCategory;
-            }
+          mapper.addMapping(j, newReg, maxCategory);
+          mapped.set(j);
         }
+      }
 
-        return mapper;
+      mapped.set(i);
+      if (!isPreslotted) {
+        nextNewRegister += maxCategory;
+      }
     }
 
-    /**
-     * Returns the parameter number that this move-param insn refers to
-     * @param ndefInsn a move-param insn (otherwise, exceptions will be thrown)
-     * @return parameter number (offset in the total parameter width)
-     */
-    private int paramNumberFromMoveParam(NormalSsaInsn ndefInsn) {
-        CstInsn origInsn = (CstInsn) ndefInsn.getOriginalRopInsn();
+    return mapper;
+  }
 
-        return ((CstInteger) origInsn.getConstant()).getValue();
-    }
+  /**
+   * Returns the parameter number that this move-param insn refers to
+   * @param ndefInsn a move-param insn (otherwise, exceptions will be thrown)
+   * @return parameter number (offset in the total parameter width)
+   */
+  private int paramNumberFromMoveParam(NormalSsaInsn ndefInsn) {
+    CstInsn origInsn = (CstInsn) ndefInsn.getOriginalRopInsn();
+
+    return ((CstInteger) origInsn.getConstant()).getValue();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/FirstFitLocalCombiningAllocator.java b/dx/src/com/android/jack/dx/ssa/back/FirstFitLocalCombiningAllocator.java
index 65a5d1d..837bee3 100644
--- a/dx/src/com/android/jack/dx/ssa/back/FirstFitLocalCombiningAllocator.java
+++ b/dx/src/com/android/jack/dx/ssa/back/FirstFitLocalCombiningAllocator.java
@@ -16,7 +16,12 @@
 
 package com.android.jack.dx.ssa.back;
 
-import com.android.jack.dx.rop.code.*;
+import com.android.jack.dx.rop.code.CstInsn;
+import com.android.jack.dx.rop.code.LocalItem;
+import com.android.jack.dx.rop.code.RegOps;
+import com.android.jack.dx.rop.code.RegisterSpec;
+import com.android.jack.dx.rop.code.RegisterSpecList;
+import com.android.jack.dx.rop.code.Rop;
 import com.android.jack.dx.rop.cst.CstInteger;
 import com.android.jack.dx.ssa.InterferenceRegisterMapper;
 import com.android.jack.dx.ssa.NormalSsaInsn;
@@ -40,1100 +45,1079 @@
  * kept together if possible.
  */
 public class FirstFitLocalCombiningAllocator extends RegisterAllocator {
-    /** local debug flag */
-    private static final boolean DEBUG = false;
+  /** local debug flag */
+  private static final boolean DEBUG = false;
 
-    /** maps local variable to a list of associated SSA registers */
-    private final Map<LocalItem, ArrayList<RegisterSpec>> localVariables;
+  /** maps local variable to a list of associated SSA registers */
+  private final Map<LocalItem, ArrayList<RegisterSpec>> localVariables;
 
-    /** list of move-result-pesudo instructions seen in this method */
-    private final ArrayList<NormalSsaInsn> moveResultPseudoInsns;
+  /** list of move-result-pesudo instructions seen in this method */
+  private final ArrayList<NormalSsaInsn> moveResultPseudoInsns;
 
-    /** list of invoke-range instructions seen in this method */
-    private final ArrayList<NormalSsaInsn> invokeRangeInsns;
+  /** list of invoke-range instructions seen in this method */
+  private final ArrayList<NormalSsaInsn> invokeRangeInsns;
 
-    /** list of phi instructions seen in this method */
-    private final ArrayList<PhiInsn> phiInsns;
+  /** list of phi instructions seen in this method */
+  private final ArrayList<PhiInsn> phiInsns;
 
-    /** indexed by SSA reg; the set of SSA regs we've mapped */
-    private final BitSet ssaRegsMapped;
+  /** indexed by SSA reg; the set of SSA regs we've mapped */
+  private final BitSet ssaRegsMapped;
 
-    /** Register mapper which will be our result */
-    private final InterferenceRegisterMapper mapper;
+  /** Register mapper which will be our result */
+  private final InterferenceRegisterMapper mapper;
 
-    /** end of rop registers range (starting at 0) reserved for parameters */
-    private final int paramRangeEnd;
+  /** end of rop registers range (starting at 0) reserved for parameters */
+  private final int paramRangeEnd;
 
-    /** set of rop registers reserved for parameters or local variables */
-    private final BitSet reservedRopRegs;
+  /** set of rop registers reserved for parameters or local variables */
+  private final BitSet reservedRopRegs;
 
-    /** set of rop registers that have been used by anything */
-    private final BitSet usedRopRegs;
+  /** set of rop registers that have been used by anything */
+  private final BitSet usedRopRegs;
 
-    /** true if converter should take steps to minimize rop-form registers */
-    private final boolean minimizeRegisters;
+  /**
+   * Constructs instance.
+   *
+   * @param ssaMeth {@code non-null;} method to process
+   * @param interference non-null interference graph for SSA registers
+   * @param minimizeRegisters true if converter should take steps to
+   * minimize rop-form registers
+   */
+  public FirstFitLocalCombiningAllocator(SsaMethod ssaMeth, InterferenceGraph interference,
+      boolean minimizeRegisters) {
+    super(ssaMeth, interference);
 
-    /**
-     * Constructs instance.
-     *
-     * @param ssaMeth {@code non-null;} method to process
-     * @param interference non-null interference graph for SSA registers
-     * @param minimizeRegisters true if converter should take steps to
-     * minimize rop-form registers
+    ssaRegsMapped = new BitSet(ssaMeth.getRegCount());
+
+    mapper = new InterferenceRegisterMapper(interference, ssaMeth.getRegCount());
+
+    /*
+     * Reserve space for the params at the bottom of the register
+     * space. Later, we'll flip the params to the end of the register
+     * space.
      */
-    public FirstFitLocalCombiningAllocator(
-            SsaMethod ssaMeth, InterferenceGraph interference,
-            boolean minimizeRegisters) {
-        super(ssaMeth, interference);
 
-        ssaRegsMapped = new BitSet(ssaMeth.getRegCount());
+    paramRangeEnd = ssaMeth.getParamWidth();
 
-        mapper = new InterferenceRegisterMapper(
-                interference, ssaMeth.getRegCount());
+    reservedRopRegs = new BitSet(paramRangeEnd * 2);
+    reservedRopRegs.set(0, paramRangeEnd);
+    usedRopRegs = new BitSet(paramRangeEnd * 2);
+    localVariables = new TreeMap<LocalItem, ArrayList<RegisterSpec>>();
+    moveResultPseudoInsns = new ArrayList<NormalSsaInsn>();
+    invokeRangeInsns = new ArrayList<NormalSsaInsn>();
+    phiInsns = new ArrayList<PhiInsn>();
+  }
 
-        this.minimizeRegisters = minimizeRegisters;
+  /** {@inheritDoc} */
+  @Override
+  public boolean wantsParamsMovedHigh() {
+    return true;
+  }
 
-        /*
-         * Reserve space for the params at the bottom of the register
-         * space. Later, we'll flip the params to the end of the register
-         * space.
-         */
+  /** {@inheritDoc} */
+  @Override
+  public RegisterMapper allocateRegisters() {
 
-        paramRangeEnd = ssaMeth.getParamWidth();
+    analyzeInstructions();
 
-        reservedRopRegs = new BitSet(paramRangeEnd * 2);
-        reservedRopRegs.set(0, paramRangeEnd);
-        usedRopRegs = new BitSet(paramRangeEnd * 2);
-        localVariables = new TreeMap<LocalItem, ArrayList<RegisterSpec>>();
-        moveResultPseudoInsns = new ArrayList<NormalSsaInsn>();
-        invokeRangeInsns = new ArrayList<NormalSsaInsn>();
-        phiInsns = new ArrayList<PhiInsn>();
+    if (DEBUG) {
+      printLocalVars();
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean wantsParamsMovedHigh() {
-        return true;
+    if (DEBUG) {
+      System.out.println("--->Mapping local-associated params");
     }
+    handleLocalAssociatedParams();
 
-    /** {@inheritDoc} */
-    @Override
-    public RegisterMapper allocateRegisters() {
-
-        analyzeInstructions();
-
-        if (DEBUG) {
-            printLocalVars();
-        }
-
-        if (DEBUG) System.out.println("--->Mapping local-associated params");
-        handleLocalAssociatedParams();
-
-        if (DEBUG) System.out.println("--->Mapping other params");
-        handleUnassociatedParameters();
-
-        if (DEBUG) System.out.println("--->Mapping invoke-range");
-        handleInvokeRangeInsns();
-
-        if (DEBUG) {
-            System.out.println("--->Mapping local-associated non-params");
-        }
-        handleLocalAssociatedOther();
-
-        if (DEBUG) System.out.println("--->Mapping check-cast results");
-        handleCheckCastResults();
-
-        if (DEBUG) System.out.println("--->Mapping phis");
-        handlePhiInsns();
-
-        if (DEBUG) System.out.println("--->Mapping others");
-        handleNormalUnassociated();
-
-        return mapper;
+    if (DEBUG) {
+      System.out.println("--->Mapping other params");
     }
+    handleUnassociatedParameters();
 
-    /**
-     * Dumps local variable table to stdout for debugging.
-     */
-    private void printLocalVars() {
-        System.out.println("Printing local vars");
-        for (Map.Entry<LocalItem, ArrayList<RegisterSpec>> e :
-                localVariables.entrySet()) {
-            StringBuilder regs = new StringBuilder();
-
-            regs.append('{');
-            regs.append(' ');
-            for (RegisterSpec reg : e.getValue()) {
-                regs.append('v');
-                regs.append(reg.getReg());
-                regs.append(' ');
-            }
-            regs.append('}');
-            System.out.printf("Local: %s Registers: %s\n", e.getKey(), regs);
-        }
+    if (DEBUG) {
+      System.out.println("--->Mapping invoke-range");
     }
+    handleInvokeRangeInsns();
 
-    /**
-     * Maps all local-associated parameters to rop registers.
-     */
-    private void handleLocalAssociatedParams() {
-        for (ArrayList<RegisterSpec> ssaRegs : localVariables.values()) {
-            int sz = ssaRegs.size();
-            int paramIndex = -1;
-            int paramCategory = 0;
-
-            // First, find out if this local variable is a parameter.
-            for (int i = 0; i < sz; i++) {
-                RegisterSpec ssaSpec = ssaRegs.get(i);
-                int ssaReg = ssaSpec.getReg();
-
-                paramIndex = getParameterIndexForReg(ssaReg);
-
-                if (paramIndex >= 0) {
-                    paramCategory = ssaSpec.getCategory();
-                    addMapping(ssaSpec, paramIndex);
-                    break;
-                }
-            }
-
-            if (paramIndex < 0) {
-                // This local wasn't a parameter.
-                continue;
-            }
-
-            // Any remaining local-associated registers will be mapped later.
-            tryMapRegs(ssaRegs, paramIndex, paramCategory, true);
-        }
+    if (DEBUG) {
+      System.out.println("--->Mapping local-associated non-params");
     }
+    handleLocalAssociatedOther();
 
-    /**
-     * Gets the parameter index for SSA registers that are method parameters.
-     * {@code -1} is returned for non-parameter registers.
-     *
-     * @param ssaReg {@code >=0;} SSA register to look up
-     * @return parameter index or {@code -1} if not a parameter
-     */
-    private int getParameterIndexForReg(int ssaReg) {
-        SsaInsn defInsn = ssaMeth.getDefinitionForRegister(ssaReg);
-        if (defInsn == null) {
-            return -1;
-        }
-
-        Rop opcode = defInsn.getOpcode();
-
-        // opcode == null for phi insns.
-        if (opcode != null && opcode.getOpcode() == RegOps.MOVE_PARAM) {
-            CstInsn origInsn = (CstInsn) defInsn.getOriginalRopInsn();
-            return  ((CstInteger) origInsn.getConstant()).getValue();
-        }
-
-        return -1;
+    if (DEBUG) {
+      System.out.println("--->Mapping check-cast results");
     }
+    handleCheckCastResults();
 
-    /**
-     * Maps all local-associated registers that are not parameters.
-     * Tries to find an unreserved range that's wide enough for all of
-     * the SSA registers, and then tries to map them all to that
-     * range. If not all fit, a new range is tried until all registers
-     * have been fit.
-     */
-    private void handleLocalAssociatedOther() {
-        for (ArrayList<RegisterSpec> specs : localVariables.values()) {
-            int ropReg = paramRangeEnd;
-
-            boolean done = false;
-            do {
-                int maxCategory = 1;
-
-                // Compute max category for remaining unmapped registers.
-                int sz = specs.size();
-                for (int i = 0; i < sz; i++) {
-                    RegisterSpec ssaSpec = specs.get(i);
-                    int category = ssaSpec.getCategory();
-                    if (!ssaRegsMapped.get(ssaSpec.getReg())
-                            && category > maxCategory) {
-                        maxCategory = category;
-                    }
-                }
-
-                ropReg = findRopRegForLocal(ropReg, maxCategory);
-                if (canMapRegs(specs, ropReg)) {
-                    done = tryMapRegs(specs, ropReg, maxCategory, true);
-                }
-
-                // Increment for next call to findRopRegForLocal.
-                ropReg++;
-            } while (!done);
-        }
+    if (DEBUG) {
+      System.out.println("--->Mapping phis");
     }
+    handlePhiInsns();
 
-    /**
-     * Tries to map a list of SSA registers into the a rop reg, marking
-     * used rop space as reserved. SSA registers that don't fit are left
-     * unmapped.
-     *
-     * @param specs {@code non-null;} SSA registers to attempt to map
-     * @param ropReg {@code >=0;} rop register to map to
-     * @param maxAllowedCategory {@code 1..2;} maximum category
-     * allowed in mapping.
-     * @param markReserved do so if {@code true}
-     * @return {@code true} if all registers were mapped, {@code false}
-     * if some remain unmapped
-     */
-    private boolean tryMapRegs(
-            ArrayList<RegisterSpec> specs, int ropReg,
-            int maxAllowedCategory, boolean markReserved) {
-        boolean remaining = false;
-        for (RegisterSpec spec : specs) {
-            if (ssaRegsMapped.get(spec.getReg())) {
-                continue;
-            }
-
-            boolean succeeded;
-            succeeded = tryMapReg(spec, ropReg, maxAllowedCategory);
-            remaining = !succeeded || remaining;
-            if (succeeded && markReserved) {
-                // This only needs to be called once really with
-                // the widest category used, but <shrug>
-                markReserved(ropReg, spec.getCategory());
-            }
-        }
-        return !remaining;
+    if (DEBUG) {
+      System.out.println("--->Mapping others");
     }
+    handleNormalUnassociated();
 
-    /**
-     * Tries to map an SSA register to a rop register.
-     *
-     * @param ssaSpec {@code non-null;} SSA register
-     * @param ropReg {@code >=0;} rop register
-     * @param maxAllowedCategory {@code 1..2;} the maximum category
-     * that the SSA register is allowed to be
-     * @return {@code true} if map succeeded, {@code false} if not
-     */
-    private boolean tryMapReg(RegisterSpec ssaSpec, int ropReg,
-            int maxAllowedCategory) {
-        if (ssaSpec.getCategory() <= maxAllowedCategory
-                && !ssaRegsMapped.get(ssaSpec.getReg())
-                && canMapReg(ssaSpec, ropReg)) {
-            addMapping(ssaSpec, ropReg);
-            return true;
-        }
+    return mapper;
+  }
 
-        return false;
+  /**
+   * Dumps local variable table to stdout for debugging.
+   */
+  private void printLocalVars() {
+    System.out.println("Printing local vars");
+    for (Map.Entry<LocalItem, ArrayList<RegisterSpec>> e : localVariables.entrySet()) {
+      StringBuilder regs = new StringBuilder();
+
+      regs.append('{');
+      regs.append(' ');
+      for (RegisterSpec reg : e.getValue()) {
+        regs.append('v');
+        regs.append(reg.getReg());
+        regs.append(' ');
+      }
+      regs.append('}');
+      System.out.printf("Local: %s Registers: %s\n", e.getKey(), regs);
     }
+  }
 
-    /**
-     * Marks a range of rop registers as "reserved for a local variable."
-     *
-     * @param ropReg {@code >= 0;} rop register to reserve
-     * @param category {@code > 0;} width to reserve
-     */
-    private void markReserved(int ropReg, int category) {
-        reservedRopRegs.set(ropReg, ropReg + category, true);
-    }
+  /**
+   * Maps all local-associated parameters to rop registers.
+   */
+  private void handleLocalAssociatedParams() {
+    for (ArrayList<RegisterSpec> ssaRegs : localVariables.values()) {
+      int sz = ssaRegs.size();
+      int paramIndex = -1;
+      int paramCategory = 0;
 
-    /**
-     * Checks to see if any rop registers in the specified range are reserved
-     * for local variables or parameters.
-     *
-     * @param ropRangeStart {@code >= 0;} lowest rop register
-     * @param width {@code > 0;} number of rop registers in range.
-     * @return {@code true} if any register in range is marked reserved
-     */
-    private boolean rangeContainsReserved(int ropRangeStart, int width) {
-        for (int i = ropRangeStart; i < (ropRangeStart + width); i++) {
-            if (reservedRopRegs.get(i)) {
-                return true;
-            }
-        }
-        return false;
-    }
-
-    /**
-     * Returns true if given rop register represents the {@code this} pointer
-     * for a non-static method.
-     *
-     * @param startReg rop register
-     * @return true if the "this" pointer is located here.
-     */
-    private boolean isThisPointerReg(int startReg) {
-        // "this" is always the first parameter.
-        return startReg == 0 && !ssaMeth.isStatic();
-    }
-
-    /**
-     * Finds a range of unreserved rop registers.
-     *
-     * @param startReg {@code >= 0;} a rop register to start the search at
-     * @param width {@code > 0;} the width, in registers, required.
-     * @return {@code >= 0;} start of available register range.
-     */
-    private int findNextUnreservedRopReg(int startReg, int width) {
-        int reg;
-
-        reg = reservedRopRegs.nextClearBit(startReg);
-
-        while (true) {
-            int i = 1;
-
-            while (i < width && !reservedRopRegs.get(reg + i)) {
-                i++;
-            }
-
-            if (i == width) {
-                return reg;
-            }
-
-            reg = reservedRopRegs.nextClearBit(reg + i);
-        }
-    }
-
-    /**
-     * Finds a range of rop regs that can be used for local variables.
-     * If {@code MIX_LOCALS_AND_OTHER} is {@code false}, this means any
-     * rop register that has not yet been used.
-     *
-     * @param startReg {@code >= 0;} a rop register to start the search at
-     * @param width {@code > 0;} the width, in registers, required.
-     * @return {@code >= 0;} start of available register range.
-     */
-    private int findRopRegForLocal(int startReg, int width) {
-        int reg;
-
-        reg = usedRopRegs.nextClearBit(startReg);
-
-        while (true) {
-            int i = 1;
-
-            while (i < width && !usedRopRegs.get(reg + i)) {
-                i++;
-            }
-
-            if (i == width) {
-                return reg;
-            }
-
-            reg = usedRopRegs.nextClearBit(reg + i);
-        }
-    }
-
-    /**
-     * Maps any parameter that isn't local-associated, which can happen
-     * in the case where there is no java debug info.
-     */
-    private void handleUnassociatedParameters() {
-        int szSsaRegs = ssaMeth.getRegCount();
-
-        for (int ssaReg = 0; ssaReg < szSsaRegs; ssaReg++) {
-            if (ssaRegsMapped.get(ssaReg)) {
-                // We already did this one above
-                continue;
-            }
-
-            int paramIndex = getParameterIndexForReg(ssaReg);
-
-            RegisterSpec ssaSpec = getDefinitionSpecForSsaReg(ssaReg);
-            if (paramIndex >= 0) {
-                addMapping(ssaSpec, paramIndex);
-            }
-        }
-    }
-
-    /**
-     * Handles all insns that want a register range for their sources.
-     */
-    private void handleInvokeRangeInsns() {
-        for (NormalSsaInsn insn : invokeRangeInsns) {
-            adjustAndMapSourceRangeRange(insn);
-        }
-    }
-
-    /**
-     * Handles check cast results to reuse the same source register.
-     * Inserts a move if it can't map the same register to both and the
-     * check cast is not caught.
-     */
-    private void handleCheckCastResults() {
-        for (NormalSsaInsn insn : moveResultPseudoInsns) {
-            RegisterSpec moveRegSpec = insn.getResult();
-            int moveReg = moveRegSpec.getReg();
-            BitSet predBlocks = insn.getBlock().getPredecessors();
-
-            // Expect one predecessor block only
-            if (predBlocks.cardinality() != 1) {
-                continue;
-            }
-
-            SsaBasicBlock predBlock =
-                    ssaMeth.getBlocks().get(predBlocks.nextSetBit(0));
-            ArrayList<SsaInsn> insnList = predBlock.getInsns();
-
-            /**
-             * If the predecessor block has a check-cast, it will be the last
-             * instruction
-             */
-            SsaInsn checkCastInsn = insnList.get(insnList.size() - 1);
-            if (checkCastInsn.getOpcode().getOpcode() != RegOps.CHECK_CAST) {
-                continue;
-            }
-
-            RegisterSpec checkRegSpec = checkCastInsn.getSources().get(0);
-            int checkReg = checkRegSpec.getReg();
-
-            /**
-             * See if either register is already mapped. Most likely the move
-             * result will be mapped already since the cast result is stored
-             * in a local variable.
-             */
-            int category = checkRegSpec.getCategory();
-            boolean moveMapped = ssaRegsMapped.get(moveReg);
-            boolean checkMapped = ssaRegsMapped.get(checkReg);
-            if (moveMapped & !checkMapped) {
-                int moveRopReg = mapper.oldToNew(moveReg);
-                checkMapped = tryMapReg(checkRegSpec, moveRopReg, category);
-            }
-            if (checkMapped & !moveMapped) {
-                int checkRopReg = mapper.oldToNew(checkReg);
-                moveMapped = tryMapReg(moveRegSpec, checkRopReg, category);
-            }
-
-            // Map any unmapped registers to anything available
-            if (!moveMapped || !checkMapped) {
-                int ropReg = findNextUnreservedRopReg(paramRangeEnd, category);
-                ArrayList<RegisterSpec> ssaRegs =
-                    new ArrayList<RegisterSpec>(2);
-                ssaRegs.add(moveRegSpec);
-                ssaRegs.add(checkRegSpec);
-
-                while (!tryMapRegs(ssaRegs, ropReg, category, false)) {
-                    ropReg = findNextUnreservedRopReg(ropReg + 1, category);
-                }
-            }
-
-            /*
-             * If source and result have a different mapping, insert a move so
-             * they can have the same mapping. Don't do this if the check cast
-             * is caught, since it will overwrite a potentially live value.
-             */
-            boolean hasExceptionHandlers =
-                checkCastInsn.getOriginalRopInsn().getCatches().size() != 0;
-            int moveRopReg = mapper.oldToNew(moveReg);
-            int checkRopReg = mapper.oldToNew(checkReg);
-            if (moveRopReg != checkRopReg && !hasExceptionHandlers) {
-                ((NormalSsaInsn) checkCastInsn).changeOneSource(0,
-                        insertMoveBefore(checkCastInsn, checkRegSpec));
-                addMapping(checkCastInsn.getSources().get(0), moveRopReg);
-            }
-        }
-    }
-
-    /**
-    * Handles all phi instructions, trying to map them to a common register.
-    */
-    private void handlePhiInsns() {
-        for (PhiInsn insn : phiInsns) {
-            processPhiInsn(insn);
-        }
-    }
-
-    /**
-     * Maps all non-parameter, non-local variable registers.
-     */
-    private void handleNormalUnassociated() {
-        int szSsaRegs = ssaMeth.getRegCount();
-
-        for (int ssaReg = 0; ssaReg < szSsaRegs; ssaReg++) {
-            if (ssaRegsMapped.get(ssaReg)) {
-                // We already did this one
-                continue;
-            }
-
-            RegisterSpec ssaSpec = getDefinitionSpecForSsaReg(ssaReg);
-
-            if (ssaSpec == null) continue;
-
-            int category = ssaSpec.getCategory();
-            // Find a rop reg that does not interfere
-            int ropReg = findNextUnreservedRopReg(paramRangeEnd, category);
-            while (!canMapReg(ssaSpec, ropReg)) {
-                ropReg = findNextUnreservedRopReg(ropReg + 1, category);
-            }
-
-            addMapping(ssaSpec, ropReg);
-        }
-    }
-
-    /**
-     * Checks to see if a list of SSA registers can all be mapped into
-     * the same rop reg. Ignores registers that have already been mapped,
-     * and checks the interference graph and ensures the range does not
-     * cross the parameter range.
-     *
-     * @param specs {@code non-null;} SSA registers to check
-     * @param ropReg {@code >=0;} rop register to check mapping to
-     * @return {@code true} if all unmapped registers can be mapped
-     */
-    private boolean canMapRegs(ArrayList<RegisterSpec> specs, int ropReg) {
-        for (RegisterSpec spec : specs) {
-            if (ssaRegsMapped.get(spec.getReg())) continue;
-            if (!canMapReg(spec, ropReg)) return false;
-        }
-        return true;
-    }
-
-    /**
-     * Checks to see if {@code ssaSpec} can be mapped to
-     * {@code ropReg}. Checks interference graph and ensures
-     * the range does not cross the parameter range.
-     *
-     * @param ssaSpec {@code non-null;} SSA spec
-     * @param ropReg prosepctive new-namespace reg
-     * @return {@code true} if mapping is possible
-     */
-    private boolean canMapReg(RegisterSpec ssaSpec, int ropReg) {
-        int category = ssaSpec.getCategory();
-        return !(spansParamRange(ropReg, category)
-                || mapper.interferes(ssaSpec, ropReg));
-    }
-
-    /**
-     * Returns true if the specified rop register + category
-     * will cross the boundry between the lower {@code paramWidth}
-     * registers reserved for method params and the upper registers. We cannot
-     * allocate a register that spans the param block and the normal block,
-     * because we will be moving the param block to high registers later.
-     *
-     * @param ssaReg register in new namespace
-     * @param category width that the register will have
-     * @return {@code true} in the case noted above
-     */
-    private boolean spansParamRange(int ssaReg, int category) {
-        return ((ssaReg < paramRangeEnd)
-                && ((ssaReg + category) > paramRangeEnd));
-    }
-
-    /**
-     * Analyze each instruction and find out all the local variable assignments
-     * and move-result-pseudo/invoke-range instrucitons.
-     */
-    private void analyzeInstructions() {
-        ssaMeth.forEachInsn(new SsaInsn.Visitor() {
-            /** {@inheritDoc} */
-            public void visitMoveInsn(NormalSsaInsn insn) {
-                processInsn(insn);
-            }
-
-            /** {@inheritDoc} */
-            public void visitPhiInsn(PhiInsn insn) {
-                processInsn(insn);
-            }
-
-            /** {@inheritDoc} */
-            public void visitNonMoveInsn(NormalSsaInsn insn) {
-                processInsn(insn);
-            }
-
-            /**
-             * This method collects three types of instructions:
-             *
-             * 1) Adds a local variable assignment to the
-             *    {@code localVariables} map.
-             * 2) Add move-result-pseudo to the
-             *    {@code moveResultPseudoInsns} list.
-             * 3) Add invoke-range to the
-             *    {@code invokeRangeInsns} list.
-             *
-             * @param insn {@code non-null;} insn that may represent a
-             * local variable assignment
-             */
-            private void processInsn(SsaInsn insn) {
-                RegisterSpec assignment;
-                assignment = insn.getLocalAssignment();
-
-                if (assignment != null) {
-                    LocalItem local = assignment.getLocalItem();
-
-                    ArrayList<RegisterSpec> regList
-                        = localVariables.get(local);
-
-                    if (regList == null) {
-                        regList = new ArrayList<RegisterSpec>();
-                        localVariables.put(local, regList);
-                    }
-
-                    regList.add(assignment);
-                }
-
-                if (insn instanceof NormalSsaInsn) {
-                    if (insn.getOpcode().getOpcode() ==
-                            RegOps.MOVE_RESULT_PSEUDO) {
-                        moveResultPseudoInsns.add((NormalSsaInsn) insn);
-                    } else if (Optimizer.getAdvice().requiresSourcesInOrder(
-                            insn.getOriginalRopInsn().getOpcode(),
-                            insn.getSources())) {
-                        invokeRangeInsns.add((NormalSsaInsn) insn);
-                    }
-                } else if (insn instanceof PhiInsn) {
-                    phiInsns.add((PhiInsn) insn);
-                }
-
-            }
-        });
-    }
-
-    /**
-     * Adds a mapping from an SSA register to a rop register.
-     * {@link #canMapReg} should have already been called.
-     *
-     * @param ssaSpec {@code non-null;} SSA register to map from
-     * @param ropReg {@code >=0;} rop register to map to
-     */
-    private void addMapping(RegisterSpec ssaSpec, int ropReg) {
+      // First, find out if this local variable is a parameter.
+      for (int i = 0; i < sz; i++) {
+        RegisterSpec ssaSpec = ssaRegs.get(i);
         int ssaReg = ssaSpec.getReg();
 
-        // An assertion.
-        if (ssaRegsMapped.get(ssaReg) || !canMapReg(ssaSpec, ropReg)) {
-            throw new RuntimeException(
-                    "attempt to add invalid register mapping");
-        }
+        paramIndex = getParameterIndexForReg(ssaReg);
 
-        if (DEBUG) {
-            System.out.printf("Add mapping s%d -> v%d c:%d\n",
-                    ssaSpec.getReg(), ropReg, ssaSpec.getCategory());
+        if (paramIndex >= 0) {
+          paramCategory = ssaSpec.getCategory();
+          addMapping(ssaSpec, paramIndex);
+          break;
         }
+      }
 
-        int category = ssaSpec.getCategory();
-        mapper.addMapping(ssaSpec.getReg(), ropReg, category);
-        ssaRegsMapped.set(ssaReg);
-        usedRopRegs.set(ropReg, ropReg + category);
+      if (paramIndex < 0) {
+        // This local wasn't a parameter.
+        continue;
+      }
+
+      // Any remaining local-associated registers will be mapped later.
+      tryMapRegs(ssaRegs, paramIndex, paramCategory, true);
+    }
+  }
+
+  /**
+   * Gets the parameter index for SSA registers that are method parameters.
+   * {@code -1} is returned for non-parameter registers.
+   *
+   * @param ssaReg {@code >=0;} SSA register to look up
+   * @return parameter index or {@code -1} if not a parameter
+   */
+  private int getParameterIndexForReg(int ssaReg) {
+    SsaInsn defInsn = ssaMeth.getDefinitionForRegister(ssaReg);
+    if (defInsn == null) {
+      return -1;
     }
 
+    Rop opcode = defInsn.getOpcode();
 
-    /**
-     * Maps the source registers of the specified instruction such that they
-     * will fall in a contiguous range in rop form. Moves are inserted as
-     * necessary to allow the range to be allocated.
-     *
-     * @param insn {@code non-null;} insn whos sources to process
-     */
-    private void adjustAndMapSourceRangeRange(NormalSsaInsn insn) {
-        int newRegStart = findRangeAndAdjust(insn);
-
-        RegisterSpecList sources = insn.getSources();
-        int szSources = sources.size();
-        int nextRopReg = newRegStart;
-
-        for (int i = 0; i < szSources; i++) {
-            RegisterSpec source = sources.get(i);
-            int sourceReg = source.getReg();
-            int category = source.getCategory();
-            int curRopReg = nextRopReg;
-            nextRopReg += category;
-
-            if (ssaRegsMapped.get(sourceReg)) {
-                continue;
-            }
-
-            LocalItem localItem = getLocalItemForReg(sourceReg);
-            addMapping(source, curRopReg);
-
-            if (localItem != null) {
-                markReserved(curRopReg, category);
-                ArrayList<RegisterSpec> similarRegisters
-                        = localVariables.get(localItem);
-
-                int szSimilar = similarRegisters.size();
-
-                /*
-                 * Try to map all SSA registers also associated with
-                 * this local.
-                 */
-                for (int j = 0; j < szSimilar; j++) {
-                    RegisterSpec similarSpec = similarRegisters.get(j);
-                    int similarReg = similarSpec.getReg();
-
-                    // Don't map anything that's also a source.
-                    if (-1 != sources.indexOfRegister(similarReg)) {
-                        continue;
-                    }
-
-                    // Registers left unmapped will get handled later.
-                    tryMapReg(similarSpec, curRopReg, category);
-                }
-            }
-        }
+    // opcode == null for phi insns.
+    if (opcode != null && opcode.getOpcode() == RegOps.MOVE_PARAM) {
+      CstInsn origInsn = (CstInsn) defInsn.getOriginalRopInsn();
+      return ((CstInteger) origInsn.getConstant()).getValue();
     }
 
-    /**
-     * Find a contiguous rop register range that fits the specified
-     * instruction's sources. First, try to center the range around
-     * sources that have already been mapped to rop registers. If that fails,
-     * just find a new contiguous range that doesn't interfere.
-     *
-     * @param insn {@code non-null;} the insn whose sources need to
-     * fit. Must be last insn in basic block.
-     * @return {@code >= 0;} rop register of start of range
-     */
-    private int findRangeAndAdjust(NormalSsaInsn insn) {
-        RegisterSpecList sources = insn.getSources();
-        int szSources = sources.size();
-        // the category for each source index
-        int categoriesForIndex[] = new int[szSources];
-        int rangeLength = 0;
+    return -1;
+  }
 
-        // Compute rangeLength and categoriesForIndex
-        for (int i = 0; i < szSources; i++) {
-            int category = sources.get(i).getCategory();
-            categoriesForIndex[i] = category;
-            rangeLength += categoriesForIndex[i];
+  /**
+   * Maps all local-associated registers that are not parameters.
+   * Tries to find an unreserved range that's wide enough for all of
+   * the SSA registers, and then tries to map them all to that
+   * range. If not all fit, a new range is tried until all registers
+   * have been fit.
+   */
+  private void handleLocalAssociatedOther() {
+    for (ArrayList<RegisterSpec> specs : localVariables.values()) {
+      int ropReg = paramRangeEnd;
+
+      boolean done = false;
+      do {
+        int maxCategory = 1;
+
+        // Compute max category for remaining unmapped registers.
+        int sz = specs.size();
+        for (int i = 0; i < sz; i++) {
+          RegisterSpec ssaSpec = specs.get(i);
+          int category = ssaSpec.getCategory();
+          if (!ssaRegsMapped.get(ssaSpec.getReg()) && category > maxCategory) {
+            maxCategory = category;
+          }
         }
 
-        // the highest score of fits tried so far
-        int maxScore = Integer.MIN_VALUE;
-        // the high scoring range's start
-        int resultRangeStart = -1;
-        // by source index: set of sources needing moves in high scoring plan
-        BitSet resultMovesRequired = null;
+        ropReg = findRopRegForLocal(ropReg, maxCategory);
+        if (canMapRegs(specs, ropReg)) {
+          done = tryMapRegs(specs, ropReg, maxCategory, true);
+        }
+
+        // Increment for next call to findRopRegForLocal.
+        ropReg++;
+      } while (!done);
+    }
+  }
+
+  /**
+   * Tries to map a list of SSA registers into the a rop reg, marking
+   * used rop space as reserved. SSA registers that don't fit are left
+   * unmapped.
+   *
+   * @param specs {@code non-null;} SSA registers to attempt to map
+   * @param ropReg {@code >=0;} rop register to map to
+   * @param maxAllowedCategory {@code 1..2;} maximum category
+   * allowed in mapping.
+   * @param markReserved do so if {@code true}
+   * @return {@code true} if all registers were mapped, {@code false}
+   * if some remain unmapped
+   */
+  private boolean tryMapRegs(ArrayList<RegisterSpec> specs, int ropReg, int maxAllowedCategory,
+      boolean markReserved) {
+    boolean remaining = false;
+    for (RegisterSpec spec : specs) {
+      if (ssaRegsMapped.get(spec.getReg())) {
+        continue;
+      }
+
+      boolean succeeded;
+      succeeded = tryMapReg(spec, ropReg, maxAllowedCategory);
+      remaining = !succeeded || remaining;
+      if (succeeded && markReserved) {
+        // This only needs to be called once really with
+        // the widest category used, but <shrug>
+        markReserved(ropReg, spec.getCategory());
+      }
+    }
+    return !remaining;
+  }
+
+  /**
+   * Tries to map an SSA register to a rop register.
+   *
+   * @param ssaSpec {@code non-null;} SSA register
+   * @param ropReg {@code >=0;} rop register
+   * @param maxAllowedCategory {@code 1..2;} the maximum category
+   * that the SSA register is allowed to be
+   * @return {@code true} if map succeeded, {@code false} if not
+   */
+  private boolean tryMapReg(RegisterSpec ssaSpec, int ropReg, int maxAllowedCategory) {
+    if (ssaSpec.getCategory() <= maxAllowedCategory && !ssaRegsMapped.get(ssaSpec.getReg())
+        && canMapReg(ssaSpec, ropReg)) {
+      addMapping(ssaSpec, ropReg);
+      return true;
+    }
+
+    return false;
+  }
+
+  /**
+   * Marks a range of rop registers as "reserved for a local variable."
+   *
+   * @param ropReg {@code >= 0;} rop register to reserve
+   * @param category {@code > 0;} width to reserve
+   */
+  private void markReserved(int ropReg, int category) {
+    reservedRopRegs.set(ropReg, ropReg + category, true);
+  }
+
+  /**
+   * Checks to see if any rop registers in the specified range are reserved
+   * for local variables or parameters.
+   *
+   * @param ropRangeStart {@code >= 0;} lowest rop register
+   * @param width {@code > 0;} number of rop registers in range.
+   * @return {@code true} if any register in range is marked reserved
+   */
+  private boolean rangeContainsReserved(int ropRangeStart, int width) {
+    for (int i = ropRangeStart; i < (ropRangeStart + width); i++) {
+      if (reservedRopRegs.get(i)) {
+        return true;
+      }
+    }
+    return false;
+  }
+
+  /**
+   * Finds a range of unreserved rop registers.
+   *
+   * @param startReg {@code >= 0;} a rop register to start the search at
+   * @param width {@code > 0;} the width, in registers, required.
+   * @return {@code >= 0;} start of available register range.
+   */
+  private int findNextUnreservedRopReg(int startReg, int width) {
+    int reg;
+
+    reg = reservedRopRegs.nextClearBit(startReg);
+
+    while (true) {
+      int i = 1;
+
+      while (i < width && !reservedRopRegs.get(reg + i)) {
+        i++;
+      }
+
+      if (i == width) {
+        return reg;
+      }
+
+      reg = reservedRopRegs.nextClearBit(reg + i);
+    }
+  }
+
+  /**
+   * Finds a range of rop regs that can be used for local variables.
+   * If {@code MIX_LOCALS_AND_OTHER} is {@code false}, this means any
+   * rop register that has not yet been used.
+   *
+   * @param startReg {@code >= 0;} a rop register to start the search at
+   * @param width {@code > 0;} the width, in registers, required.
+   * @return {@code >= 0;} start of available register range.
+   */
+  private int findRopRegForLocal(int startReg, int width) {
+    int reg;
+
+    reg = usedRopRegs.nextClearBit(startReg);
+
+    while (true) {
+      int i = 1;
+
+      while (i < width && !usedRopRegs.get(reg + i)) {
+        i++;
+      }
+
+      if (i == width) {
+        return reg;
+      }
+
+      reg = usedRopRegs.nextClearBit(reg + i);
+    }
+  }
+
+  /**
+   * Maps any parameter that isn't local-associated, which can happen
+   * in the case where there is no java debug info.
+   */
+  private void handleUnassociatedParameters() {
+    int szSsaRegs = ssaMeth.getRegCount();
+
+    for (int ssaReg = 0; ssaReg < szSsaRegs; ssaReg++) {
+      if (ssaRegsMapped.get(ssaReg)) {
+        // We already did this one above
+        continue;
+      }
+
+      int paramIndex = getParameterIndexForReg(ssaReg);
+
+      RegisterSpec ssaSpec = getDefinitionSpecForSsaReg(ssaReg);
+      if (paramIndex >= 0) {
+        addMapping(ssaSpec, paramIndex);
+      }
+    }
+  }
+
+  /**
+   * Handles all insns that want a register range for their sources.
+   */
+  private void handleInvokeRangeInsns() {
+    for (NormalSsaInsn insn : invokeRangeInsns) {
+      adjustAndMapSourceRangeRange(insn);
+    }
+  }
+
+  /**
+   * Handles check cast results to reuse the same source register.
+   * Inserts a move if it can't map the same register to both and the
+   * check cast is not caught.
+   */
+  private void handleCheckCastResults() {
+    for (NormalSsaInsn insn : moveResultPseudoInsns) {
+      RegisterSpec moveRegSpec = insn.getResult();
+      int moveReg = moveRegSpec.getReg();
+      BitSet predBlocks = insn.getBlock().getPredecessors();
+
+      // Expect one predecessor block only
+      if (predBlocks.cardinality() != 1) {
+        continue;
+      }
+
+      SsaBasicBlock predBlock = ssaMeth.getBlocks().get(predBlocks.nextSetBit(0));
+      ArrayList<SsaInsn> insnList = predBlock.getInsns();
+
+      /**
+       * If the predecessor block has a check-cast, it will be the last
+       * instruction
+       */
+      SsaInsn checkCastInsn = insnList.get(insnList.size() - 1);
+      if (checkCastInsn.getOpcode().getOpcode() != RegOps.CHECK_CAST) {
+        continue;
+      }
+
+      RegisterSpec checkRegSpec = checkCastInsn.getSources().get(0);
+      int checkReg = checkRegSpec.getReg();
+
+      /**
+       * See if either register is already mapped. Most likely the move
+       * result will be mapped already since the cast result is stored
+       * in a local variable.
+       */
+      int category = checkRegSpec.getCategory();
+      boolean moveMapped = ssaRegsMapped.get(moveReg);
+      boolean checkMapped = ssaRegsMapped.get(checkReg);
+      if (moveMapped & !checkMapped) {
+        int moveRopReg = mapper.oldToNew(moveReg);
+        checkMapped = tryMapReg(checkRegSpec, moveRopReg, category);
+      }
+      if (checkMapped & !moveMapped) {
+        int checkRopReg = mapper.oldToNew(checkReg);
+        moveMapped = tryMapReg(moveRegSpec, checkRopReg, category);
+      }
+
+      // Map any unmapped registers to anything available
+      if (!moveMapped || !checkMapped) {
+        int ropReg = findNextUnreservedRopReg(paramRangeEnd, category);
+        ArrayList<RegisterSpec> ssaRegs = new ArrayList<RegisterSpec>(2);
+        ssaRegs.add(moveRegSpec);
+        ssaRegs.add(checkRegSpec);
+
+        while (!tryMapRegs(ssaRegs, ropReg, category, false)) {
+          ropReg = findNextUnreservedRopReg(ropReg + 1, category);
+        }
+      }
+
+      /*
+       * If source and result have a different mapping, insert a move so
+       * they can have the same mapping. Don't do this if the check cast
+       * is caught, since it will overwrite a potentially live value.
+       */
+      boolean hasExceptionHandlers = checkCastInsn.getOriginalRopInsn().getCatches().size() != 0;
+      int moveRopReg = mapper.oldToNew(moveReg);
+      int checkRopReg = mapper.oldToNew(checkReg);
+      if (moveRopReg != checkRopReg && !hasExceptionHandlers) {
+        ((NormalSsaInsn) checkCastInsn).changeOneSource(0,
+            insertMoveBefore(checkCastInsn, checkRegSpec));
+        addMapping(checkCastInsn.getSources().get(0), moveRopReg);
+      }
+    }
+  }
+
+  /**
+  * Handles all phi instructions, trying to map them to a common register.
+  */
+  private void handlePhiInsns() {
+    for (PhiInsn insn : phiInsns) {
+      processPhiInsn(insn);
+    }
+  }
+
+  /**
+   * Maps all non-parameter, non-local variable registers.
+   */
+  private void handleNormalUnassociated() {
+    int szSsaRegs = ssaMeth.getRegCount();
+
+    for (int ssaReg = 0; ssaReg < szSsaRegs; ssaReg++) {
+      if (ssaRegsMapped.get(ssaReg)) {
+        // We already did this one
+        continue;
+      }
+
+      RegisterSpec ssaSpec = getDefinitionSpecForSsaReg(ssaReg);
+
+      if (ssaSpec == null) {
+        continue;
+      }
+
+      int category = ssaSpec.getCategory();
+      // Find a rop reg that does not interfere
+      int ropReg = findNextUnreservedRopReg(paramRangeEnd, category);
+      while (!canMapReg(ssaSpec, ropReg)) {
+        ropReg = findNextUnreservedRopReg(ropReg + 1, category);
+      }
+
+      addMapping(ssaSpec, ropReg);
+    }
+  }
+
+  /**
+   * Checks to see if a list of SSA registers can all be mapped into
+   * the same rop reg. Ignores registers that have already been mapped,
+   * and checks the interference graph and ensures the range does not
+   * cross the parameter range.
+   *
+   * @param specs {@code non-null;} SSA registers to check
+   * @param ropReg {@code >=0;} rop register to check mapping to
+   * @return {@code true} if all unmapped registers can be mapped
+   */
+  private boolean canMapRegs(ArrayList<RegisterSpec> specs, int ropReg) {
+    for (RegisterSpec spec : specs) {
+      if (ssaRegsMapped.get(spec.getReg())) {
+        continue;
+      }
+      if (!canMapReg(spec, ropReg)) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  /**
+   * Checks to see if {@code ssaSpec} can be mapped to
+   * {@code ropReg}. Checks interference graph and ensures
+   * the range does not cross the parameter range.
+   *
+   * @param ssaSpec {@code non-null;} SSA spec
+   * @param ropReg prosepctive new-namespace reg
+   * @return {@code true} if mapping is possible
+   */
+  private boolean canMapReg(RegisterSpec ssaSpec, int ropReg) {
+    int category = ssaSpec.getCategory();
+    return !(spansParamRange(ropReg, category) || mapper.interferes(ssaSpec, ropReg));
+  }
+
+  /**
+   * Returns true if the specified rop register + category
+   * will cross the boundry between the lower {@code paramWidth}
+   * registers reserved for method params and the upper registers. We cannot
+   * allocate a register that spans the param block and the normal block,
+   * because we will be moving the param block to high registers later.
+   *
+   * @param ssaReg register in new namespace
+   * @param category width that the register will have
+   * @return {@code true} in the case noted above
+   */
+  private boolean spansParamRange(int ssaReg, int category) {
+    return ((ssaReg < paramRangeEnd) && ((ssaReg + category) > paramRangeEnd));
+  }
+
+  /**
+   * Analyze each instruction and find out all the local variable assignments
+   * and move-result-pseudo/invoke-range instrucitons.
+   */
+  private void analyzeInstructions() {
+    ssaMeth.forEachInsn(new SsaInsn.Visitor() {
+      /** {@inheritDoc} */
+      @Override
+      public void visitMoveInsn(NormalSsaInsn insn) {
+        processInsn(insn);
+      }
+
+      /** {@inheritDoc} */
+      @Override
+      public void visitPhiInsn(PhiInsn insn) {
+        processInsn(insn);
+      }
+
+      /** {@inheritDoc} */
+      @Override
+      public void visitNonMoveInsn(NormalSsaInsn insn) {
+        processInsn(insn);
+      }
+
+      /**
+       * This method collects three types of instructions:
+       *
+       * 1) Adds a local variable assignment to the
+       *    {@code localVariables} map.
+       * 2) Add move-result-pseudo to the
+       *    {@code moveResultPseudoInsns} list.
+       * 3) Add invoke-range to the
+       *    {@code invokeRangeInsns} list.
+       *
+       * @param insn {@code non-null;} insn that may represent a
+       * local variable assignment
+       */
+      private void processInsn(SsaInsn insn) {
+        RegisterSpec assignment;
+        assignment = insn.getLocalAssignment();
+
+        if (assignment != null) {
+          LocalItem local = assignment.getLocalItem();
+
+          ArrayList<RegisterSpec> regList = localVariables.get(local);
+
+          if (regList == null) {
+            regList = new ArrayList<RegisterSpec>();
+            localVariables.put(local, regList);
+          }
+
+          regList.add(assignment);
+        }
+
+        if (insn instanceof NormalSsaInsn) {
+          if (insn.getOpcode().getOpcode() == RegOps.MOVE_RESULT_PSEUDO) {
+            moveResultPseudoInsns.add((NormalSsaInsn) insn);
+          } else if (Optimizer.getAdvice().requiresSourcesInOrder(
+              insn.getOriginalRopInsn().getOpcode(), insn.getSources())) {
+            invokeRangeInsns.add((NormalSsaInsn) insn);
+          }
+        } else if (insn instanceof PhiInsn) {
+          phiInsns.add((PhiInsn) insn);
+        }
+
+      }
+    });
+  }
+
+  /**
+   * Adds a mapping from an SSA register to a rop register.
+   * {@link #canMapReg} should have already been called.
+   *
+   * @param ssaSpec {@code non-null;} SSA register to map from
+   * @param ropReg {@code >=0;} rop register to map to
+   */
+  private void addMapping(RegisterSpec ssaSpec, int ropReg) {
+    int ssaReg = ssaSpec.getReg();
+
+    // An assertion.
+    if (ssaRegsMapped.get(ssaReg) || !canMapReg(ssaSpec, ropReg)) {
+      throw new RuntimeException("attempt to add invalid register mapping");
+    }
+
+    if (DEBUG) {
+      System.out.printf("Add mapping s%d -> v%d c:%d\n", ssaSpec.getReg(), ropReg,
+          ssaSpec.getCategory());
+    }
+
+    int category = ssaSpec.getCategory();
+    mapper.addMapping(ssaSpec.getReg(), ropReg, category);
+    ssaRegsMapped.set(ssaReg);
+    usedRopRegs.set(ropReg, ropReg + category);
+  }
+
+
+  /**
+   * Maps the source registers of the specified instruction such that they
+   * will fall in a contiguous range in rop form. Moves are inserted as
+   * necessary to allow the range to be allocated.
+   *
+   * @param insn {@code non-null;} insn whos sources to process
+   */
+  private void adjustAndMapSourceRangeRange(NormalSsaInsn insn) {
+    int newRegStart = findRangeAndAdjust(insn);
+
+    RegisterSpecList sources = insn.getSources();
+    int szSources = sources.size();
+    int nextRopReg = newRegStart;
+
+    for (int i = 0; i < szSources; i++) {
+      RegisterSpec source = sources.get(i);
+      int sourceReg = source.getReg();
+      int category = source.getCategory();
+      int curRopReg = nextRopReg;
+      nextRopReg += category;
+
+      if (ssaRegsMapped.get(sourceReg)) {
+        continue;
+      }
+
+      LocalItem localItem = getLocalItemForReg(sourceReg);
+      addMapping(source, curRopReg);
+
+      if (localItem != null) {
+        markReserved(curRopReg, category);
+        ArrayList<RegisterSpec> similarRegisters = localVariables.get(localItem);
+
+        int szSimilar = similarRegisters.size();
 
         /*
-         * First, go through each source that's already been mapped. Try
-         * to center the range around the rop register this source is mapped
-         * to.
+         * Try to map all SSA registers also associated with
+         * this local.
          */
-        int rangeStartOffset = 0;
-        for (int i = 0; i < szSources; i++) {
-            int ssaCenterReg = sources.get(i).getReg();
+        for (int j = 0; j < szSimilar; j++) {
+          RegisterSpec similarSpec = similarRegisters.get(j);
+          int similarReg = similarSpec.getReg();
 
-            if (i != 0) {
-                rangeStartOffset -= categoriesForIndex[i - 1];
-            }
-            if (!ssaRegsMapped.get(ssaCenterReg)) {
-                continue;
-            }
+          // Don't map anything that's also a source.
+          if (-1 != sources.indexOfRegister(similarReg)) {
+            continue;
+          }
 
-            int rangeStart = mapper.oldToNew(ssaCenterReg) + rangeStartOffset;
-
-            if (rangeStart < 0 || spansParamRange(rangeStart, rangeLength)) {
-                continue;
-            }
-
-            BitSet curMovesRequired = new BitSet(szSources);
-
-            int fitWidth
-                    = fitPlanForRange(rangeStart, insn, categoriesForIndex,
-                    curMovesRequired);
-
-            if (fitWidth < 0) {
-                continue;
-            }
-
-            int score = fitWidth - curMovesRequired.cardinality();
-
-            if (score > maxScore) {
-                maxScore = score;
-                resultRangeStart = rangeStart;
-                resultMovesRequired = curMovesRequired;
-            }
-
-            if (fitWidth == rangeLength) {
-                // We can't do any better than this, so stop here
-                break;
-            }
+          // Registers left unmapped will get handled later.
+          tryMapReg(similarSpec, curRopReg, category);
         }
+      }
+    }
+  }
 
+  /**
+   * Find a contiguous rop register range that fits the specified
+   * instruction's sources. First, try to center the range around
+   * sources that have already been mapped to rop registers. If that fails,
+   * just find a new contiguous range that doesn't interfere.
+   *
+   * @param insn {@code non-null;} the insn whose sources need to
+   * fit. Must be last insn in basic block.
+   * @return {@code >= 0;} rop register of start of range
+   */
+  private int findRangeAndAdjust(NormalSsaInsn insn) {
+    RegisterSpecList sources = insn.getSources();
+    int szSources = sources.size();
+    // the category for each source index
+    int categoriesForIndex[] = new int[szSources];
+    int rangeLength = 0;
+
+    // Compute rangeLength and categoriesForIndex
+    for (int i = 0; i < szSources; i++) {
+      int category = sources.get(i).getCategory();
+      categoriesForIndex[i] = category;
+      rangeLength += categoriesForIndex[i];
+    }
+
+    // the highest score of fits tried so far
+    int maxScore = Integer.MIN_VALUE;
+    // the high scoring range's start
+    int resultRangeStart = -1;
+    // by source index: set of sources needing moves in high scoring plan
+    BitSet resultMovesRequired = null;
+
+    /*
+     * First, go through each source that's already been mapped. Try
+     * to center the range around the rop register this source is mapped
+     * to.
+     */
+    int rangeStartOffset = 0;
+    for (int i = 0; i < szSources; i++) {
+      int ssaCenterReg = sources.get(i).getReg();
+
+      if (i != 0) {
+        rangeStartOffset -= categoriesForIndex[i - 1];
+      }
+      if (!ssaRegsMapped.get(ssaCenterReg)) {
+        continue;
+      }
+
+      int rangeStart = mapper.oldToNew(ssaCenterReg) + rangeStartOffset;
+
+      if (rangeStart < 0 || spansParamRange(rangeStart, rangeLength)) {
+        continue;
+      }
+
+      BitSet curMovesRequired = new BitSet(szSources);
+
+      int fitWidth = fitPlanForRange(rangeStart, insn, categoriesForIndex, curMovesRequired);
+
+      if (fitWidth < 0) {
+        continue;
+      }
+
+      int score = fitWidth - curMovesRequired.cardinality();
+
+      if (score > maxScore) {
+        maxScore = score;
+        resultRangeStart = rangeStart;
+        resultMovesRequired = curMovesRequired;
+      }
+
+      if (fitWidth == rangeLength) {
+        // We can't do any better than this, so stop here
+        break;
+      }
+    }
+
+    /*
+     * If we were unable to find a plan for a fit centered around
+     * an already-mapped source, just try to find a range of
+     * registers we can move the range into.
+     */
+
+if (resultRangeStart == -1) {
+      resultMovesRequired = new BitSet(szSources);
+
+      resultRangeStart =
+          findAnyFittingRange(insn, rangeLength, categoriesForIndex, resultMovesRequired);
+    }
+
+    /*
+     * Now, insert any moves required.
+     */
+
+for (int i = resultMovesRequired.nextSetBit(0); i >= 0;
+        i = resultMovesRequired.nextSetBit(i + 1)) {
+      insn.changeOneSource(i, insertMoveBefore(insn, sources.get(i)));
+    }
+
+    return resultRangeStart;
+  }
+
+  /**
+   * Finds an unreserved range that will fit the sources of the
+   * specified instruction. Does not bother trying to center the range
+   * around an already-mapped source register;
+   *
+   * @param insn {@code non-null;} insn to build range for
+   * @param rangeLength {@code >=0;} length required in register units
+   * @param categoriesForIndex {@code non-null;} indexed by source index;
+   * the category for each source
+   * @param outMovesRequired {@code non-null;} an output parameter indexed by
+   * source index that will contain the set of sources which need
+   * moves inserted
+   * @return the rop register that starts the fitting range
+   */
+  private int findAnyFittingRange(NormalSsaInsn insn, int rangeLength, int[] categoriesForIndex,
+      BitSet outMovesRequired) {
+    int rangeStart = paramRangeEnd;
+    while (true) {
+      rangeStart = findNextUnreservedRopReg(rangeStart, rangeLength);
+      int fitWidth = fitPlanForRange(rangeStart, insn, categoriesForIndex, outMovesRequired);
+
+      if (fitWidth >= 0) {
+        break;
+      }
+      rangeStart++;
+      outMovesRequired.clear();
+    }
+    return rangeStart;
+  }
+
+  /**
+   * Attempts to build a plan for fitting a range of sources into rop
+   * registers.
+   *
+   * @param ropReg {@code >= 0;} rop reg that begins range
+   * @param insn {@code non-null;} insn to plan range for
+   * @param categoriesForIndex {@code non-null;} indexed by source index;
+   * the category for each source
+   * @param outMovesRequired {@code non-null;} an output parameter indexed by
+   * source index that will contain the set of sources which need
+   * moves inserted
+   * @return the width of the fit that that does not involve added moves or
+   * {@code -1} if "no fit possible"
+   */
+  private int fitPlanForRange(int ropReg, NormalSsaInsn insn, int[] categoriesForIndex,
+      BitSet outMovesRequired) {
+    RegisterSpecList sources = insn.getSources();
+    int szSources = sources.size();
+    int fitWidth = 0;
+    IntSet liveOut = insn.getBlock().getLiveOutRegs();
+    RegisterSpecList liveOutSpecs = ssaSetToSpecs(liveOut);
+
+    // An SSA reg may only be mapped into a range once.
+    BitSet seen = new BitSet(ssaMeth.getRegCount());
+
+    for (int i = 0; i < szSources; i++) {
+      RegisterSpec ssaSpec = sources.get(i);
+      int ssaReg = ssaSpec.getReg();
+      int category = categoriesForIndex[i];
+
+      if (i != 0) {
+        ropReg += categoriesForIndex[i - 1];
+      }
+
+      if (ssaRegsMapped.get(ssaReg) && mapper.oldToNew(ssaReg) == ropReg) {
+        // This is a register that is already mapped appropriately.
+        fitWidth += category;
+      } else if (rangeContainsReserved(ropReg, category)) {
+        fitWidth = -1;
+        break;
+      } else if (!ssaRegsMapped.get(ssaReg) && canMapReg(ssaSpec, ropReg) && !seen.get(ssaReg)) {
+        // This is a register that can be mapped appropriately.
+        fitWidth += category;
+      } else if (!mapper.areAnyPinned(liveOutSpecs, ropReg, category)
+          && !mapper.areAnyPinned(sources, ropReg, category)) {
         /*
-         * If we were unable to find a plan for a fit centered around
-         * an already-mapped source, just try to find a range of
-         * registers we can move the range into.
-         */
-
-        if (resultRangeStart == -1) {
-            resultMovesRequired = new BitSet(szSources);
-
-            resultRangeStart = findAnyFittingRange(insn, rangeLength,
-                    categoriesForIndex, resultMovesRequired);
-        }
-
-        /*
-         * Now, insert any moves required.
-         */
-
-        for (int i = resultMovesRequired.nextSetBit(0); i >= 0;
-             i = resultMovesRequired.nextSetBit(i+1)) {
-            insn.changeOneSource(i, insertMoveBefore(insn, sources.get(i)));
-        }
-
-        return resultRangeStart;
-    }
-
-    /**
-     * Finds an unreserved range that will fit the sources of the
-     * specified instruction. Does not bother trying to center the range
-     * around an already-mapped source register;
-     *
-     * @param insn {@code non-null;} insn to build range for
-     * @param rangeLength {@code >=0;} length required in register units
-     * @param categoriesForIndex {@code non-null;} indexed by source index;
-     * the category for each source
-     * @param outMovesRequired {@code non-null;} an output parameter indexed by
-     * source index that will contain the set of sources which need
-     * moves inserted
-     * @return the rop register that starts the fitting range
-     */
-    private int findAnyFittingRange(NormalSsaInsn insn, int rangeLength,
-            int[] categoriesForIndex, BitSet outMovesRequired) {
-        int rangeStart = paramRangeEnd;
-        while (true) {
-            rangeStart = findNextUnreservedRopReg(rangeStart, rangeLength);
-            int fitWidth
-                    = fitPlanForRange(rangeStart, insn,
-                    categoriesForIndex, outMovesRequired);
-
-            if (fitWidth >= 0) {
-                break;
-            }
-            rangeStart++;
-            outMovesRequired.clear();
-        }
-        return rangeStart;
-    }
-
-    /**
-     * Attempts to build a plan for fitting a range of sources into rop
-     * registers.
-     *
-     * @param ropReg {@code >= 0;} rop reg that begins range
-     * @param insn {@code non-null;} insn to plan range for
-     * @param categoriesForIndex {@code non-null;} indexed by source index;
-     * the category for each source
-     * @param outMovesRequired {@code non-null;} an output parameter indexed by
-     * source index that will contain the set of sources which need
-     * moves inserted
-     * @return the width of the fit that that does not involve added moves or
-     * {@code -1} if "no fit possible"
-     */
-    private int fitPlanForRange(int ropReg, NormalSsaInsn insn,
-            int[] categoriesForIndex, BitSet outMovesRequired) {
-        RegisterSpecList sources = insn.getSources();
-        int szSources = sources.size();
-        int fitWidth = 0;
-        IntSet liveOut = insn.getBlock().getLiveOutRegs();
-        RegisterSpecList liveOutSpecs = ssaSetToSpecs(liveOut);
-
-        // An SSA reg may only be mapped into a range once.
-        BitSet seen = new BitSet(ssaMeth.getRegCount());
-
-        for (int i = 0; i < szSources ; i++) {
-            RegisterSpec ssaSpec = sources.get(i);
-            int ssaReg = ssaSpec.getReg();
-            int category = categoriesForIndex[i];
-
-            if (i != 0) {
-                ropReg += categoriesForIndex[i-1];
-            }
-
-            if (ssaRegsMapped.get(ssaReg)
-                    && mapper.oldToNew(ssaReg) == ropReg) {
-                // This is a register that is already mapped appropriately.
-                fitWidth += category;
-            } else if (rangeContainsReserved(ropReg, category)) {
-                fitWidth = -1;
-                break;
-            } else if (!ssaRegsMapped.get(ssaReg)
-                    && canMapReg(ssaSpec, ropReg)
-                    && !seen.get(ssaReg)) {
-                // This is a register that can be mapped appropriately.
-                fitWidth += category;
-            } else if (!mapper.areAnyPinned(liveOutSpecs, ropReg, category)
-                    && !mapper.areAnyPinned(sources, ropReg, category)) {
-                /*
-                 * This is a source that can be moved. We can insert a
-                 * move as long as:
-                 *
-                 *   * no SSA register pinned to the desired rop reg
-                 *     is live out on the block
-                 *
-                 *   * no SSA register pinned to desired rop reg is
-                 *     a source of this insn (since this may require
-                 *     overlapping moves, which we can't presently handle)
-                 */
-
-                outMovesRequired.set(i);
-            } else {
-                fitWidth = -1;
-                break;
-            }
-
-            seen.set(ssaReg);
-        }
-        return fitWidth;
-    }
-
-    /**
-     * Converts a bit set of SSA registers into a RegisterSpecList containing
-     * the definition specs of all the registers.
-     *
-     * @param ssaSet {@code non-null;} set of SSA registers
-     * @return list of RegisterSpecs as noted above
-     */
-    RegisterSpecList ssaSetToSpecs(IntSet ssaSet) {
-        RegisterSpecList result = new RegisterSpecList(ssaSet.elements());
-
-        IntIterator iter = ssaSet.iterator();
-
-        int i = 0;
-        while (iter.hasNext()) {
-            result.set(i++, getDefinitionSpecForSsaReg(iter.next()));
-        }
-
-        return result;
-    }
-
-    /**
-     * Gets a local item associated with an ssa register, if one exists.
-     *
-     * @param ssaReg {@code >= 0;} SSA register
-     * @return {@code null-ok;} associated local item or null
-     */
-    private LocalItem getLocalItemForReg(int ssaReg) {
-        for (Map.Entry<LocalItem, ArrayList<RegisterSpec>> entry :
-                 localVariables.entrySet()) {
-            for (RegisterSpec spec : entry.getValue()) {
-                if (spec.getReg() == ssaReg) {
-                    return entry.getKey();
-                }
-            }
-        }
-
-        return null;
-    }
-
-    /**
-     * Attempts to map the sources and result of a phi to a common register.
-     * Will try existing mappings first, from most to least common. If none
-     * of the registers have mappings yet, a new mapping is created.
-     */
-    private void processPhiInsn(PhiInsn insn) {
-        RegisterSpec result = insn.getResult();
-        int resultReg = result.getReg();
-        int category = result.getCategory();
-
-        RegisterSpecList sources = insn.getSources();
-        int sourcesSize = sources.size();
-
-        // List of phi sources / result that need mapping
-        ArrayList<RegisterSpec> ssaRegs = new ArrayList<RegisterSpec>();
-
-        // Track how many times a particular mapping is found
-        Multiset mapSet = new Multiset(sourcesSize + 1);
-
-        /*
-         * If the result of the phi has an existing mapping, get it.
-         * Otherwise, add it to the list of regs that need mapping.
-         */
-        if (ssaRegsMapped.get(resultReg)) {
-            mapSet.add(mapper.oldToNew(resultReg));
-        } else {
-            ssaRegs.add(result);
-        }
-
-        for (int i = 0; i < sourcesSize; i++) {
-            RegisterSpec source = sources.get(i);
-            SsaInsn def = ssaMeth.getDefinitionForRegister(source.getReg());
-            RegisterSpec sourceDef = def.getResult();
-            int sourceReg = sourceDef.getReg();
-
-            /*
-             * If a source of the phi has an existing mapping, get it.
-             * Otherwise, add it to the list of regs that need mapping.
-             */
-            if (ssaRegsMapped.get(sourceReg)) {
-                mapSet.add(mapper.oldToNew(sourceReg));
-            } else {
-                ssaRegs.add(sourceDef);
-            }
-        }
-
-        // Try all existing mappings, with the most common ones first
-        for (int i = 0; i < mapSet.getSize(); i++) {
-            int maxReg = mapSet.getAndRemoveHighestCount();
-            tryMapRegs(ssaRegs, maxReg, category, false);
-        }
-
-        // Map any remaining unmapped regs with whatever fits
-        int mapReg = findNextUnreservedRopReg(paramRangeEnd, category);
-        while (!tryMapRegs(ssaRegs, mapReg, category, false)) {
-            mapReg = findNextUnreservedRopReg(mapReg + 1, category);
-        }
-    }
-
-    // A set that tracks how often elements are added to it.
-    private static class Multiset {
-        private final int[] reg;
-        private final int[] count;
-        private int size;
-
-        /**
-         * Constructs an instance.
+         * This is a source that can be moved. We can insert a
+         * move as long as:
          *
-         * @param maxSize the maximum distinct elements the set may have
-         */
-        public Multiset(int maxSize) {
-            reg = new int[maxSize];
-            count = new int[maxSize];
-            size = 0;
-        }
-
-        /**
-         * Adds an element to the set.
+         *   * no SSA register pinned to the desired rop reg
+         *     is live out on the block
          *
-         * @param element element to add
+         *   * no SSA register pinned to desired rop reg is
+         *     a source of this insn (since this may require
+         *     overlapping moves, which we can't presently handle)
          */
-        public void add(int element) {
-            for (int i = 0; i < size; i++) {
-                if (reg[i] == element) {
-                    count[i]++;
-                    return;
-                }
-            }
 
-            reg[size] = element;
-            count[size] = 1;
-            size++;
-        }
+outMovesRequired.set(i);
+      } else {
+        fitWidth = -1;
+        break;
+      }
 
-        /**
-         * Searches the set for the element that has been added the most.
-         * In the case of a tie, the element that was added first is returned.
-         * Then, it clears the count on that element. The size of the set
-         * remains unchanged.
-         *
-         * @return element with the highest count
-         */
-        public int getAndRemoveHighestCount() {
-            int maxIndex = -1;
-            int maxReg = -1;
-            int maxCount = 0;
-
-            for (int i = 0; i < size; i++) {
-                if (maxCount < count[i]) {
-                    maxIndex = i;
-                    maxReg = reg[i];
-                    maxCount = count[i];
-                }
-            }
-
-            count[maxIndex] = 0;
-            return maxReg;
-        }
-
-        /**
-         * Gets the number of distinct elements in the set.
-         *
-         * @return size of the set
-         */
-        public int getSize() {
-            return size;
-        }
+      seen.set(ssaReg);
     }
+    return fitWidth;
+  }
+
+  /**
+   * Converts a bit set of SSA registers into a RegisterSpecList containing
+   * the definition specs of all the registers.
+   *
+   * @param ssaSet {@code non-null;} set of SSA registers
+   * @return list of RegisterSpecs as noted above
+   */
+  RegisterSpecList ssaSetToSpecs(IntSet ssaSet) {
+    RegisterSpecList result = new RegisterSpecList(ssaSet.elements());
+
+    IntIterator iter = ssaSet.iterator();
+
+    int i = 0;
+    while (iter.hasNext()) {
+      result.set(i++, getDefinitionSpecForSsaReg(iter.next()));
+    }
+
+    return result;
+  }
+
+  /**
+   * Gets a local item associated with an ssa register, if one exists.
+   *
+   * @param ssaReg {@code >= 0;} SSA register
+   * @return {@code null-ok;} associated local item or null
+   */
+  private LocalItem getLocalItemForReg(int ssaReg) {
+    for (Map.Entry<LocalItem, ArrayList<RegisterSpec>> entry : localVariables.entrySet()) {
+      for (RegisterSpec spec : entry.getValue()) {
+        if (spec.getReg() == ssaReg) {
+          return entry.getKey();
+        }
+      }
+    }
+
+    return null;
+  }
+
+  /**
+   * Attempts to map the sources and result of a phi to a common register.
+   * Will try existing mappings first, from most to least common. If none
+   * of the registers have mappings yet, a new mapping is created.
+   */
+  private void processPhiInsn(PhiInsn insn) {
+    RegisterSpec result = insn.getResult();
+    int resultReg = result.getReg();
+    int category = result.getCategory();
+
+    RegisterSpecList sources = insn.getSources();
+    int sourcesSize = sources.size();
+
+    // List of phi sources / result that need mapping
+    ArrayList<RegisterSpec> ssaRegs = new ArrayList<RegisterSpec>();
+
+    // Track how many times a particular mapping is found
+    Multiset mapSet = new Multiset(sourcesSize + 1);
+
+    /*
+     * If the result of the phi has an existing mapping, get it.
+     * Otherwise, add it to the list of regs that need mapping.
+     */
+    if (ssaRegsMapped.get(resultReg)) {
+      mapSet.add(mapper.oldToNew(resultReg));
+    } else {
+      ssaRegs.add(result);
+    }
+
+    for (int i = 0; i < sourcesSize; i++) {
+      RegisterSpec source = sources.get(i);
+      SsaInsn def = ssaMeth.getDefinitionForRegister(source.getReg());
+      RegisterSpec sourceDef = def.getResult();
+      int sourceReg = sourceDef.getReg();
+
+      /*
+       * If a source of the phi has an existing mapping, get it.
+       * Otherwise, add it to the list of regs that need mapping.
+       */
+      if (ssaRegsMapped.get(sourceReg)) {
+        mapSet.add(mapper.oldToNew(sourceReg));
+      } else {
+        ssaRegs.add(sourceDef);
+      }
+    }
+
+    // Try all existing mappings, with the most common ones first
+    for (int i = 0; i < mapSet.getSize(); i++) {
+      int maxReg = mapSet.getAndRemoveHighestCount();
+      tryMapRegs(ssaRegs, maxReg, category, false);
+    }
+
+    // Map any remaining unmapped regs with whatever fits
+    int mapReg = findNextUnreservedRopReg(paramRangeEnd, category);
+    while (!tryMapRegs(ssaRegs, mapReg, category, false)) {
+      mapReg = findNextUnreservedRopReg(mapReg + 1, category);
+    }
+  }
+
+  // A set that tracks how often elements are added to it.
+  private static class Multiset {
+    private final int[] reg;
+    private final int[] count;
+    private int size;
+
+    /**
+     * Constructs an instance.
+     *
+     * @param maxSize the maximum distinct elements the set may have
+     */
+    public Multiset(int maxSize) {
+      reg = new int[maxSize];
+      count = new int[maxSize];
+      size = 0;
+    }
+
+    /**
+     * Adds an element to the set.
+     *
+     * @param element element to add
+     */
+    public void add(int element) {
+      for (int i = 0; i < size; i++) {
+        if (reg[i] == element) {
+          count[i]++;
+          return;
+        }
+      }
+
+      reg[size] = element;
+      count[size] = 1;
+      size++;
+    }
+
+    /**
+     * Searches the set for the element that has been added the most.
+     * In the case of a tie, the element that was added first is returned.
+     * Then, it clears the count on that element. The size of the set
+     * remains unchanged.
+     *
+     * @return element with the highest count
+     */
+    public int getAndRemoveHighestCount() {
+      int maxIndex = -1;
+      int maxReg = -1;
+      int maxCount = 0;
+
+      for (int i = 0; i < size; i++) {
+        if (maxCount < count[i]) {
+          maxIndex = i;
+          maxReg = reg[i];
+          maxCount = count[i];
+        }
+      }
+
+      count[maxIndex] = 0;
+      return maxReg;
+    }
+
+    /**
+     * Gets the number of distinct elements in the set.
+     *
+     * @return size of the set
+     */
+    public int getSize() {
+      return size;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/IdenticalBlockCombiner.java b/dx/src/com/android/jack/dx/ssa/back/IdenticalBlockCombiner.java
index c679d61..9e8b870 100644
--- a/dx/src/com/android/jack/dx/ssa/back/IdenticalBlockCombiner.java
+++ b/dx/src/com/android/jack/dx/ssa/back/IdenticalBlockCombiner.java
@@ -18,12 +18,8 @@
 
 import com.android.jack.dx.rop.code.BasicBlock;
 import com.android.jack.dx.rop.code.BasicBlockList;
-import com.android.jack.dx.rop.code.CstInsn;
-import com.android.jack.dx.rop.code.Insn;
-import com.android.jack.dx.rop.code.InsnList;
 import com.android.jack.dx.rop.code.RegOps;
 import com.android.jack.dx.rop.code.RopMethod;
-import com.android.jack.dx.rop.code.SwitchInsn;
 import com.android.jack.dx.util.IntList;
 
 import java.util.BitSet;
@@ -35,148 +31,145 @@
  * frequently are created when catch blocks are edge-split.
  */
 public class IdenticalBlockCombiner {
-    private final RopMethod ropMethod;
-    private final BasicBlockList blocks;
-    private final BasicBlockList newBlocks;
+  private final RopMethod ropMethod;
+  private final BasicBlockList blocks;
+  private final BasicBlockList newBlocks;
 
-    /**
-     * Constructs instance. Call {@code process()} to run.
-     *
-     * @param rm {@code non-null;} instance to process
-     */
-    public IdenticalBlockCombiner(RopMethod rm) {
-        ropMethod = rm;
-        blocks = ropMethod.getBlocks();
-        newBlocks = blocks.getMutableCopy();
-    }
+  /**
+   * Constructs instance. Call {@code process()} to run.
+   *
+   * @param rm {@code non-null;} instance to process
+   */
+  public IdenticalBlockCombiner(RopMethod rm) {
+    ropMethod = rm;
+    blocks = ropMethod.getBlocks();
+    newBlocks = blocks.getMutableCopy();
+  }
 
-    /**
-     * Runs algorithm. TODO: This is n^2, and could be made linear-ish with
-     * a hash. In particular, hash the contents of each block and only
-     * compare blocks with the same hash.
-     *
-     * @return {@code non-null;} new method that has been processed
-     */
-    public RopMethod process() {
-        int szBlocks = blocks.size();
-        // indexed by label
-        BitSet toDelete = new BitSet(blocks.getMaxLabel());
+  /**
+   * Runs algorithm. TODO(dx team): This is n^2, and could be made linear-ish with
+   * a hash. In particular, hash the contents of each block and only
+   * compare blocks with the same hash.
+   *
+   * @return {@code non-null;} new method that has been processed
+   */
+  public RopMethod process() {
+    int szBlocks = blocks.size();
+    // indexed by label
+    BitSet toDelete = new BitSet(blocks.getMaxLabel());
 
-        // For each non-deleted block...
-        for (int bindex = 0; bindex < szBlocks; bindex++) {
-            BasicBlock b = blocks.get(bindex);
+    // For each non-deleted block...
+    for (int bindex = 0; bindex < szBlocks; bindex++) {
+      BasicBlock b = blocks.get(bindex);
 
-            if (toDelete.get(b.getLabel())) {
-                // doomed block
-                continue;
-            }
+      if (toDelete.get(b.getLabel())) {
+        // doomed block
+        continue;
+      }
 
-            IntList preds = ropMethod.labelToPredecessors(b.getLabel());
+      IntList preds = ropMethod.labelToPredecessors(b.getLabel());
 
-            // ...look at all of it's predecessors that have only one succ...
-            int szPreds = preds.size();
-            for (int i = 0; i < szPreds; i++) {
-                int iLabel = preds.get(i);
+      // ...look at all of it's predecessors that have only one succ...
+      int szPreds = preds.size();
+      for (int i = 0; i < szPreds; i++) {
+        int iLabel = preds.get(i);
 
-                BasicBlock iBlock = blocks.labelToBlock(iLabel);
+        BasicBlock iBlock = blocks.labelToBlock(iLabel);
 
-                if (toDelete.get(iLabel)
-                        || iBlock.getSuccessors().size() > 1
-                        || iBlock.getFirstInsn().getOpcode().getOpcode() ==
-                            RegOps.MOVE_RESULT) {
-                    continue;
-                }
-
-                IntList toCombine = new IntList();
-
-                // ...and see if they can be combined with any other preds...
-                for (int j = i + 1; j < szPreds; j++) {
-                    int jLabel = preds.get(j);
-                    BasicBlock jBlock = blocks.labelToBlock(jLabel);
-
-                    if (jBlock.getSuccessors().size() == 1
-                            && compareInsns(iBlock, jBlock)) {
-
-                        toCombine.add(jLabel);
-                        toDelete.set(jLabel);
-                    }
-                }
-
-                combineBlocks(iLabel, toCombine);
-            }
+        if (toDelete.get(iLabel) || iBlock.getSuccessors().size() > 1
+            || iBlock.getFirstInsn().getOpcode().getOpcode() == RegOps.MOVE_RESULT) {
+          continue;
         }
 
-        for (int i = szBlocks - 1; i >= 0; i--) {
-            if (toDelete.get(newBlocks.get(i).getLabel())) {
-                newBlocks.set(i, null);
-            }
+        IntList toCombine = new IntList();
+
+        // ...and see if they can be combined with any other preds...
+        for (int j = i + 1; j < szPreds; j++) {
+          int jLabel = preds.get(j);
+          BasicBlock jBlock = blocks.labelToBlock(jLabel);
+
+          if (jBlock.getSuccessors().size() == 1 && compareInsns(iBlock, jBlock)) {
+
+            toCombine.add(jLabel);
+            toDelete.set(jLabel);
+          }
         }
 
-        newBlocks.shrinkToFit();
-        newBlocks.setImmutable();
-
-        return new RopMethod(newBlocks, ropMethod.getFirstLabel());
+        combineBlocks(iLabel, toCombine);
+      }
     }
 
-    /**
-     * Helper method to compare the contents of two blocks.
-     *
-     * @param a {@code non-null;} a block to compare
-     * @param b {@code non-null;} another block to compare
-     * @return {@code true} iff the two blocks' instructions are the same
-     */
-    private static boolean compareInsns(BasicBlock a, BasicBlock b) {
-        return a.getInsns().contentEquals(b.getInsns());
+    for (int i = szBlocks - 1; i >= 0; i--) {
+      if (toDelete.get(newBlocks.get(i).getLabel())) {
+        newBlocks.set(i, null);
+      }
     }
 
-    /**
-     * Combines blocks proven identical into one alpha block, re-writing
-     * all of the successor links that point to the beta blocks to point
-     * to the alpha block instead.
-     *
-     * @param alphaLabel block that will replace all the beta block
-     * @param betaLabels label list of blocks to combine
-     */
-    private void combineBlocks(int alphaLabel, IntList betaLabels) {
-        int szBetas = betaLabels.size();
+    newBlocks.shrinkToFit();
+    newBlocks.setImmutable();
 
-        for (int i = 0; i < szBetas; i++) {
-            int betaLabel = betaLabels.get(i);
-            BasicBlock bb = blocks.labelToBlock(betaLabel);
-            IntList preds = ropMethod.labelToPredecessors(bb.getLabel());
-            int szPreds = preds.size();
+    return new RopMethod(newBlocks, ropMethod.getFirstLabel());
+  }
 
-            for (int j = 0; j < szPreds; j++) {
-                BasicBlock predBlock = newBlocks.labelToBlock(preds.get(j));
-                replaceSucc(predBlock, betaLabel, alphaLabel);
-            }
-        }
+  /**
+   * Helper method to compare the contents of two blocks.
+   *
+   * @param a {@code non-null;} a block to compare
+   * @param b {@code non-null;} another block to compare
+   * @return {@code true} iff the two blocks' instructions are the same
+   */
+  private static boolean compareInsns(BasicBlock a, BasicBlock b) {
+    return a.getInsns().contentEquals(b.getInsns());
+  }
+
+  /**
+   * Combines blocks proven identical into one alpha block, re-writing
+   * all of the successor links that point to the beta blocks to point
+   * to the alpha block instead.
+   *
+   * @param alphaLabel block that will replace all the beta block
+   * @param betaLabels label list of blocks to combine
+   */
+  private void combineBlocks(int alphaLabel, IntList betaLabels) {
+    int szBetas = betaLabels.size();
+
+    for (int i = 0; i < szBetas; i++) {
+      int betaLabel = betaLabels.get(i);
+      BasicBlock bb = blocks.labelToBlock(betaLabel);
+      IntList preds = ropMethod.labelToPredecessors(bb.getLabel());
+      int szPreds = preds.size();
+
+      for (int j = 0; j < szPreds; j++) {
+        BasicBlock predBlock = newBlocks.labelToBlock(preds.get(j));
+        replaceSucc(predBlock, betaLabel, alphaLabel);
+      }
+    }
+  }
+
+  /**
+   * Replaces one of a block's successors with a different label. Constructs
+   * an updated BasicBlock instance and places it in {@code newBlocks}.
+   *
+   * @param block block to replace
+   * @param oldLabel label of successor to replace
+   * @param newLabel label of new successor
+   */
+  private void replaceSucc(BasicBlock block, int oldLabel, int newLabel) {
+    IntList newSuccessors = block.getSuccessors().mutableCopy();
+    int newPrimarySuccessor;
+
+    newSuccessors.set(newSuccessors.indexOf(oldLabel), newLabel);
+    newPrimarySuccessor = block.getPrimarySuccessor();
+
+    if (newPrimarySuccessor == oldLabel) {
+      newPrimarySuccessor = newLabel;
     }
 
-    /**
-     * Replaces one of a block's successors with a different label. Constructs
-     * an updated BasicBlock instance and places it in {@code newBlocks}.
-     *
-     * @param block block to replace
-     * @param oldLabel label of successor to replace
-     * @param newLabel label of new successor
-     */
-    private void replaceSucc(BasicBlock block, int oldLabel, int newLabel) {
-        IntList newSuccessors = block.getSuccessors().mutableCopy();
-        int newPrimarySuccessor;
+    newSuccessors.setImmutable();
 
-        newSuccessors.set(newSuccessors.indexOf(oldLabel), newLabel);
-        newPrimarySuccessor = block.getPrimarySuccessor();
+    BasicBlock newBB =
+        new BasicBlock(block.getLabel(), block.getInsns(), newSuccessors, newPrimarySuccessor);
 
-        if (newPrimarySuccessor == oldLabel) {
-            newPrimarySuccessor = newLabel;
-        }
-
-        newSuccessors.setImmutable();
-
-        BasicBlock newBB = new BasicBlock(block.getLabel(),
-                block.getInsns(), newSuccessors, newPrimarySuccessor);
-
-        newBlocks.set(newBlocks.indexOfLabel(block.getLabel()), newBB);
-    }
+    newBlocks.set(newBlocks.indexOfLabel(block.getLabel()), newBB);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/InterferenceGraph.java b/dx/src/com/android/jack/dx/ssa/back/InterferenceGraph.java
index 00a2c69..a93a2a7 100644
--- a/dx/src/com/android/jack/dx/ssa/back/InterferenceGraph.java
+++ b/dx/src/com/android/jack/dx/ssa/back/InterferenceGraph.java
@@ -16,98 +16,89 @@
 
 package com.android.jack.dx.ssa.back;
 
-import com.android.jack.dx.rop.code.RegisterSpec;
-import com.android.jack.dx.ssa.PhiInsn;
 import com.android.jack.dx.ssa.SetFactory;
-import com.android.jack.dx.ssa.SsaBasicBlock;
-import com.android.jack.dx.ssa.SsaInsn;
-import com.android.jack.dx.ssa.SsaMethod;
-import com.android.jack.dx.util.BitIntSet;
 import com.android.jack.dx.util.IntSet;
-import com.android.jack.dx.util.ListIntSet;
 
-import java.util.BitSet;
-import java.util.List;
 import java.util.ArrayList;
 
 /**
  * A register interference graph
  */
 public class InterferenceGraph {
-    /**
-     * {@code non-null;} interference graph, indexed by register in
-     * both dimensions
-     */
-    private final ArrayList<IntSet> interference;
+  /**
+   * {@code non-null;} interference graph, indexed by register in
+   * both dimensions
+   */
+  private final ArrayList<IntSet> interference;
 
-    /**
-     * Creates a new graph.
-     *
-     * @param countRegs {@code >= 0;} the start count of registers in
-     * the namespace. New registers can be added subsequently.
-     */
-    public InterferenceGraph(int countRegs) {
-        interference = new ArrayList<IntSet>(countRegs);
+  /**
+   * Creates a new graph.
+   *
+   * @param countRegs {@code >= 0;} the start count of registers in
+   * the namespace. New registers can be added subsequently.
+   */
+  public InterferenceGraph(int countRegs) {
+    interference = new ArrayList<IntSet>(countRegs);
 
-        for (int i = 0; i < countRegs; i++) {
-            interference.add(SetFactory.makeInterferenceSet(countRegs));
-        }
+    for (int i = 0; i < countRegs; i++) {
+      interference.add(SetFactory.makeInterferenceSet(countRegs));
     }
+  }
 
-    /**
-     * Adds a register pair to the interference/liveness graph. Parameter
-     * order is insignificant.
-     *
-     * @param regV one register index
-     * @param regW another register index
-     */
-    public void add(int regV, int regW) {
-        ensureCapacity(Math.max(regV, regW) + 1);
+  /**
+   * Adds a register pair to the interference/liveness graph. Parameter
+   * order is insignificant.
+   *
+   * @param regV one register index
+   * @param regW another register index
+   */
+  public void add(int regV, int regW) {
+    ensureCapacity(Math.max(regV, regW) + 1);
 
-        interference.get(regV).add(regW);
-        interference.get(regW).add(regV);
+    interference.get(regV).add(regW);
+    interference.get(regW).add(regV);
+  }
+
+  /**
+   * Dumps interference graph to stdout for debugging.
+   */
+  public void dumpToStdout() {
+    int oldRegCount = interference.size();
+
+    for (int i = 0; i < oldRegCount; i++) {
+      StringBuilder sb = new StringBuilder();
+
+      sb.append("Reg " + i + ":" + interference.get(i).toString());
+
+      System.out.println(sb.toString());
     }
+  }
 
-    /**
-     * Dumps interference graph to stdout for debugging.
-     */
-    public void dumpToStdout() {
-        int oldRegCount = interference.size();
-
-        for (int i = 0; i < oldRegCount; i++) {
-            StringBuilder sb = new StringBuilder();
-
-            sb.append("Reg " + i + ":" + interference.get(i).toString());
-
-            System.out.println(sb.toString());
-        }
+  /**
+   * Merges the interference set for a register into a given bit set
+   *
+   * @param reg {@code >= 0;} register
+   * @param set {@code non-null;} interference set; will be merged
+   * with set for given register
+   */
+  public void mergeInterferenceSet(int reg, IntSet set) {
+    if (reg < interference.size()) {
+      set.merge(interference.get(reg));
     }
+  }
 
-    /**
-     * Merges the interference set for a register into a given bit set
-     *
-     * @param reg {@code >= 0;} register
-     * @param set {@code non-null;} interference set; will be merged
-     * with set for given register
-     */
-    public void mergeInterferenceSet(int reg, IntSet set) {
-        if (reg < interference.size()) {
-            set.merge(interference.get(reg));
-        }
+  /**
+   * Ensures that the interference graph is appropriately sized.
+   *
+   * @param size requested minumum size
+   */
+  private void ensureCapacity(int size) {
+    int countRegs = interference.size();
+
+    interference.ensureCapacity(size);
+
+    for (int i = countRegs; i < size; i++) {
+      interference.add(SetFactory.makeInterferenceSet(size));
     }
-
-    /**
-     * Ensures that the interference graph is appropriately sized.
-     *
-     * @param size requested minumum size
-     */
-    private void ensureCapacity(int size) {
-        int countRegs = interference.size();
-
-        interference.ensureCapacity(size);
-
-        for (int i = countRegs; i < size; i++) {
-            interference.add(SetFactory.makeInterferenceSet(size));
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/LivenessAnalyzer.java b/dx/src/com/android/jack/dx/ssa/back/LivenessAnalyzer.java
index 44c9964..5c37f07 100644
--- a/dx/src/com/android/jack/dx/ssa/back/LivenessAnalyzer.java
+++ b/dx/src/com/android/jack/dx/ssa/back/LivenessAnalyzer.java
@@ -22,9 +22,9 @@
 import com.android.jack.dx.ssa.SsaInsn;
 import com.android.jack.dx.ssa.SsaMethod;
 
+import java.util.ArrayList;
 import java.util.BitSet;
 import java.util.List;
-import java.util.ArrayList;
 
 /**
  * From Appel "Modern Compiler Implementation in Java" algorithm 19.17
@@ -35,253 +35,244 @@
  * M = visitedBlocks <p>
  */
 public class LivenessAnalyzer {
-    /**
-     * {@code non-null;} index by basic block indexed set of basic blocks
-     * that have already been visited. "M" as written in the original Appel
-     * algorithm.
-     */
-    private final BitSet visitedBlocks;
+  /**
+   * {@code non-null;} index by basic block indexed set of basic blocks
+   * that have already been visited. "M" as written in the original Appel
+   * algorithm.
+   */
+  private final BitSet visitedBlocks;
 
-    /**
-     * {@code non-null;} set of blocks remaing to visit as "live out as block"
-     */
-    private final BitSet liveOutBlocks;
+  /**
+   * {@code non-null;} set of blocks remaing to visit as "live out as block"
+   */
+  private final BitSet liveOutBlocks;
 
-    /**
-     * {@code >=0;} SSA register currently being analyzed.
-     * "v" in the original Appel algorithm.
-     */
-    private final int regV;
+  /**
+   * {@code >=0;} SSA register currently being analyzed.
+   * "v" in the original Appel algorithm.
+   */
+  private final int regV;
 
-    /** method to process */
-    private final SsaMethod ssaMeth;
+  /** method to process */
+  private final SsaMethod ssaMeth;
 
-    /** interference graph being updated */
-    private final InterferenceGraph interference;
+  /** interference graph being updated */
+  private final InterferenceGraph interference;
 
-    /** block "n" in Appel 19.17 */
-    private SsaBasicBlock blockN;
+  /** block "n" in Appel 19.17 */
+  private SsaBasicBlock blockN;
 
-    /** index of statement {@code s} in {@code blockN} */
-    private int statementIndex;
+  /** index of statement {@code s} in {@code blockN} */
+  private int statementIndex;
 
-    /** the next function to call */
-    private NextFunction nextFunction;
+  /** the next function to call */
+  private NextFunction nextFunction;
 
-    /** constants for {@link #nextFunction} */
-    private static enum NextFunction {
-        LIVE_IN_AT_STATEMENT,
-            LIVE_OUT_AT_STATEMENT,
-            LIVE_OUT_AT_BLOCK,
-            DONE;
+  /** constants for {@link #nextFunction} */
+  private static enum NextFunction {
+    LIVE_IN_AT_STATEMENT, LIVE_OUT_AT_STATEMENT, LIVE_OUT_AT_BLOCK, DONE;
+  }
+
+  /**
+   * Runs register liveness algorithm for a method, updating the
+   * live in/out information in {@code SsaBasicBlock} instances and
+   * returning an interference graph.
+   *
+   * @param ssaMeth {@code non-null;} method to process
+   * @return {@code non-null;} interference graph indexed by SSA
+   * registers in both directions
+   */
+  public static InterferenceGraph constructInterferenceGraph(SsaMethod ssaMeth) {
+    int szRegs = ssaMeth.getRegCount();
+    InterferenceGraph interference = new InterferenceGraph(szRegs);
+
+    for (int i = 0; i < szRegs; i++) {
+      new LivenessAnalyzer(ssaMeth, i, interference).run();
     }
 
-    /**
-     * Runs register liveness algorithm for a method, updating the
-     * live in/out information in {@code SsaBasicBlock} instances and
-     * returning an interference graph.
-     *
-     * @param ssaMeth {@code non-null;} method to process
-     * @return {@code non-null;} interference graph indexed by SSA
-     * registers in both directions
-     */
-    public static InterferenceGraph constructInterferenceGraph(
-            SsaMethod ssaMeth) {
-        int szRegs = ssaMeth.getRegCount();
-        InterferenceGraph interference = new InterferenceGraph(szRegs);
+    coInterferePhis(ssaMeth, interference);
 
-        for (int i = 0; i < szRegs; i++) {
-            new LivenessAnalyzer(ssaMeth, i, interference).run();
+    return interference;
+  }
+
+  /**
+   * Makes liveness analyzer instance for specific register.
+   *
+   * @param ssaMeth {@code non-null;} method to process
+   * @param reg register whose liveness to analyze
+   * @param interference {@code non-null;} indexed by SSA reg in
+   * both dimensions; graph to update
+   *
+   */
+  private LivenessAnalyzer(SsaMethod ssaMeth, int reg, InterferenceGraph interference) {
+    int blocksSz = ssaMeth.getBlocks().size();
+
+    this.ssaMeth = ssaMeth;
+    this.regV = reg;
+    visitedBlocks = new BitSet(blocksSz);
+    liveOutBlocks = new BitSet(blocksSz);
+    this.interference = interference;
+  }
+
+  /**
+   * The algorithm in Appel is presented in partial tail-recursion
+   * form. Obviously, that's not efficient in java, so this function
+   * serves as the dispatcher instead.
+   */
+  private void handleTailRecursion() {
+    while (nextFunction != NextFunction.DONE) {
+      switch (nextFunction) {
+        case LIVE_IN_AT_STATEMENT:
+          nextFunction = NextFunction.DONE;
+          liveInAtStatement();
+          break;
+
+        case LIVE_OUT_AT_STATEMENT:
+          nextFunction = NextFunction.DONE;
+          liveOutAtStatement();
+          break;
+
+        case LIVE_OUT_AT_BLOCK:
+          nextFunction = NextFunction.DONE;
+          liveOutAtBlock();
+          break;
+
+        default:
+      }
+    }
+  }
+
+  /**
+   * From Appel algorithm 19.17.
+   */
+  public void run() {
+    List<SsaInsn> useList = ssaMeth.getUseListForRegister(regV);
+
+    for (SsaInsn insn : useList) {
+      nextFunction = NextFunction.DONE;
+
+      if (insn instanceof PhiInsn) {
+        // If s is a phi-function with V as it's ith argument.
+        PhiInsn phi = (PhiInsn) insn;
+
+        for (SsaBasicBlock pred : phi.predBlocksForReg(regV, ssaMeth)) {
+          blockN = pred;
+
+          nextFunction = NextFunction.LIVE_OUT_AT_BLOCK;
+          handleTailRecursion();
+        }
+      } else {
+        // Special management for registers of category 2, indeed they use
+        // two 32-bits registers thus there is an implicit interference between
+        // the result register and operands contrary to category 1 where there
+        // is no writing of registers before all operands are read.
+        RegisterSpec resultSpec = insn.getResult();
+        if (resultSpec != null && resultSpec.getCategory() == 2
+            && insn.getSources().specForRegister(regV).getCategory() == 2) {
+          interference.add(regV, resultSpec.getReg());
         }
 
-        coInterferePhis(ssaMeth, interference);
+        blockN = insn.getBlock();
+        statementIndex = blockN.getInsns().indexOf(insn);
 
-        return interference;
-    }
-
-    /**
-     * Makes liveness analyzer instance for specific register.
-     *
-     * @param ssaMeth {@code non-null;} method to process
-     * @param reg register whose liveness to analyze
-     * @param interference {@code non-null;} indexed by SSA reg in
-     * both dimensions; graph to update
-     *
-     */
-    private LivenessAnalyzer(SsaMethod ssaMeth, int reg,
-            InterferenceGraph interference) {
-        int blocksSz = ssaMeth.getBlocks().size();
-
-        this.ssaMeth = ssaMeth;
-        this.regV = reg;
-        visitedBlocks = new BitSet(blocksSz);
-        liveOutBlocks = new BitSet(blocksSz);
-        this.interference = interference;
-    }
-
-    /**
-     * The algorithm in Appel is presented in partial tail-recursion
-     * form. Obviously, that's not efficient in java, so this function
-     * serves as the dispatcher instead.
-     */
-    private void handleTailRecursion() {
-        while (nextFunction != NextFunction.DONE) {
-            switch (nextFunction) {
-                case LIVE_IN_AT_STATEMENT:
-                    nextFunction = NextFunction.DONE;
-                    liveInAtStatement();
-                    break;
-
-                case LIVE_OUT_AT_STATEMENT:
-                    nextFunction = NextFunction.DONE;
-                    liveOutAtStatement();
-                    break;
-
-                case LIVE_OUT_AT_BLOCK:
-                    nextFunction = NextFunction.DONE;
-                    liveOutAtBlock();
-                    break;
-
-                default:
-            }
-        }
-    }
-
-    /**
-     * From Appel algorithm 19.17.
-     */
-    public void run() {
-        List<SsaInsn> useList = ssaMeth.getUseListForRegister(regV);
-
-        for (SsaInsn insn : useList) {
-            nextFunction = NextFunction.DONE;
-
-            if (insn instanceof PhiInsn) {
-                // If s is a phi-function with V as it's ith argument.
-                PhiInsn phi = (PhiInsn) insn;
-
-                for (SsaBasicBlock pred :
-                         phi.predBlocksForReg(regV, ssaMeth)) {
-                    blockN = pred;
-
-                    nextFunction = NextFunction.LIVE_OUT_AT_BLOCK;
-                    handleTailRecursion();
-                }
-            } else {
-                // Special management for registers of category 2, indeed they use
-                // two 32-bits registers thus there is an implicit interference between
-                // the result register and operands contrary to category 1 where there
-                // is no writing of registers before all operands are read.
-                RegisterSpec resultSpec = insn.getResult();
-                if (resultSpec != null && resultSpec.getCategory() == 2
-                    && insn.getSources().specForRegister(regV).getCategory() == 2) {
-                  interference.add(regV, resultSpec.getReg());
-                }
-
-                blockN = insn.getBlock();
-                statementIndex = blockN.getInsns().indexOf(insn);
-
-                if (statementIndex < 0) {
-                    throw new RuntimeException(
-                            "insn not found in it's own block");
-                }
-
-                nextFunction = NextFunction.LIVE_IN_AT_STATEMENT;
-                handleTailRecursion();
-            }
+        if (statementIndex < 0) {
+          throw new RuntimeException("insn not found in it's own block");
         }
 
-        int nextLiveOutBlock;
-        while ((nextLiveOutBlock = liveOutBlocks.nextSetBit(0)) >= 0) {
-            blockN = ssaMeth.getBlocks().get(nextLiveOutBlock);
-            liveOutBlocks.clear(nextLiveOutBlock);
-            nextFunction = NextFunction.LIVE_OUT_AT_BLOCK;
-            handleTailRecursion();
-        }
+        nextFunction = NextFunction.LIVE_IN_AT_STATEMENT;
+        handleTailRecursion();
+      }
     }
 
-    /**
-     * "v is live-out at n."
-     */
-    private void liveOutAtBlock() {
-        if (! visitedBlocks.get(blockN.getIndex())) {
-            visitedBlocks.set(blockN.getIndex());
-
-            blockN.addLiveOut(regV);
-
-            ArrayList<SsaInsn> insns;
-
-            insns = blockN.getInsns();
-
-            // Live out at last statement in blockN
-            statementIndex = insns.size() - 1;
-            nextFunction = NextFunction.LIVE_OUT_AT_STATEMENT;
-        }
+    int nextLiveOutBlock;
+    while ((nextLiveOutBlock = liveOutBlocks.nextSetBit(0)) >= 0) {
+      blockN = ssaMeth.getBlocks().get(nextLiveOutBlock);
+      liveOutBlocks.clear(nextLiveOutBlock);
+      nextFunction = NextFunction.LIVE_OUT_AT_BLOCK;
+      handleTailRecursion();
     }
+  }
 
-    /**
-     * "v is live-in at s."
-     */
-    private void liveInAtStatement() {
-        // if s is the first statement in block N
-        if (statementIndex == 0) {
-            // v is live-in at n
-            blockN.addLiveIn(regV);
+  /**
+   * "v is live-out at n."
+   */
+  private void liveOutAtBlock() {
+    if (!visitedBlocks.get(blockN.getIndex())) {
+      visitedBlocks.set(blockN.getIndex());
 
-            BitSet preds = blockN.getPredecessors();
+      blockN.addLiveOut(regV);
 
-            liveOutBlocks.or(preds);
-        } else {
-            // Let s' be the statement preceeding s
-            statementIndex -= 1;
-            nextFunction = NextFunction.LIVE_OUT_AT_STATEMENT;
-        }
+      ArrayList<SsaInsn> insns;
+
+      insns = blockN.getInsns();
+
+      // Live out at last statement in blockN
+      statementIndex = insns.size() - 1;
+      nextFunction = NextFunction.LIVE_OUT_AT_STATEMENT;
     }
+  }
 
-    /**
-     * "v is live-out at s."
-     */
-    private void liveOutAtStatement() {
-        SsaInsn statement = blockN.getInsns().get(statementIndex);
-        RegisterSpec rs = statement.getResult();
+  /**
+   * "v is live-in at s."
+   */
+  private void liveInAtStatement() {
+    // if s is the first statement in block N
+    if (statementIndex == 0) {
+      // v is live-in at n
+      blockN.addLiveIn(regV);
 
-        if (!statement.isResultReg(regV)) {
-            if (rs != null) {
-                interference.add(regV, rs.getReg());
-            }
-            nextFunction = NextFunction.LIVE_IN_AT_STATEMENT;
-        }
+      BitSet preds = blockN.getPredecessors();
+
+      liveOutBlocks.or(preds);
+    } else {
+      // Let s' be the statement preceeding s
+      statementIndex -= 1;
+      nextFunction = NextFunction.LIVE_OUT_AT_STATEMENT;
     }
+  }
 
-    /**
-     * Ensures that all the phi result registers for all the phis in the
-     * same basic block interfere with each other. This is needed since
-     * the dead code remover has allowed through "dead-end phis" whose
-     * results are not used except as local assignments. Without this step,
-     * a the result of a dead-end phi might be assigned the same register
-     * as the result of another phi, and the phi removal move scheduler may
-     * generate moves that over-write the live result.
-     *
-     * @param ssaMeth {@code non-null;} method to pricess
-     * @param interference {@code non-null;} interference graph
-     */
-    private static void coInterferePhis(SsaMethod ssaMeth,
-            InterferenceGraph interference) {
-        for (SsaBasicBlock b : ssaMeth.getBlocks()) {
-            List<SsaInsn> phis = b.getPhiInsns();
+  /**
+   * "v is live-out at s."
+   */
+  private void liveOutAtStatement() {
+    SsaInsn statement = blockN.getInsns().get(statementIndex);
+    RegisterSpec rs = statement.getResult();
 
-            int szPhis = phis.size();
-
-            for (int i = 0; i < szPhis; i++) {
-                for (int j = 0; j < szPhis; j++) {
-                    if (i == j) {
-                        continue;
-                    }
-
-                    interference.add(phis.get(i).getResult().getReg(),
-                        phis.get(j).getResult().getReg());
-                }
-            }
-        }
+    if (!statement.isResultReg(regV)) {
+      if (rs != null) {
+        interference.add(regV, rs.getReg());
+      }
+      nextFunction = NextFunction.LIVE_IN_AT_STATEMENT;
     }
+  }
+
+  /**
+   * Ensures that all the phi result registers for all the phis in the
+   * same basic block interfere with each other. This is needed since
+   * the dead code remover has allowed through "dead-end phis" whose
+   * results are not used except as local assignments. Without this step,
+   * a the result of a dead-end phi might be assigned the same register
+   * as the result of another phi, and the phi removal move scheduler may
+   * generate moves that over-write the live result.
+   *
+   * @param ssaMeth {@code non-null;} method to pricess
+   * @param interference {@code non-null;} interference graph
+   */
+  private static void coInterferePhis(SsaMethod ssaMeth, InterferenceGraph interference) {
+    for (SsaBasicBlock b : ssaMeth.getBlocks()) {
+      List<SsaInsn> phis = b.getPhiInsns();
+
+      int szPhis = phis.size();
+
+      for (int i = 0; i < szPhis; i++) {
+        for (int j = 0; j < szPhis; j++) {
+          if (i == j) {
+            continue;
+          }
+
+          interference.add(phis.get(i).getResult().getReg(), phis.get(j).getResult().getReg());
+        }
+      }
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/NullRegisterAllocator.java b/dx/src/com/android/jack/dx/ssa/back/NullRegisterAllocator.java
index 28b2000..051a159 100644
--- a/dx/src/com/android/jack/dx/ssa/back/NullRegisterAllocator.java
+++ b/dx/src/com/android/jack/dx/ssa/back/NullRegisterAllocator.java
@@ -20,39 +20,35 @@
 import com.android.jack.dx.ssa.RegisterMapper;
 import com.android.jack.dx.ssa.SsaMethod;
 
-import java.util.BitSet;
-import java.util.ArrayList;
-
 /**
  * A register allocator that maps SSA register n to Rop register 2*n,
  * essentially preserving the original mapping and remaining agnostic
  * about normal or wide categories. Used for debugging.
  */
 public class NullRegisterAllocator extends RegisterAllocator {
-    /** {@inheritDoc} */
-    public NullRegisterAllocator(SsaMethod ssaMeth,
-            InterferenceGraph interference) {
-        super(ssaMeth, interference);
+  /** {@inheritDoc} */
+  public NullRegisterAllocator(SsaMethod ssaMeth, InterferenceGraph interference) {
+    super(ssaMeth, interference);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean wantsParamsMovedHigh() {
+    // We're not smart enough for this.
+    return false;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public RegisterMapper allocateRegisters() {
+    int oldRegCount = ssaMeth.getRegCount();
+
+    BasicRegisterMapper mapper = new BasicRegisterMapper(oldRegCount);
+
+    for (int i = 0; i < oldRegCount; i++) {
+      mapper.addMapping(i, i * 2, 2);
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean wantsParamsMovedHigh() {
-        // We're not smart enough for this.
-        return false;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public RegisterMapper allocateRegisters() {
-        int oldRegCount = ssaMeth.getRegCount();
-
-        BasicRegisterMapper mapper = new BasicRegisterMapper(oldRegCount);
-
-        for (int i = 0; i < oldRegCount; i++) {
-            mapper.addMapping(i, i*2, 2);
-        }
-
-        return mapper;
-    }
+    return mapper;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/RegisterAllocator.java b/dx/src/com/android/jack/dx/ssa/back/RegisterAllocator.java
index e81a9d6..9a13b8b 100644
--- a/dx/src/com/android/jack/dx/ssa/back/RegisterAllocator.java
+++ b/dx/src/com/android/jack/dx/ssa/back/RegisterAllocator.java
@@ -30,168 +30,160 @@
 import com.android.jack.dx.util.IntIterator;
 import com.android.jack.dx.util.IntSet;
 
-import java.util.BitSet;
 import java.util.ArrayList;
 
 /**
  * Base class of all register allocators.
  */
 public abstract class RegisterAllocator {
-    /** method being processed */
-    protected final SsaMethod ssaMeth;
+  /** method being processed */
+  protected final SsaMethod ssaMeth;
 
-    /** interference graph, indexed by register in both dimensions */
-    protected final InterferenceGraph interference;
+  /** interference graph, indexed by register in both dimensions */
+  protected final InterferenceGraph interference;
 
-    /**
-     * Creates an instance. Call {@code allocateRegisters} to run.
-     * @param ssaMeth method to process.
-     * @param interference Interference graph, indexed by register in both
-     * dimensions.
-     */
-    public RegisterAllocator(SsaMethod ssaMeth,
-            InterferenceGraph interference) {
-        this.ssaMeth = ssaMeth;
-        this.interference = interference;
+  /**
+   * Creates an instance. Call {@code allocateRegisters} to run.
+   * @param ssaMeth method to process.
+   * @param interference Interference graph, indexed by register in both
+   * dimensions.
+   */
+  public RegisterAllocator(SsaMethod ssaMeth, InterferenceGraph interference) {
+    this.ssaMeth = ssaMeth;
+    this.interference = interference;
+  }
+
+  /**
+   * Indicates whether the method params were allocated at the bottom
+   * of the namespace, and thus should be moved up to the top of the
+   * namespace after phi removal.
+   *
+   * @return {@code true} if params should be moved from low to high
+   */
+  public abstract boolean wantsParamsMovedHigh();
+
+  /**
+   * Runs the algorithm.
+   *
+   * @return a register mapper to apply to the {@code SsaMethod}
+   */
+  public abstract RegisterMapper allocateRegisters();
+
+  /**
+   * Returns the category (width) of the definition site of the register.
+   * Returns {@code 1} for undefined registers.
+   *
+   * @param reg register
+   * @return {@code 1..2}
+   */
+  protected final int getCategoryForSsaReg(int reg) {
+    SsaInsn definition = ssaMeth.getDefinitionForRegister(reg);
+
+    if (definition == null) {
+      // an undefined reg
+      return 1;
+    } else {
+      return definition.getResult().getCategory();
+    }
+  }
+
+  /**
+   * Returns the RegisterSpec of the definition of the register.
+   *
+   * @param reg {@code >= 0;} SSA register
+   * @return definition spec of the register or null if it is never defined
+   * (for the case of "version 0" SSA registers)
+   */
+  protected final RegisterSpec getDefinitionSpecForSsaReg(int reg) {
+    SsaInsn definition = ssaMeth.getDefinitionForRegister(reg);
+
+    return definition == null ? null : definition.getResult();
+  }
+
+  /**
+   * Returns true if the definition site of this register is a
+   * move-param (ie, this is a method parameter).
+   *
+   * @param reg register in question
+   * @return {@code true} if this is a method parameter
+   */
+  protected boolean isDefinitionMoveParam(int reg) {
+    SsaInsn defInsn = ssaMeth.getDefinitionForRegister(reg);
+
+    if (defInsn instanceof NormalSsaInsn) {
+      NormalSsaInsn ndefInsn = (NormalSsaInsn) defInsn;
+
+      return ndefInsn.getOpcode().getOpcode() == RegOps.MOVE_PARAM;
     }
 
-    /**
-     * Indicates whether the method params were allocated at the bottom
-     * of the namespace, and thus should be moved up to the top of the
-     * namespace after phi removal.
-     *
-     * @return {@code true} if params should be moved from low to high
-     */
-    public abstract boolean wantsParamsMovedHigh();
+    return false;
+  }
 
-    /**
-     * Runs the algorithm.
-     *
-     * @return a register mapper to apply to the {@code SsaMethod}
-     */
-    public abstract RegisterMapper allocateRegisters();
+  /**
+   * Inserts a move instruction for a specified SSA register before a
+   * specified instruction, creating a new SSA register and adjusting the
+   * interference graph in the process. The insn currently must be the
+   * last insn in a block.
+   *
+   * @param insn {@code non-null;} insn to insert move before, must
+   * be last insn in block
+   * @param reg {@code non-null;} SSA register to duplicate
+   * @return {@code non-null;} spec of new SSA register created by move
+   */
+  protected final RegisterSpec insertMoveBefore(SsaInsn insn, RegisterSpec reg) {
+    SsaBasicBlock block = insn.getBlock();
+    ArrayList<SsaInsn> insns = block.getInsns();
+    int insnIndex = insns.indexOf(insn);
 
-    /**
-     * Returns the category (width) of the definition site of the register.
-     * Returns {@code 1} for undefined registers.
-     *
-     * @param reg register
-     * @return {@code 1..2}
-     */
-    protected final int getCategoryForSsaReg(int reg) {
-        SsaInsn definition = ssaMeth.getDefinitionForRegister(reg);
-
-        if (definition == null) {
-            // an undefined reg
-            return 1;
-        } else {
-            return definition.getResult().getCategory();
-        }
+    if (insnIndex < 0) {
+      throw new IllegalArgumentException("specified insn is not in this block");
     }
 
-    /**
-     * Returns the RegisterSpec of the definition of the register.
-     *
-     * @param reg {@code >= 0;} SSA register
-     * @return definition spec of the register or null if it is never defined
-     * (for the case of "version 0" SSA registers)
-     */
-    protected final RegisterSpec getDefinitionSpecForSsaReg(int reg) {
-        SsaInsn definition = ssaMeth.getDefinitionForRegister(reg);
-
-        return definition == null ? null : definition.getResult();
+    if (insnIndex != insns.size() - 1) {
+      /*
+       * Presently, the interference updater only works when
+       * adding before the last insn, and the last insn must have no
+       * result
+       */
+      throw new IllegalArgumentException("Adding move here not supported:" + insn.toHuman());
     }
 
-    /**
-     * Returns true if the definition site of this register is a
-     * move-param (ie, this is a method parameter).
-     *
-     * @param reg register in question
-     * @return {@code true} if this is a method parameter
+    /*
+     * Get new register and make new move instruction.
      */
-    protected boolean isDefinitionMoveParam(int reg) {
-        SsaInsn defInsn = ssaMeth.getDefinitionForRegister(reg);
 
-        if (defInsn instanceof NormalSsaInsn) {
-            NormalSsaInsn ndefInsn = (NormalSsaInsn) defInsn;
+// The new result must not have an associated local variable.
+    RegisterSpec newRegSpec = RegisterSpec.make(ssaMeth.makeNewSsaReg(), reg.getTypeBearer());
 
-            return ndefInsn.getOpcode().getOpcode() == RegOps.MOVE_PARAM;
-        }
+    SsaInsn toAdd = SsaInsn.makeFromRop(new PlainInsn(Rops.opMove(newRegSpec.getType()),
+        SourcePosition.NO_INFO, newRegSpec, RegisterSpecList.make(reg)), block);
 
-        return false;
+    insns.add(insnIndex, toAdd);
+
+    int newReg = newRegSpec.getReg();
+
+    /*
+     * Adjust interference graph based on what's live out of the current
+     * block and what's used by the final instruction.
+     */
+
+IntSet liveOut = block.getLiveOutRegs();
+    IntIterator liveOutIter = liveOut.iterator();
+
+    while (liveOutIter.hasNext()) {
+      interference.add(newReg, liveOutIter.next());
     }
 
-    /**
-     * Inserts a move instruction for a specified SSA register before a
-     * specified instruction, creating a new SSA register and adjusting the
-     * interference graph in the process. The insn currently must be the
-     * last insn in a block.
-     *
-     * @param insn {@code non-null;} insn to insert move before, must
-     * be last insn in block
-     * @param reg {@code non-null;} SSA register to duplicate
-     * @return {@code non-null;} spec of new SSA register created by move
-     */
-    protected final RegisterSpec insertMoveBefore(SsaInsn insn,
-            RegisterSpec reg) {
-        SsaBasicBlock block = insn.getBlock();
-        ArrayList<SsaInsn> insns = block.getInsns();
-        int insnIndex = insns.indexOf(insn);
+    // Everything that's a source in the last insn interferes.
+    RegisterSpecList sources = insn.getSources();
+    int szSources = sources.size();
 
-        if (insnIndex < 0) {
-            throw new IllegalArgumentException (
-                    "specified insn is not in this block");
-        }
-
-        if (insnIndex != insns.size() - 1) {
-            /*
-             * Presently, the interference updater only works when
-             * adding before the last insn, and the last insn must have no
-             * result
-             */
-            throw new IllegalArgumentException(
-                    "Adding move here not supported:" + insn.toHuman());
-        }
-
-        /*
-         * Get new register and make new move instruction.
-         */
-
-        // The new result must not have an associated local variable.
-        RegisterSpec newRegSpec = RegisterSpec.make(ssaMeth.makeNewSsaReg(),
-                reg.getTypeBearer());
-
-        SsaInsn toAdd = SsaInsn.makeFromRop(
-                new PlainInsn(Rops.opMove(newRegSpec.getType()),
-                        SourcePosition.NO_INFO, newRegSpec,
-                        RegisterSpecList.make(reg)), block);
-
-        insns.add(insnIndex, toAdd);
-
-        int newReg = newRegSpec.getReg();
-
-        /*
-         * Adjust interference graph based on what's live out of the current
-         * block and what's used by the final instruction.
-         */
-
-        IntSet liveOut = block.getLiveOutRegs();
-        IntIterator liveOutIter = liveOut.iterator();
-
-        while (liveOutIter.hasNext()) {
-            interference.add(newReg, liveOutIter.next());
-        }
-
-        // Everything that's a source in the last insn interferes.
-        RegisterSpecList sources = insn.getSources();
-        int szSources = sources.size();
-
-        for (int i = 0; i < szSources; i++) {
-            interference.add(newReg, sources.get(i).getReg());
-        }
-
-        ssaMeth.onInsnsChanged();
-
-        return newRegSpec;
+    for (int i = 0; i < szSources; i++) {
+      interference.add(newReg, sources.get(i).getReg());
     }
+
+    ssaMeth.onInsnsChanged();
+
+    return newRegSpec;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/ssa/back/SsaToRop.java b/dx/src/com/android/jack/dx/ssa/back/SsaToRop.java
index 2c63a55..9d984f9 100644
--- a/dx/src/com/android/jack/dx/ssa/back/SsaToRop.java
+++ b/dx/src/com/android/jack/dx/ssa/back/SsaToRop.java
@@ -42,339 +42,326 @@
  * Converts a method in SSA form to ROP form.
  */
 public class SsaToRop {
-    /** local debug flag */
-    private static final boolean DEBUG = false;
+  /** local debug flag */
+  private static final boolean DEBUG = false;
 
-    /** {@code non-null;} method to process */
-    private final SsaMethod ssaMeth;
+  /** {@code non-null;} method to process */
+  private final SsaMethod ssaMeth;
 
-    /**
-     * {@code true} if the converter should attempt to minimize
-     * the rop-form register count
-     */
-    private final boolean minimizeRegisters;
+  /**
+   * {@code true} if the converter should attempt to minimize
+   * the rop-form register count
+   */
+  private final boolean minimizeRegisters;
 
-    /** {@code non-null;} interference graph */
-    private final InterferenceGraph interference;
+  /** {@code non-null;} interference graph */
+  private final InterferenceGraph interference;
 
-    /**
-     * Converts a method in SSA form to ROP form.
-     *
-     * @param ssaMeth {@code non-null;} method to process
-     * @param minimizeRegisters {@code true} if the converter should
-     * attempt to minimize the rop-form register count
-     * @return {@code non-null;} rop-form output
-     */
-    public static RopMethod convertToRopMethod(SsaMethod ssaMeth,
-            boolean minimizeRegisters) {
-        return new SsaToRop(ssaMeth, minimizeRegisters).convert();
+  /**
+   * Converts a method in SSA form to ROP form.
+   *
+   * @param ssaMeth {@code non-null;} method to process
+   * @param minimizeRegisters {@code true} if the converter should
+   * attempt to minimize the rop-form register count
+   * @return {@code non-null;} rop-form output
+   */
+  public static RopMethod convertToRopMethod(SsaMethod ssaMeth, boolean minimizeRegisters) {
+    return new SsaToRop(ssaMeth, minimizeRegisters).convert();
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param ssaMeth {@code non-null;} method to process
+   * @param minimizeRegisters {@code true} if the converter should
+   * attempt to minimize the rop-form register count
+   */
+  private SsaToRop(SsaMethod ssaMethod, boolean minimizeRegisters) {
+    this.minimizeRegisters = minimizeRegisters;
+    this.ssaMeth = ssaMethod;
+    this.interference = LivenessAnalyzer.constructInterferenceGraph(ssaMethod);
+  }
+
+  /**
+   * Performs the conversion.
+   *
+   * @return {@code non-null;} rop-form output
+   */
+  private RopMethod convert() {
+    if (DEBUG) {
+      interference.dumpToStdout();
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param ssaMeth {@code non-null;} method to process
-     * @param minimizeRegisters {@code true} if the converter should
-     * attempt to minimize the rop-form register count
-     */
-    private SsaToRop(SsaMethod ssaMethod, boolean minimizeRegisters) {
-        this.minimizeRegisters = minimizeRegisters;
-        this.ssaMeth = ssaMethod;
-        this.interference =
-            LivenessAnalyzer.constructInterferenceGraph(ssaMethod);
+    // These are other allocators for debugging or historical comparison:
+    // allocator = new NullRegisterAllocator(ssaMeth, interference);
+    // allocator = new FirstFitAllocator(ssaMeth, interference);
+
+    RegisterAllocator allocator =
+        new FirstFitLocalCombiningAllocator(ssaMeth, interference, minimizeRegisters);
+
+    RegisterMapper mapper = allocator.allocateRegisters();
+
+    if (DEBUG) {
+      System.out.println("Printing reg map");
+      System.out.println(((BasicRegisterMapper) mapper).toHuman());
     }
 
-    /**
-     * Performs the conversion.
-     *
-     * @return {@code non-null;} rop-form output
-     */
-    private RopMethod convert() {
-        if (DEBUG) {
-            interference.dumpToStdout();
-        }
+    ssaMeth.setBackMode();
 
-        // These are other allocators for debugging or historical comparison:
-        // allocator = new NullRegisterAllocator(ssaMeth, interference);
-        // allocator = new FirstFitAllocator(ssaMeth, interference);
+    ssaMeth.mapRegisters(mapper);
 
-        RegisterAllocator allocator =
-            new FirstFitLocalCombiningAllocator(ssaMeth, interference,
-                    minimizeRegisters);
+    removePhiFunctions();
 
-        RegisterMapper mapper = allocator.allocateRegisters();
-
-        if (DEBUG) {
-            System.out.println("Printing reg map");
-            System.out.println(((BasicRegisterMapper)mapper).toHuman());
-        }
-
-        ssaMeth.setBackMode();
-
-        ssaMeth.mapRegisters(mapper);
-
-        removePhiFunctions();
-
-        if (allocator.wantsParamsMovedHigh()) {
-            moveParametersToHighRegisters();
-        }
-
-        removeEmptyGotos();
-
-        RopMethod ropMethod = new RopMethod(convertBasicBlocks(),
-                ssaMeth.blockIndexToRopLabel(ssaMeth.getEntryBlockIndex()));
-        ropMethod = new IdenticalBlockCombiner(ropMethod).process();
-
-        return ropMethod;
+    if (allocator.wantsParamsMovedHigh()) {
+      moveParametersToHighRegisters();
     }
 
-    /**
-     * Removes all blocks containing only GOTOs from the control flow.
-     * Although much of this work will be done later when converting
-     * from rop to dex, not all simplification cases can be handled
-     * there. Furthermore, any no-op block between the exit block and
-     * blocks containing the real return or throw statements must be
-     * removed.
-     */
-    private void removeEmptyGotos() {
-        final ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
+    removeEmptyGotos();
 
-        ssaMeth.forEachBlockDepthFirst(false, new SsaBasicBlock.Visitor() {
-            public void visitBlock(SsaBasicBlock b, SsaBasicBlock parent) {
-                ArrayList<SsaInsn> insns = b.getInsns();
+    RopMethod ropMethod = new RopMethod(convertBasicBlocks(),
+        ssaMeth.blockIndexToRopLabel(ssaMeth.getEntryBlockIndex()));
+    ropMethod = new IdenticalBlockCombiner(ropMethod).process();
 
-                if ((insns.size() == 1)
-                        && (insns.get(0).getOpcode() == Rops.GOTO)) {
-                    BitSet preds = (BitSet) b.getPredecessors().clone();
+    return ropMethod;
+  }
 
-                    for (int i = preds.nextSetBit(0); i >= 0;
-                            i = preds.nextSetBit(i + 1)) {
-                        SsaBasicBlock pb = blocks.get(i);
-                        pb.replaceSuccessor(b.getIndex(),
-                                b.getPrimarySuccessorIndex());
-                    }
-                }
-            }
-        });
-    }
+  /**
+   * Removes all blocks containing only GOTOs from the control flow.
+   * Although much of this work will be done later when converting
+   * from rop to dex, not all simplification cases can be handled
+   * there. Furthermore, any no-op block between the exit block and
+   * blocks containing the real return or throw statements must be
+   * removed.
+   */
+  private void removeEmptyGotos() {
+    final ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
 
-    /**
-     * See Appel 19.6. To remove the phi instructions in an edge-split
-     * SSA representation we know we can always insert a move in a
-     * predecessor block.
-     */
-    private void removePhiFunctions() {
-        ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
-
-        for (SsaBasicBlock block : blocks) {
-            // Add moves in all the pred blocks for each phi insn.
-            block.forEachPhiInsn(new PhiVisitor(blocks));
-
-            // Delete the phi insns.
-            block.removeAllPhiInsns();
-        }
-
-        /*
-         * After all move insns have been added, sort them so they don't
-         * destructively interfere.
-         */
-        for (SsaBasicBlock block : blocks) {
-            block.scheduleMovesFromPhis();
-        }
-    }
-
-    /**
-     * Helper for {@link #removePhiFunctions}: PhiSuccessorUpdater for
-     * adding move instructions to predecessors based on phi insns.
-     */
-    private static class PhiVisitor implements PhiInsn.Visitor {
-        private final ArrayList<SsaBasicBlock> blocks;
-
-        public PhiVisitor(ArrayList<SsaBasicBlock> blocks) {
-            this.blocks = blocks;
-        }
-
-        public void visitPhiInsn(PhiInsn insn) {
-            RegisterSpecList sources = insn.getSources();
-            RegisterSpec result = insn.getResult();
-            int sz = sources.size();
-
-            for (int i = 0; i < sz; i++) {
-                RegisterSpec source = sources.get(i);
-                SsaBasicBlock predBlock = blocks.get(
-                        insn.predBlockIndexForSourcesIndex(i));
-
-                predBlock.addMoveToEnd(result, source);
-            }
-        }
-    }
-
-    /**
-     * Moves the parameter registers, which allocateRegisters() places
-     * at the bottom of the frame, up to the top of the frame to match
-     * Dalvik calling convention.
-     */
-    private void moveParametersToHighRegisters() {
-        int paramWidth = ssaMeth.getParamWidth();
-        BasicRegisterMapper mapper
-                = new BasicRegisterMapper(ssaMeth.getRegCount());
-        int regCount = ssaMeth.getRegCount();
-
-        for (int i = 0; i < regCount; i++) {
-            if (i < paramWidth) {
-                mapper.addMapping(i, regCount - paramWidth + i, 1);
-            } else {
-                mapper.addMapping(i, i - paramWidth, 1);
-            }
-        }
-
-        if (DEBUG) {
-            System.out.printf("Moving %d registers from 0 to %d\n",
-                    paramWidth, regCount - paramWidth);
-        }
-
-        ssaMeth.mapRegisters(mapper);
-    }
-
-    /**
-     * @return rop-form basic block list
-     */
-    private BasicBlockList convertBasicBlocks() {
-        ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
-
-        // Exit block may be null.
-        SsaBasicBlock exitBlock = ssaMeth.getExitBlock();
-
-        ssaMeth.computeReachability();
-        int ropBlockCount = ssaMeth.getCountReachableBlocks();
-
-        // Don't count the exit block, if it exists and is reachable.
-        ropBlockCount -= (exitBlock != null && exitBlock.isReachable()) ? 1 : 0;
-
-        BasicBlockList result = new BasicBlockList(ropBlockCount);
-
-        // Convert all the reachable blocks except the exit block.
-        int ropBlockIndex = 0;
-        for (SsaBasicBlock b : blocks) {
-            if (b.isReachable() && b != exitBlock) {
-                result.set(ropBlockIndex++, convertBasicBlock(b));
-            }
-        }
-
-        // The exit block, which is discarded, must do nothing.
-        if (exitBlock != null && exitBlock.getInsns().size() != 0) {
-            throw new RuntimeException(
-                    "Exit block must have no insns when leaving SSA form");
-        }
-
-        return result;
-    }
-
-    /**
-     * Validates that a basic block is a valid end predecessor. It must
-     * end in a RETURN or a THROW. Throws a runtime exception on error.
-     *
-     * @param b {@code non-null;} block to validate
-     * @throws RuntimeException on error
-     */
-    private void verifyValidExitPredecessor(SsaBasicBlock b) {
+    ssaMeth.forEachBlockDepthFirst(false, new SsaBasicBlock.Visitor() {
+      @Override
+      public void visitBlock(SsaBasicBlock b, SsaBasicBlock parent) {
         ArrayList<SsaInsn> insns = b.getInsns();
-        SsaInsn lastInsn = insns.get(insns.size() - 1);
-        Rop opcode = lastInsn.getOpcode();
 
-        if (opcode.getBranchingness() != Rop.BRANCH_RETURN
-                && opcode != Rops.THROW) {
-            throw new RuntimeException("Exit predecessor must end"
-                    + " in valid exit statement.");
+        if ((insns.size() == 1) && (insns.get(0).getOpcode() == Rops.GOTO)) {
+          BitSet preds = (BitSet) b.getPredecessors().clone();
+
+          for (int i = preds.nextSetBit(0); i >= 0; i = preds.nextSetBit(i + 1)) {
+            SsaBasicBlock pb = blocks.get(i);
+            pb.replaceSuccessor(b.getIndex(), b.getPrimarySuccessorIndex());
+          }
         }
+      }
+    });
+  }
+
+  /**
+   * See Appel 19.6. To remove the phi instructions in an edge-split
+   * SSA representation we know we can always insert a move in a
+   * predecessor block.
+   */
+  private void removePhiFunctions() {
+    ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
+
+    for (SsaBasicBlock block : blocks) {
+      // Add moves in all the pred blocks for each phi insn.
+      block.forEachPhiInsn(new PhiVisitor(blocks));
+
+      // Delete the phi insns.
+      block.removeAllPhiInsns();
     }
 
-    /**
-     * Converts a single basic block to rop form.
-     *
-     * @param block SSA block to process
-     * @return {@code non-null;} ROP block
+    /*
+     * After all move insns have been added, sort them so they don't
+     * destructively interfere.
      */
-    private BasicBlock convertBasicBlock(SsaBasicBlock block) {
-        IntList successorList = block.getRopLabelSuccessorList();
-        int primarySuccessorLabel = block.getPrimarySuccessorRopLabel();
+    for (SsaBasicBlock block : blocks) {
+      block.scheduleMovesFromPhis();
+    }
+  }
 
-        // Filter out any reference to the SSA form's exit block.
+  /**
+   * Helper for {@link #removePhiFunctions}: PhiSuccessorUpdater for
+   * adding move instructions to predecessors based on phi insns.
+   */
+  private static class PhiVisitor implements PhiInsn.Visitor {
+    private final ArrayList<SsaBasicBlock> blocks;
 
-        // Exit block may be null.
-        SsaBasicBlock exitBlock = ssaMeth.getExitBlock();
-        int exitRopLabel = (exitBlock == null) ? -1 : exitBlock.getRopLabel();
-
-        if (successorList.contains(exitRopLabel)) {
-            if (successorList.size() > 1) {
-                throw new RuntimeException(
-                        "Exit predecessor must have no other successors"
-                                + Hex.u2(block.getRopLabel()));
-            } else {
-                successorList = IntList.EMPTY;
-                primarySuccessorLabel = -1;
-
-                verifyValidExitPredecessor(block);
-            }
-        }
-
-        successorList.setImmutable();
-
-        BasicBlock result = new BasicBlock(
-                block.getRopLabel(), convertInsns(block.getInsns()),
-                successorList,
-                primarySuccessorLabel);
-
-        return result;
+    public PhiVisitor(ArrayList<SsaBasicBlock> blocks) {
+      this.blocks = blocks;
     }
 
-    /**
-     * Converts an insn list to rop form.
-     *
-     * @param ssaInsns {@code non-null;} old instructions
-     * @return {@code non-null;} immutable instruction list
-     */
-    private InsnList convertInsns(ArrayList<SsaInsn> ssaInsns) {
-        int insnCount = ssaInsns.size();
-        InsnList result = new InsnList(insnCount);
+    @Override
+    public void visitPhiInsn(PhiInsn insn) {
+      RegisterSpecList sources = insn.getSources();
+      RegisterSpec result = insn.getResult();
+      int sz = sources.size();
 
-        for (int i = 0; i < insnCount; i++) {
-            result.set(i, ssaInsns.get(i).toRopInsn());
-        }
+      for (int i = 0; i < sz; i++) {
+        RegisterSpec source = sources.get(i);
+        SsaBasicBlock predBlock = blocks.get(insn.predBlockIndexForSourcesIndex(i));
 
-        result.setImmutable();
+        predBlock.addMoveToEnd(result, source);
+      }
+    }
+  }
 
-        return result;
+  /**
+   * Moves the parameter registers, which allocateRegisters() places
+   * at the bottom of the frame, up to the top of the frame to match
+   * Dalvik calling convention.
+   */
+  private void moveParametersToHighRegisters() {
+    int paramWidth = ssaMeth.getParamWidth();
+    BasicRegisterMapper mapper = new BasicRegisterMapper(ssaMeth.getRegCount());
+    int regCount = ssaMeth.getRegCount();
+
+    for (int i = 0; i < regCount; i++) {
+      if (i < paramWidth) {
+        mapper.addMapping(i, regCount - paramWidth + i, 1);
+      } else {
+        mapper.addMapping(i, i - paramWidth, 1);
+      }
     }
 
-    /**
-     * <b>Note:</b> This method is not presently used.
-     *
-     * @return a list of registers ordered by most-frequently-used to
-     * least-frequently-used. Each register is listed once and only
-     * once.
-     */
-    public int[] getRegistersByFrequency() {
-        int regCount = ssaMeth.getRegCount();
-        Integer[] ret = new Integer[regCount];
-
-        for (int i = 0; i < regCount; i++) {
-            ret[i] = i;
-        }
-
-        Arrays.sort(ret, new Comparator<Integer>() {
-            public int compare(Integer o1, Integer o2) {
-                return ssaMeth.getUseListForRegister(o2).size()
-                        - ssaMeth.getUseListForRegister(o1).size();
-            }
-        });
-
-        int result[] = new int[regCount];
-
-        for (int i = 0; i < regCount; i++) {
-            result[i] = ret[i];
-        }
-
-        return result;
+    if (DEBUG) {
+      System.out.printf("Moving %d registers from 0 to %d\n", paramWidth, regCount - paramWidth);
     }
+
+    ssaMeth.mapRegisters(mapper);
+  }
+
+  /**
+   * @return rop-form basic block list
+   */
+  private BasicBlockList convertBasicBlocks() {
+    ArrayList<SsaBasicBlock> blocks = ssaMeth.getBlocks();
+
+    // Exit block may be null.
+    SsaBasicBlock exitBlock = ssaMeth.getExitBlock();
+
+    ssaMeth.computeReachability();
+    int ropBlockCount = ssaMeth.getCountReachableBlocks();
+
+    // Don't count the exit block, if it exists and is reachable.
+    ropBlockCount -= (exitBlock != null && exitBlock.isReachable()) ? 1 : 0;
+
+    BasicBlockList result = new BasicBlockList(ropBlockCount);
+
+    // Convert all the reachable blocks except the exit block.
+    int ropBlockIndex = 0;
+    for (SsaBasicBlock b : blocks) {
+      if (b.isReachable() && b != exitBlock) {
+        result.set(ropBlockIndex++, convertBasicBlock(b));
+      }
+    }
+
+    // The exit block, which is discarded, must do nothing.
+    if (exitBlock != null && exitBlock.getInsns().size() != 0) {
+      throw new RuntimeException("Exit block must have no insns when leaving SSA form");
+    }
+
+    return result;
+  }
+
+  /**
+   * Validates that a basic block is a valid end predecessor. It must
+   * end in a RETURN or a THROW. Throws a runtime exception on error.
+   *
+   * @param b {@code non-null;} block to validate
+   * @throws RuntimeException on error
+   */
+  private void verifyValidExitPredecessor(SsaBasicBlock b) {
+    ArrayList<SsaInsn> insns = b.getInsns();
+    SsaInsn lastInsn = insns.get(insns.size() - 1);
+    Rop opcode = lastInsn.getOpcode();
+
+    if (opcode.getBranchingness() != Rop.BRANCH_RETURN && opcode != Rops.THROW) {
+      throw new RuntimeException("Exit predecessor must end" + " in valid exit statement.");
+    }
+  }
+
+  /**
+   * Converts a single basic block to rop form.
+   *
+   * @param block SSA block to process
+   * @return {@code non-null;} ROP block
+   */
+  private BasicBlock convertBasicBlock(SsaBasicBlock block) {
+    IntList successorList = block.getRopLabelSuccessorList();
+    int primarySuccessorLabel = block.getPrimarySuccessorRopLabel();
+
+    // Filter out any reference to the SSA form's exit block.
+
+    // Exit block may be null.
+    SsaBasicBlock exitBlock = ssaMeth.getExitBlock();
+    int exitRopLabel = (exitBlock == null) ? -1 : exitBlock.getRopLabel();
+
+    if (successorList.contains(exitRopLabel)) {
+      if (successorList.size() > 1) {
+        throw new RuntimeException(
+            "Exit predecessor must have no other successors" + Hex.u2(block.getRopLabel()));
+      } else {
+        successorList = IntList.EMPTY;
+        primarySuccessorLabel = -1;
+
+        verifyValidExitPredecessor(block);
+      }
+    }
+
+    successorList.setImmutable();
+
+    BasicBlock result = new BasicBlock(block.getRopLabel(), convertInsns(block.getInsns()),
+        successorList, primarySuccessorLabel);
+
+    return result;
+  }
+
+  /**
+   * Converts an insn list to rop form.
+   *
+   * @param ssaInsns {@code non-null;} old instructions
+   * @return {@code non-null;} immutable instruction list
+   */
+  private InsnList convertInsns(ArrayList<SsaInsn> ssaInsns) {
+    int insnCount = ssaInsns.size();
+    InsnList result = new InsnList(insnCount);
+
+    for (int i = 0; i < insnCount; i++) {
+      result.set(i, ssaInsns.get(i).toRopInsn());
+    }
+
+    result.setImmutable();
+
+    return result;
+  }
+
+  /**
+   * <b>Note:</b> This method is not presently used.
+   *
+   * @return a list of registers ordered by most-frequently-used to
+   * least-frequently-used. Each register is listed once and only
+   * once.
+   */
+  public int[] getRegistersByFrequency() {
+    int regCount = ssaMeth.getRegCount();
+    Integer[] ret = new Integer[regCount];
+
+    for (int i = 0; i < regCount; i++) {
+      ret[i] = i;
+    }
+
+    Arrays.sort(ret, new Comparator<Integer>() {
+      @Override
+      public int compare(Integer o1, Integer o2) {
+        return ssaMeth.getUseListForRegister(o2).size() - ssaMeth.getUseListForRegister(o1).size();
+      }
+    });
+
+    int result[] = new int[regCount];
+
+    for (int i = 0; i < regCount; i++) {
+      result[i] = ret[i];
+    }
+
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/AnnotatedOutput.java b/dx/src/com/android/jack/dx/util/AnnotatedOutput.java
index 6bbe4b7..b8374b4 100644
--- a/dx/src/com/android/jack/dx/util/AnnotatedOutput.java
+++ b/dx/src/com/android/jack/dx/util/AnnotatedOutput.java
@@ -20,60 +20,59 @@
  * Interface for a binary output destination that may be augmented
  * with textual annotations.
  */
-public interface AnnotatedOutput
-        extends Output {
-    /**
-     * Get whether this instance will actually keep annotations.
-     *
-     * @return {@code true} iff annotations are being kept
-     */
-    public boolean annotates();
+public interface AnnotatedOutput extends Output {
+  /**
+   * Get whether this instance will actually keep annotations.
+   *
+   * @return {@code true} iff annotations are being kept
+   */
+  public boolean annotates();
 
-    /**
-     * Get whether this instance is intended to keep verbose annotations.
-     * Annotators may use the result of calling this method to inform their
-     * annotation activity.
-     *
-     * @return {@code true} iff annotations are to be verbose
-     */
-    public boolean isVerbose();
+  /**
+   * Get whether this instance is intended to keep verbose annotations.
+   * Annotators may use the result of calling this method to inform their
+   * annotation activity.
+   *
+   * @return {@code true} iff annotations are to be verbose
+   */
+  public boolean isVerbose();
 
-    /**
-     * Add an annotation for the subsequent output. Any previously
-     * open annotation will be closed by this call, and the new
-     * annotation marks all subsequent output until another annotation
-     * call.
-     *
-     * @param msg {@code non-null;} the annotation message
-     */
-    public void annotate(String msg);
+  /**
+   * Add an annotation for the subsequent output. Any previously
+   * open annotation will be closed by this call, and the new
+   * annotation marks all subsequent output until another annotation
+   * call.
+   *
+   * @param msg {@code non-null;} the annotation message
+   */
+  public void annotate(String msg);
 
-    /**
-     * Add an annotation for a specified amount of subsequent
-     * output. Any previously open annotation will be closed by this
-     * call. If there is already pending annotation from one or more
-     * previous calls to this method, the new call "consumes" output
-     * after all the output covered by the previous calls.
-     *
-     * @param amt {@code >= 0;} the amount of output for this annotation to
-     * cover
-     * @param msg {@code non-null;} the annotation message
-     */
-    public void annotate(int amt, String msg);
+  /**
+   * Add an annotation for a specified amount of subsequent
+   * output. Any previously open annotation will be closed by this
+   * call. If there is already pending annotation from one or more
+   * previous calls to this method, the new call "consumes" output
+   * after all the output covered by the previous calls.
+   *
+   * @param amt {@code >= 0;} the amount of output for this annotation to
+   * cover
+   * @param msg {@code non-null;} the annotation message
+   */
+  public void annotate(int amt, String msg);
 
-    /**
-     * End the most recent annotation. Subsequent output will be unannotated,
-     * until the next call to {@link #annotate}.
-     */
-    public void endAnnotation();
+  /**
+   * End the most recent annotation. Subsequent output will be unannotated,
+   * until the next call to {@link #annotate}.
+   */
+  public void endAnnotation();
 
-    /**
-     * Get the maximum width of the annotated output. This is advisory:
-     * Implementations of this interface are encouraged to deal with too-wide
-     * output, but annotaters are encouraged to attempt to avoid exceeding
-     * the indicated width.
-     *
-     * @return {@code >= 1;} the maximum width
-     */
-    public int getAnnotationWidth();
+  /**
+   * Get the maximum width of the annotated output. This is advisory:
+   * Implementations of this interface are encouraged to deal with too-wide
+   * output, but annotaters are encouraged to attempt to avoid exceeding
+   * the indicated width.
+   *
+   * @return {@code >= 1;} the maximum width
+   */
+  public int getAnnotationWidth();
 }
diff --git a/dx/src/com/android/jack/dx/util/BitIntSet.java b/dx/src/com/android/jack/dx/util/BitIntSet.java
index a4f5156..b19a387 100644
--- a/dx/src/com/android/jack/dx/util/BitIntSet.java
+++ b/dx/src/com/android/jack/dx/util/BitIntSet.java
@@ -23,123 +23,129 @@
  */
 public class BitIntSet implements IntSet {
 
-    /** also accessed in ListIntSet */
-    int[] bits;
+  /** also accessed in ListIntSet */
+  int[] bits;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param max the maximum value of ints in this set.
-     */
-    public BitIntSet(int max) {
-        bits = Bits.makeBitSet(max);
+  /**
+   * Constructs an instance.
+   *
+   * @param max the maximum value of ints in this set.
+   */
+  public BitIntSet(int max) {
+    bits = Bits.makeBitSet(max);
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void add(int value) {
+    ensureCapacity(value);
+    Bits.set(bits, value, true);
+  }
+
+  /**
+   * Ensures that the bit set has the capacity to represent the given value.
+   *
+   * @param value {@code >= 0;} value to represent
+   */
+  private void ensureCapacity(int value) {
+    if (value >= Bits.getMax(bits)) {
+      int[] newBits = Bits.makeBitSet(Math.max(value + 1, 2 * Bits.getMax(bits)));
+      System.arraycopy(bits, 0, newBits, 0, bits.length);
+      bits = newBits;
     }
+  }
 
-    /** @inheritDoc */
-    public void add(int value) {
-        ensureCapacity(value);
-        Bits.set(bits, value, true);
+  /** @inheritDoc */
+  @Override
+  public void remove(int value) {
+    if (value < Bits.getMax(bits)) {
+      Bits.set(bits, value, false);
     }
+  }
 
-    /**
-     * Ensures that the bit set has the capacity to represent the given value.
-     *
-     * @param value {@code >= 0;} value to represent
-     */
-    private void ensureCapacity(int value) {
-        if (value >= Bits.getMax(bits)) {
-            int[] newBits = Bits.makeBitSet(
-                    Math.max(value + 1, 2 * Bits.getMax(bits)));
-            System.arraycopy(bits, 0, newBits, 0, bits.length);
-            bits = newBits;
-        }
+  /** @inheritDoc */
+  @Override
+  public boolean has(int value) {
+    return (value < Bits.getMax(bits)) && Bits.get(bits, value);
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void merge(IntSet other) {
+    if (other instanceof BitIntSet) {
+      BitIntSet o = (BitIntSet) other;
+      ensureCapacity(Bits.getMax(o.bits) + 1);
+      Bits.or(bits, o.bits);
+    } else if (other instanceof ListIntSet) {
+      ListIntSet o = (ListIntSet) other;
+      int sz = o.ints.size();
+
+      if (sz > 0) {
+        ensureCapacity(o.ints.get(sz - 1));
+      }
+      for (int i = 0; i < o.ints.size(); i++) {
+        Bits.set(bits, o.ints.get(i), true);
+      }
+    } else {
+      IntIterator iter = other.iterator();
+      while (iter.hasNext()) {
+        add(iter.next());
+      }
     }
+  }
 
-    /** @inheritDoc */
-    public void remove(int value) {
-        if (value < Bits.getMax(bits)) {
-            Bits.set(bits, value, false);
-        }
-    }
+  /** @inheritDoc */
+  @Override
+  public int elements() {
+    return Bits.bitCount(bits);
+  }
 
-    /** @inheritDoc */
-    public boolean has(int value) {
-        return (value < Bits.getMax(bits)) && Bits.get(bits, value);
-    }
+  /** @inheritDoc */
+  @Override
+  public IntIterator iterator() {
+    return new IntIterator() {
+      private int idx = Bits.findFirst(bits, 0);
 
-    /** @inheritDoc */
-    public void merge(IntSet other) {
-        if (other instanceof BitIntSet) {
-            BitIntSet o = (BitIntSet) other;
-            ensureCapacity(Bits.getMax(o.bits) + 1);
-            Bits.or(bits, o.bits);
-        } else if (other instanceof ListIntSet) {
-            ListIntSet o = (ListIntSet) other;
-            int sz = o.ints.size();
+      /** @inheritDoc */
+      @Override
+      public boolean hasNext() {
+        return idx >= 0;
+      }
 
-            if (sz > 0) {
-                ensureCapacity(o.ints.get(sz - 1));
-            }
-            for (int i = 0; i < o.ints.size(); i++) {
-                Bits.set(bits, o.ints.get(i), true);
-            }
-        } else {
-            IntIterator iter = other.iterator();
-            while (iter.hasNext()) {
-                add(iter.next());
-            }
-        }
-    }
-
-    /** @inheritDoc */
-    public int elements() {
-        return Bits.bitCount(bits);
-    }
-
-    /** @inheritDoc */
-    public IntIterator iterator() {
-        return new IntIterator() {
-            private int idx = Bits.findFirst(bits, 0);
-
-            /** @inheritDoc */
-            public boolean hasNext() {
-                return idx >= 0;
-            }
-
-            /** @inheritDoc */
-            public int next() {
-                if (!hasNext()) {
-                    throw new NoSuchElementException();
-                }
-
-                int ret = idx;
-
-                idx = Bits.findFirst(bits, idx+1);
-
-                return ret;
-            }
-        };
-    }
-
-    /** @inheritDoc */
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-
-        sb.append('{');
-
-        boolean first = true;
-        for (int i = Bits.findFirst(bits, 0)
-                ; i >= 0
-                ; i = Bits.findFirst(bits, i + 1)) {
-            if (!first) {
-                sb.append(", ");
-            }
-            first = false;
-            sb.append(i);
+      /** @inheritDoc */
+      @Override
+      public int next() {
+        if (!hasNext()) {
+          throw new NoSuchElementException();
         }
 
-        sb.append('}');
+        int ret = idx;
 
-        return sb.toString();
+        idx = Bits.findFirst(bits, idx + 1);
+
+        return ret;
+      }
+    };
+  }
+
+  /** @inheritDoc */
+  @Override
+  public String toString() {
+    StringBuilder sb = new StringBuilder();
+
+    sb.append('{');
+
+    boolean first = true;
+    for (int i = Bits.findFirst(bits, 0); i >= 0; i = Bits.findFirst(bits, i + 1)) {
+      if (!first) {
+        sb.append(", ");
+      }
+      first = false;
+      sb.append(i);
     }
+
+    sb.append('}');
+
+    return sb.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Bits.java b/dx/src/com/android/jack/dx/util/Bits.java
index 629d5cf..ea77735 100644
--- a/dx/src/com/android/jack/dx/util/Bits.java
+++ b/dx/src/com/android/jack/dx/util/Bits.java
@@ -20,217 +20,217 @@
  * Utilities for treating {@code int[]}s as bit sets.
  */
 public final class Bits {
-    /**
-     * This class is uninstantiable.
-     */
-    private Bits() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private Bits() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Constructs a bit set to contain bits up to the given index (exclusive).
+   *
+   * @param max {@code >= 0;} the maximum bit index (exclusive)
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public static int[] makeBitSet(int max) {
+    int size = (max + 0x1f) >> 5;
+    return new int[size];
+  }
+
+  /**
+   * Gets the maximum index (exclusive) for the given bit set.
+   *
+   * @param bits {@code non-null;} bit set in question
+   * @return {@code >= 0;} the maximum index (exclusive) that may be set
+   */
+  public static int getMax(int[] bits) {
+    return bits.length * 0x20;
+  }
+
+  /**
+   * Gets the value of the bit at the given index.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param idx {@code >= 0, < getMax(set);} which bit
+   * @return the value of the indicated bit
+   */
+  public static boolean get(int[] bits, int idx) {
+    int arrayIdx = idx >> 5;
+    int bit = 1 << (idx & 0x1f);
+    return (bits[arrayIdx] & bit) != 0;
+  }
+
+  /**
+   * Sets the given bit to the given value.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param idx {@code >= 0, < getMax(set);} which bit
+   * @param value the new value for the bit
+   */
+  public static void set(int[] bits, int idx, boolean value) {
+    int arrayIdx = idx >> 5;
+    int bit = 1 << (idx & 0x1f);
+
+    if (value) {
+      bits[arrayIdx] |= bit;
+    } else {
+      bits[arrayIdx] &= ~bit;
+    }
+  }
+
+  /**
+   * Sets the given bit to {@code true}.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param idx {@code >= 0, < getMax(set);} which bit
+   */
+  public static void set(int[] bits, int idx) {
+    int arrayIdx = idx >> 5;
+    int bit = 1 << (idx & 0x1f);
+    bits[arrayIdx] |= bit;
+  }
+
+  /**
+   * Sets the given bit to {@code false}.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param idx {@code >= 0, < getMax(set);} which bit
+   */
+  public static void clear(int[] bits, int idx) {
+    int arrayIdx = idx >> 5;
+    int bit = 1 << (idx & 0x1f);
+    bits[arrayIdx] &= ~bit;
+  }
+
+  /**
+   * Returns whether or not the given bit set is empty, that is, whether
+   * no bit is set to {@code true}.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @return {@code true} iff all bits are {@code false}
+   */
+  public static boolean isEmpty(int[] bits) {
+    int len = bits.length;
+
+    for (int i = 0; i < len; i++) {
+      if (bits[i] != 0) {
+        return false;
+      }
     }
 
-    /**
-     * Constructs a bit set to contain bits up to the given index (exclusive).
-     *
-     * @param max {@code >= 0;} the maximum bit index (exclusive)
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public static int[] makeBitSet(int max) {
-        int size = (max + 0x1f) >> 5;
-        return new int[size];
+    return true;
+  }
+
+  /**
+   * Gets the number of bits set to {@code true} in the given bit set.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @return {@code >= 0;} the bit count (aka population count) of the set
+   */
+  public static int bitCount(int[] bits) {
+    int len = bits.length;
+    int count = 0;
+
+    for (int i = 0; i < len; i++) {
+      count += Integer.bitCount(bits[i]);
     }
 
-    /**
-     * Gets the maximum index (exclusive) for the given bit set.
-     *
-     * @param bits {@code non-null;} bit set in question
-     * @return {@code >= 0;} the maximum index (exclusive) that may be set
-     */
-    public static int getMax(int[] bits) {
-        return bits.length * 0x20;
-    }
+    return count;
+  }
 
-    /**
-     * Gets the value of the bit at the given index.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param idx {@code >= 0, < getMax(set);} which bit
-     * @return the value of the indicated bit
-     */
-    public static boolean get(int[] bits, int idx) {
-        int arrayIdx = idx >> 5;
-        int bit = 1 << (idx & 0x1f);
-        return (bits[arrayIdx] & bit) != 0;
-    }
+  /**
+   * Returns whether any bits are set to {@code true} in the
+   * specified range.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param start {@code >= 0;} index of the first bit in the range (inclusive)
+   * @param end {@code >= 0;} index of the last bit in the range (exclusive)
+   * @return {@code true} if any bit is set to {@code true} in
+   * the indicated range
+   */
+  public static boolean anyInRange(int[] bits, int start, int end) {
+    int idx = findFirst(bits, start);
+    return (idx >= 0) && (idx < end);
+  }
 
-    /**
-     * Sets the given bit to the given value.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param idx {@code >= 0, < getMax(set);} which bit
-     * @param value the new value for the bit
-     */
-    public static void set(int[] bits, int idx, boolean value) {
-        int arrayIdx = idx >> 5;
-        int bit = 1 << (idx & 0x1f);
+  /**
+   * Finds the lowest-order bit set at or after the given index in the
+   * given bit set.
+   *
+   * @param bits {@code non-null;} bit set to operate on
+   * @param idx {@code >= 0;} minimum index to return
+   * @return {@code >= -1;} lowest-order bit set at or after {@code idx},
+   * or {@code -1} if there is no appropriate bit index to return
+   */
+  public static int findFirst(int[] bits, int idx) {
+    int len = bits.length;
+    int minBit = idx & 0x1f;
 
-        if (value) {
-            bits[arrayIdx] |= bit;
-        } else {
-            bits[arrayIdx] &= ~bit;
+    for (int arrayIdx = idx >> 5; arrayIdx < len; arrayIdx++) {
+      int word = bits[arrayIdx];
+      if (word != 0) {
+        int bitIdx = findFirst(word, minBit);
+        if (bitIdx >= 0) {
+          return (arrayIdx << 5) + bitIdx;
         }
+      }
+      minBit = 0;
     }
 
-    /**
-     * Sets the given bit to {@code true}.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param idx {@code >= 0, < getMax(set);} which bit
-     */
-    public static void set(int[] bits, int idx) {
-        int arrayIdx = idx >> 5;
-        int bit = 1 << (idx & 0x1f);
-        bits[arrayIdx] |= bit;
+    return -1;
+  }
+
+  /**
+   * Finds the lowest-order bit set at or after the given index in the
+   * given {@code int}.
+   *
+   * @param value the value in question
+   * @param idx 0..31 the minimum bit index to return
+   * @return {@code >= -1;} lowest-order bit set at or after {@code idx},
+   * or {@code -1} if there is no appropriate bit index to return
+   */
+  public static int findFirst(int value, int idx) {
+    value &= ~((1 << idx) - 1); // Mask off too-low bits.
+    int result = Integer.numberOfTrailingZeros(value);
+    return (result == 32) ? -1 : result;
+  }
+
+  /**
+   * Ors bit array {@code b} into bit array {@code a}.
+   * {@code a.length} must be greater than or equal to
+   * {@code b.length}.
+   *
+   * @param a {@code non-null;} int array to be ored with other argument. This
+   * argument is modified.
+   * @param b {@code non-null;} int array to be ored into {@code a}. This
+   * argument is not modified.
+   */
+  public static void or(int[] a, int[] b) {
+    for (int i = 0; i < b.length; i++) {
+      a[i] |= b[i];
     }
+  }
 
-    /**
-     * Sets the given bit to {@code false}.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param idx {@code >= 0, < getMax(set);} which bit
-     */
-    public static void clear(int[] bits, int idx) {
-        int arrayIdx = idx >> 5;
-        int bit = 1 << (idx & 0x1f);
-        bits[arrayIdx] &= ~bit;
-    }
+  public static String toHuman(int[] bits) {
+    StringBuilder sb = new StringBuilder();
 
-    /**
-     * Returns whether or not the given bit set is empty, that is, whether
-     * no bit is set to {@code true}.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @return {@code true} iff all bits are {@code false}
-     */
-    public static boolean isEmpty(int[] bits) {
-        int len = bits.length;
+    boolean needsComma = false;
 
-        for (int i = 0; i < len; i++) {
-            if (bits[i] != 0) {
-                return false;
-            }
+    sb.append('{');
+
+    int bitsLength = 32 * bits.length;
+    for (int i = 0; i < bitsLength; i++) {
+      if (Bits.get(bits, i)) {
+        if (needsComma) {
+          sb.append(',');
         }
-
-        return true;
+        needsComma = true;
+        sb.append(i);
+      }
     }
+    sb.append('}');
 
-    /**
-     * Gets the number of bits set to {@code true} in the given bit set.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @return {@code >= 0;} the bit count (aka population count) of the set
-     */
-    public static int bitCount(int[] bits) {
-        int len = bits.length;
-        int count = 0;
-
-        for (int i = 0; i < len; i++) {
-            count += Integer.bitCount(bits[i]);
-        }
-
-        return count;
-    }
-
-    /**
-     * Returns whether any bits are set to {@code true} in the
-     * specified range.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param start {@code >= 0;} index of the first bit in the range (inclusive)
-     * @param end {@code >= 0;} index of the last bit in the range (exclusive)
-     * @return {@code true} if any bit is set to {@code true} in
-     * the indicated range
-     */
-    public static boolean anyInRange(int[] bits, int start, int end) {
-        int idx = findFirst(bits, start);
-        return (idx >= 0) && (idx < end);
-    }
-
-    /**
-     * Finds the lowest-order bit set at or after the given index in the
-     * given bit set.
-     *
-     * @param bits {@code non-null;} bit set to operate on
-     * @param idx {@code >= 0;} minimum index to return
-     * @return {@code >= -1;} lowest-order bit set at or after {@code idx},
-     * or {@code -1} if there is no appropriate bit index to return
-     */
-    public static int findFirst(int[] bits, int idx) {
-        int len = bits.length;
-        int minBit = idx & 0x1f;
-
-        for (int arrayIdx = idx >> 5; arrayIdx < len; arrayIdx++) {
-            int word = bits[arrayIdx];
-            if (word != 0) {
-                int bitIdx = findFirst(word, minBit);
-                if (bitIdx >= 0) {
-                    return (arrayIdx << 5) + bitIdx;
-                }
-            }
-            minBit = 0;
-        }
-
-        return -1;
-    }
-
-    /**
-     * Finds the lowest-order bit set at or after the given index in the
-     * given {@code int}.
-     *
-     * @param value the value in question
-     * @param idx 0..31 the minimum bit index to return
-     * @return {@code >= -1;} lowest-order bit set at or after {@code idx},
-     * or {@code -1} if there is no appropriate bit index to return
-     */
-    public static int findFirst(int value, int idx) {
-        value &= ~((1 << idx) - 1); // Mask off too-low bits.
-        int result = Integer.numberOfTrailingZeros(value);
-        return (result == 32) ? -1 : result;
-    }
-
-    /**
-     * Ors bit array {@code b} into bit array {@code a}.
-     * {@code a.length} must be greater than or equal to
-     * {@code b.length}.
-     *
-     * @param a {@code non-null;} int array to be ored with other argument. This
-     * argument is modified.
-     * @param b {@code non-null;} int array to be ored into {@code a}. This
-     * argument is not modified.
-     */
-    public static void or(int[] a, int[] b) {
-        for (int i = 0; i < b.length; i++) {
-            a[i] |= b[i];
-        }
-    }
-
-    public static String toHuman(int[] bits) {
-        StringBuilder sb = new StringBuilder();
-
-        boolean needsComma = false;
-
-        sb.append('{');
-
-        int bitsLength = 32 * bits.length;
-        for (int i = 0; i < bitsLength; i++) {
-            if (Bits.get(bits, i)) {
-                if (needsComma) {
-                    sb.append(',');
-                }
-                needsComma = true;
-                sb.append(i);
-            }
-        }
-        sb.append('}');
-
-        return sb.toString();
-    }
+    return sb.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ByteArray.java b/dx/src/com/android/jack/dx/util/ByteArray.java
index b5ff800..e696542 100644
--- a/dx/src/com/android/jack/dx/util/ByteArray.java
+++ b/dx/src/com/android/jack/dx/util/ByteArray.java
@@ -27,335 +27,328 @@
  * <b>Note:</b> Multibyte accessors all use big-endian order.
  */
 public final class ByteArray {
-    /** {@code non-null;} underlying array */
-    private final byte[] bytes;
+  /** {@code non-null;} underlying array */
+  private final byte[] bytes;
 
-    /** {@code >= 0}; start index of the slice (inclusive) */
-    private final int start;
+  /** {@code >= 0}; start index of the slice (inclusive) */
+  private final int start;
 
-    /** {@code >= 0, <= bytes.length}; size computed as
-     * {@code end - start} (in the constructor) */
-    private final int size;
+  /** {@code >= 0, <= bytes.length}; size computed as
+   * {@code end - start} (in the constructor) */
+  private final int size;
 
+  /**
+   * Constructs an instance.
+   *
+   * @param bytes {@code non-null;} the underlying array
+   * @param start {@code >= 0;} start index of the slice (inclusive)
+   * @param end {@code >= start, <= bytes.length;} end index of
+   * the slice (exclusive)
+   */
+  public ByteArray(byte[] bytes, int start, int end) {
+    if (bytes == null) {
+      throw new NullPointerException("bytes == null");
+    }
+
+    if (start < 0) {
+      throw new IllegalArgumentException("start < 0");
+    }
+
+    if (end < start) {
+      throw new IllegalArgumentException("end < start");
+    }
+
+    if (end > bytes.length) {
+      throw new IllegalArgumentException("end > bytes.length");
+    }
+
+    this.bytes = bytes;
+    this.start = start;
+    this.size = end - start;
+  }
+
+  /**
+   * Constructs an instance from an entire {@code byte[]}.
+   *
+   * @param bytes {@code non-null;} the underlying array
+   */
+  public ByteArray(byte[] bytes) {
+    this(bytes, 0, bytes.length);
+  }
+
+  /**
+   * Gets the size of the array, in bytes.
+   *
+   * @return {@code >= 0;} the size
+   */
+  public int size() {
+    return size;
+  }
+
+  /**
+   * Returns a slice (that is, a sub-array) of this instance.
+   *
+   * @param start {@code >= 0;} start index of the slice (inclusive)
+   * @param end {@code >= start, <= size();} end index of
+   * the slice (exclusive)
+   * @return {@code non-null;} the slice
+   */
+  public ByteArray slice(int start, int end) {
+    checkOffsets(start, end);
+    return new ByteArray(bytes, start + this.start, end + this.start);
+  }
+
+  /**
+   * Returns the offset into the given array represented by the given
+   * offset into this instance.
+   *
+   * @param offset offset into this instance
+   * @param bytes {@code non-null;} (alleged) underlying array
+   * @return corresponding offset into {@code bytes}
+   * @throws IllegalArgumentException thrown if {@code bytes} is
+   * not the underlying array of this instance
+   */
+  public int underlyingOffset(int offset, byte[] bytes) {
+    if (bytes != this.bytes) {
+      throw new IllegalArgumentException("wrong bytes");
+    }
+
+    return start + offset;
+  }
+
+  /**
+   * Gets the {@code signed byte} value at a particular offset.
+   *
+   * @param off {@code >= 0, < size();} offset to fetch
+   * @return {@code signed byte} at that offset
+   */
+  public int getByte(int off) {
+    checkOffsets(off, off + 1);
+    return getByte0(off);
+  }
+
+  /**
+   * Gets the {@code signed short} value at a particular offset.
+   *
+   * @param off {@code >= 0, < (size() - 1);} offset to fetch
+   * @return {@code signed short} at that offset
+   */
+  public int getShort(int off) {
+    checkOffsets(off, off + 2);
+    return (getByte0(off) << 8) | getUnsignedByte0(off + 1);
+  }
+
+  /**
+   * Gets the {@code signed int} value at a particular offset.
+   *
+   * @param off {@code >= 0, < (size() - 3);} offset to fetch
+   * @return {@code signed int} at that offset
+   */
+  public int getInt(int off) {
+    checkOffsets(off, off + 4);
+    return (getByte0(off) << 24) | (getUnsignedByte0(off + 1) << 16)
+        | (getUnsignedByte0(off + 2) << 8) | getUnsignedByte0(off + 3);
+  }
+
+  /**
+   * Gets the {@code signed long} value at a particular offset.
+   *
+   * @param off {@code >= 0, < (size() - 7);} offset to fetch
+   * @return {@code signed int} at that offset
+   */
+  public long getLong(int off) {
+    checkOffsets(off, off + 8);
+    int part1 = (getByte0(off) << 24) | (getUnsignedByte0(off + 1) << 16)
+        | (getUnsignedByte0(off + 2) << 8) | getUnsignedByte0(off + 3);
+    int part2 = (getByte0(off + 4) << 24) | (getUnsignedByte0(off + 5) << 16)
+        | (getUnsignedByte0(off + 6) << 8) | getUnsignedByte0(off + 7);
+
+    return (part2 & 0xffffffffL) | ((long) part1) << 32;
+  }
+
+  /**
+   * Gets the {@code unsigned byte} value at a particular offset.
+   *
+   * @param off {@code >= 0, < size();} offset to fetch
+   * @return {@code unsigned byte} at that offset
+   */
+  public int getUnsignedByte(int off) {
+    checkOffsets(off, off + 1);
+    return getUnsignedByte0(off);
+  }
+
+  /**
+   * Gets the {@code unsigned short} value at a particular offset.
+   *
+   * @param off {@code >= 0, < (size() - 1);} offset to fetch
+   * @return {@code unsigned short} at that offset
+   */
+  public int getUnsignedShort(int off) {
+    checkOffsets(off, off + 2);
+    return (getUnsignedByte0(off) << 8) | getUnsignedByte0(off + 1);
+  }
+
+  /**
+   * Copies the contents of this instance into the given raw
+   * {@code byte[]} at the given offset. The given array must be
+   * large enough.
+   *
+   * @param out {@code non-null;} array to hold the output
+   * @param offset {@code non-null;} index into {@code out} for the first
+   * byte of output
+   */
+  public void getBytes(byte[] out, int offset) {
+    if ((out.length - offset) < size) {
+      throw new IndexOutOfBoundsException("(out.length - offset) < " + "size()");
+    }
+
+    System.arraycopy(bytes, start, out, offset, size);
+  }
+
+  /**
+   * Checks a range of offsets for validity, throwing if invalid.
+   *
+   * @param s start offset (inclusive)
+   * @param e end offset (exclusive)
+   */
+  private void checkOffsets(int s, int e) {
+    if ((s < 0) || (e < s) || (e > size)) {
+      throw new IllegalArgumentException("bad range: " + s + ".." + e + "; actual size " + size);
+    }
+  }
+
+  /**
+   * Gets the {@code signed byte} value at the given offset,
+   * without doing any argument checking.
+   *
+   * @param off offset to fetch
+   * @return byte at that offset
+   */
+  private int getByte0(int off) {
+    return bytes[start + off];
+  }
+
+  /**
+   * Gets the {@code unsigned byte} value at the given offset,
+   * without doing any argument checking.
+   *
+   * @param off offset to fetch
+   * @return byte at that offset
+   */
+  private int getUnsignedByte0(int off) {
+    return bytes[start + off] & 0xff;
+  }
+
+  /**
+   * Gets a {@code DataInputStream} that reads from this instance,
+   * with the cursor starting at the beginning of this instance's data.
+   * <b>Note:</b> The returned instance may be cast to {@link #GetCursor}
+   * if needed.
+   *
+   * @return {@code non-null;} an appropriately-constructed
+   * {@code DataInputStream} instance
+   */
+  public MyDataInputStream makeDataInputStream() {
+    return new MyDataInputStream(makeInputStream());
+  }
+
+  /**
+   * Gets a {@code InputStream} that reads from this instance,
+   * with the cursor starting at the beginning of this instance's data.
+   * <b>Note:</b> The returned instance may be cast to {@link #GetCursor}
+   * if needed.
+   *
+   * @return {@code non-null;} an appropriately-constructed
+   * {@code InputStream} instancex
+   */
+  public MyInputStream makeInputStream() {
+    return new MyInputStream();
+  }
+
+  /**
+   * Helper interface that allows one to get the cursor (of a stream).
+   */
+  public interface GetCursor {
     /**
-     * Constructs an instance.
+     * Gets the current cursor.
      *
-     * @param bytes {@code non-null;} the underlying array
-     * @param start {@code >= 0;} start index of the slice (inclusive)
-     * @param end {@code >= start, <= bytes.length;} end index of
-     * the slice (exclusive)
+     * @return {@code 0..size();} the cursor
      */
-    public ByteArray(byte[] bytes, int start, int end) {
-        if (bytes == null) {
-            throw new NullPointerException("bytes == null");
-        }
+    public int getCursor();
+  }
 
-        if (start < 0) {
-            throw new IllegalArgumentException("start < 0");
-        }
+  /**
+   * Helper class for {@link #makeInputStream}, which implements the
+   * stream functionality.
+   */
+  public class MyInputStream extends InputStream {
+    /** 0..size; the cursor */
+    private int cursor;
 
-        if (end < start) {
-            throw new IllegalArgumentException("end < start");
-        }
+    /** 0..size; the mark */
+    private int mark;
 
-        if (end > bytes.length) {
-            throw new IllegalArgumentException("end > bytes.length");
-        }
-
-        this.bytes = bytes;
-        this.start = start;
-        this.size = end - start;
+    public MyInputStream() {
+      cursor = 0;
+      mark = 0;
     }
 
-    /**
-     * Constructs an instance from an entire {@code byte[]}.
-     *
-     * @param bytes {@code non-null;} the underlying array
-     */
-    public ByteArray(byte[] bytes) {
-        this(bytes, 0, bytes.length);
+    @Override
+    public int read() throws IOException {
+      if (cursor >= size) {
+        return -1;
+      }
+
+      int result = getUnsignedByte0(cursor);
+      cursor++;
+      return result;
     }
 
-    /**
-     * Gets the size of the array, in bytes.
-     *
-     * @return {@code >= 0;} the size
-     */
-    public int size() {
-        return size;
+    @Override
+    public int read(byte[] arr, int offset, int length) {
+      if ((offset + length) > arr.length) {
+        length = arr.length - offset;
+      }
+
+      int maxLength = size - cursor;
+      if (length > maxLength) {
+        length = maxLength;
+      }
+
+      System.arraycopy(bytes, cursor + start, arr, offset, length);
+      cursor += length;
+      return length;
     }
 
-    /**
-     * Returns a slice (that is, a sub-array) of this instance.
-     *
-     * @param start {@code >= 0;} start index of the slice (inclusive)
-     * @param end {@code >= start, <= size();} end index of
-     * the slice (exclusive)
-     * @return {@code non-null;} the slice
-     */
-    public ByteArray slice(int start, int end) {
-        checkOffsets(start, end);
-        return new ByteArray(bytes, start + this.start, end + this.start);
+    @Override
+    public int available() {
+      return size - cursor;
     }
 
-    /**
-     * Returns the offset into the given array represented by the given
-     * offset into this instance.
-     *
-     * @param offset offset into this instance
-     * @param bytes {@code non-null;} (alleged) underlying array
-     * @return corresponding offset into {@code bytes}
-     * @throws IllegalArgumentException thrown if {@code bytes} is
-     * not the underlying array of this instance
-     */
-    public int underlyingOffset(int offset, byte[] bytes) {
-        if (bytes != this.bytes) {
-            throw new IllegalArgumentException("wrong bytes");
-        }
-
-        return start + offset;
+    @Override
+    public void mark(int reserve) {
+      mark = cursor;
     }
 
-    /**
-     * Gets the {@code signed byte} value at a particular offset.
-     *
-     * @param off {@code >= 0, < size();} offset to fetch
-     * @return {@code signed byte} at that offset
-     */
-    public int getByte(int off) {
-        checkOffsets(off, off + 1);
-        return getByte0(off);
+    @Override
+    public void reset() {
+      cursor = mark;
     }
 
-    /**
-     * Gets the {@code signed short} value at a particular offset.
-     *
-     * @param off {@code >= 0, < (size() - 1);} offset to fetch
-     * @return {@code signed short} at that offset
-     */
-    public int getShort(int off) {
-        checkOffsets(off, off + 2);
-        return (getByte0(off) << 8) | getUnsignedByte0(off + 1);
+    @Override
+    public boolean markSupported() {
+      return true;
     }
+  }
 
-    /**
-     * Gets the {@code signed int} value at a particular offset.
-     *
-     * @param off {@code >= 0, < (size() - 3);} offset to fetch
-     * @return {@code signed int} at that offset
-     */
-    public int getInt(int off) {
-        checkOffsets(off, off + 4);
-        return (getByte0(off) << 24) |
-            (getUnsignedByte0(off + 1) << 16) |
-            (getUnsignedByte0(off + 2) << 8) |
-            getUnsignedByte0(off + 3);
+  /**
+   * Helper class for {@link #makeDataInputStream}. This is used
+   * simply so that the cursor of a wrapped {@link #MyInputStream}
+   * instance may be easily determined.
+   */
+  public static class MyDataInputStream extends DataInputStream {
+    public MyDataInputStream(MyInputStream wrapped) {
+      super(wrapped);
     }
-
-    /**
-     * Gets the {@code signed long} value at a particular offset.
-     *
-     * @param off {@code >= 0, < (size() - 7);} offset to fetch
-     * @return {@code signed int} at that offset
-     */
-    public long getLong(int off) {
-        checkOffsets(off, off + 8);
-        int part1 = (getByte0(off) << 24) |
-            (getUnsignedByte0(off + 1) << 16) |
-            (getUnsignedByte0(off + 2) << 8) |
-            getUnsignedByte0(off + 3);
-        int part2 = (getByte0(off + 4) << 24) |
-            (getUnsignedByte0(off + 5) << 16) |
-            (getUnsignedByte0(off + 6) << 8) |
-            getUnsignedByte0(off + 7);
-
-        return (part2 & 0xffffffffL) | ((long) part1) << 32;
-    }
-
-    /**
-     * Gets the {@code unsigned byte} value at a particular offset.
-     *
-     * @param off {@code >= 0, < size();} offset to fetch
-     * @return {@code unsigned byte} at that offset
-     */
-    public int getUnsignedByte(int off) {
-        checkOffsets(off, off + 1);
-        return getUnsignedByte0(off);
-    }
-
-    /**
-     * Gets the {@code unsigned short} value at a particular offset.
-     *
-     * @param off {@code >= 0, < (size() - 1);} offset to fetch
-     * @return {@code unsigned short} at that offset
-     */
-    public int getUnsignedShort(int off) {
-        checkOffsets(off, off + 2);
-        return (getUnsignedByte0(off) << 8) | getUnsignedByte0(off + 1);
-    }
-
-    /**
-     * Copies the contents of this instance into the given raw
-     * {@code byte[]} at the given offset. The given array must be
-     * large enough.
-     *
-     * @param out {@code non-null;} array to hold the output
-     * @param offset {@code non-null;} index into {@code out} for the first
-     * byte of output
-     */
-    public void getBytes(byte[] out, int offset) {
-        if ((out.length - offset) < size) {
-            throw new IndexOutOfBoundsException("(out.length - offset) < " +
-                                                "size()");
-        }
-
-        System.arraycopy(bytes, start, out, offset, size);
-    }
-
-    /**
-     * Checks a range of offsets for validity, throwing if invalid.
-     *
-     * @param s start offset (inclusive)
-     * @param e end offset (exclusive)
-     */
-    private void checkOffsets(int s, int e) {
-        if ((s < 0) || (e < s) || (e > size)) {
-            throw new IllegalArgumentException("bad range: " + s + ".." + e +
-                                               "; actual size " + size);
-        }
-    }
-
-    /**
-     * Gets the {@code signed byte} value at the given offset,
-     * without doing any argument checking.
-     *
-     * @param off offset to fetch
-     * @return byte at that offset
-     */
-    private int getByte0(int off) {
-        return bytes[start + off];
-    }
-
-    /**
-     * Gets the {@code unsigned byte} value at the given offset,
-     * without doing any argument checking.
-     *
-     * @param off offset to fetch
-     * @return byte at that offset
-     */
-    private int getUnsignedByte0(int off) {
-        return bytes[start + off] & 0xff;
-    }
-
-    /**
-     * Gets a {@code DataInputStream} that reads from this instance,
-     * with the cursor starting at the beginning of this instance's data.
-     * <b>Note:</b> The returned instance may be cast to {@link #GetCursor}
-     * if needed.
-     *
-     * @return {@code non-null;} an appropriately-constructed
-     * {@code DataInputStream} instance
-     */
-    public MyDataInputStream makeDataInputStream() {
-        return new MyDataInputStream(makeInputStream());
-    }
-
-    /**
-     * Gets a {@code InputStream} that reads from this instance,
-     * with the cursor starting at the beginning of this instance's data.
-     * <b>Note:</b> The returned instance may be cast to {@link #GetCursor}
-     * if needed.
-     *
-     * @return {@code non-null;} an appropriately-constructed
-     * {@code InputStream} instancex
-     */
-    public MyInputStream makeInputStream() {
-        return new MyInputStream();
-    }
-
-    /**
-     * Helper interface that allows one to get the cursor (of a stream).
-     */
-    public interface GetCursor {
-        /**
-         * Gets the current cursor.
-         *
-         * @return {@code 0..size();} the cursor
-         */
-        public int getCursor();
-    }
-
-    /**
-     * Helper class for {@link #makeInputStream}, which implements the
-     * stream functionality.
-     */
-    public class MyInputStream extends InputStream {
-        /** 0..size; the cursor */
-        private int cursor;
-
-        /** 0..size; the mark */
-        private int mark;
-
-        public MyInputStream() {
-            cursor = 0;
-            mark = 0;
-        }
-
-        public int read() throws IOException {
-            if (cursor >= size) {
-                return -1;
-            }
-
-            int result = getUnsignedByte0(cursor);
-            cursor++;
-            return result;
-        }
-
-        public int read(byte[] arr, int offset, int length) {
-            if ((offset + length) > arr.length) {
-                length = arr.length - offset;
-            }
-
-            int maxLength = size - cursor;
-            if (length > maxLength) {
-                length = maxLength;
-            }
-
-            System.arraycopy(bytes, cursor + start, arr, offset, length);
-            cursor += length;
-            return length;
-        }
-
-        public int available() {
-            return size - cursor;
-        }
-
-        public void mark(int reserve) {
-            mark = cursor;
-        }
-
-        public void reset() {
-            cursor = mark;
-        }
-
-        public boolean markSupported() {
-            return true;
-        }
-    }
-
-    /**
-     * Helper class for {@link #makeDataInputStream}. This is used
-     * simply so that the cursor of a wrapped {@link #MyInputStream}
-     * instance may be easily determined.
-     */
-    public static class MyDataInputStream extends DataInputStream {
-        /** {@code non-null;} the underlying {@link #MyInputStream} */
-        private final MyInputStream wrapped;
-
-        public MyDataInputStream(MyInputStream wrapped) {
-            super(wrapped);
-
-            this.wrapped = wrapped;
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ByteArrayAnnotatedOutput.java b/dx/src/com/android/jack/dx/util/ByteArrayAnnotatedOutput.java
index 09174e0..fcfab9f 100644
--- a/dx/src/com/android/jack/dx/util/ByteArrayAnnotatedOutput.java
+++ b/dx/src/com/android/jack/dx/util/ByteArrayAnnotatedOutput.java
@@ -27,606 +27,622 @@
  * <p><b>Note:</b> As per the {@link Output} interface, multi-byte
  * writes all use little-endian order.</p>
  */
-public final class ByteArrayAnnotatedOutput
-        implements AnnotatedOutput, ByteOutput {
-    /** default size for stretchy instances */
-    private static final int DEFAULT_SIZE = 1000;
+public final class ByteArrayAnnotatedOutput implements AnnotatedOutput, ByteOutput {
+  /** default size for stretchy instances */
+  private static final int DEFAULT_SIZE = 1000;
 
-    /**
-     * whether the instance is stretchy, that is, whether its array
-     * may be resized to increase capacity
+  /**
+   * whether the instance is stretchy, that is, whether its array
+   * may be resized to increase capacity
+   */
+  private final boolean stretchy;
+
+  /** {@code non-null;} the data itself */
+  private byte[] data;
+
+  /** {@code >= 0;} current output cursor */
+  private int cursor;
+
+  /** whether annotations are to be verbose */
+  private boolean verbose;
+
+  /**
+   * {@code null-ok;} list of annotations, or {@code null} if this instance
+   * isn't keeping them
+   */
+  private ArrayList<Annotation> annotations;
+
+  /** {@code >= 40 (if used);} the desired maximum annotation width */
+  private int annotationWidth;
+
+  /**
+   * {@code >= 8 (if used);} the number of bytes of hex output to use
+   * in annotations
+   */
+  private int hexCols;
+
+  /**
+   * Constructs an instance with a fixed maximum size. Note that the
+   * given array is the only one that will be used to store data. In
+   * particular, no reallocation will occur in order to expand the
+   * capacity of the resulting instance. Also, the constructed
+   * instance does not keep annotations by default.
+   *
+   * @param data {@code non-null;} data array to use for output
+   */
+  public ByteArrayAnnotatedOutput(byte[] data) {
+    this(data, false);
+  }
+
+  /**
+   * Constructs a "stretchy" instance. The underlying array may be
+   * reallocated. The constructed instance does not keep annotations
+   * by default.
+   */
+  public ByteArrayAnnotatedOutput() {
+    this(DEFAULT_SIZE);
+  }
+
+  /**
+   * Constructs a "stretchy" instance with initial size {@code size}. The
+   * underlying array may be reallocated. The constructed instance does not
+   * keep annotations by default.
+   */
+  public ByteArrayAnnotatedOutput(int size) {
+    this(new byte[size], true);
+  }
+
+  /**
+   * Internal constructor.
+   *
+   * @param data {@code non-null;} data array to use for output
+   * @param stretchy whether the instance is to be stretchy
+   */
+  private ByteArrayAnnotatedOutput(byte[] data, boolean stretchy) {
+    if (data == null) {
+      throw new NullPointerException("data == null");
+    }
+
+    this.stretchy = stretchy;
+    this.data = data;
+    this.cursor = 0;
+    this.verbose = false;
+    this.annotations = null;
+    this.annotationWidth = 0;
+    this.hexCols = 0;
+  }
+
+  /**
+   * Gets the underlying {@code byte[]} of this instance, which
+   * may be larger than the number of bytes written
+   *
+   * @see #toByteArray
+   *
+   * @return {@code non-null;} the {@code byte[]}
+   */
+  public byte[] getArray() {
+    return data;
+  }
+
+  /**
+   * Constructs and returns a new {@code byte[]} that contains
+   * the written contents exactly (that is, with no extra unwritten
+   * bytes at the end).
+   *
+   * @see #getArray
+   *
+   * @return {@code non-null;} an appropriately-constructed array
+   */
+  public byte[] toByteArray() {
+    byte[] result = new byte[cursor];
+    System.arraycopy(data, 0, result, 0, cursor);
+    return result;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getCursor() {
+    return cursor;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void assertCursor(int expectedCursor) {
+    if (cursor != expectedCursor) {
+      throw new ExceptionWithContext(
+          "expected cursor " + expectedCursor + "; actual value: " + cursor);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeByte(int value) {
+    int writeAt = cursor;
+    int end = writeAt + 1;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    data[writeAt] = (byte) value;
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeShort(int value) {
+    int writeAt = cursor;
+    int end = writeAt + 2;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    data[writeAt] = (byte) value;
+    data[writeAt + 1] = (byte) (value >> 8);
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeInt(int value) {
+    int writeAt = cursor;
+    int end = writeAt + 4;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    data[writeAt] = (byte) value;
+    data[writeAt + 1] = (byte) (value >> 8);
+    data[writeAt + 2] = (byte) (value >> 16);
+    data[writeAt + 3] = (byte) (value >> 24);
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeLong(long value) {
+    int writeAt = cursor;
+    int end = writeAt + 8;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    int half = (int) value;
+    data[writeAt] = (byte) half;
+    data[writeAt + 1] = (byte) (half >> 8);
+    data[writeAt + 2] = (byte) (half >> 16);
+    data[writeAt + 3] = (byte) (half >> 24);
+
+    half = (int) (value >> 32);
+    data[writeAt + 4] = (byte) half;
+    data[writeAt + 5] = (byte) (half >> 8);
+    data[writeAt + 6] = (byte) (half >> 16);
+    data[writeAt + 7] = (byte) (half >> 24);
+
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeUleb128(int value) {
+    if (stretchy) {
+      ensureCapacity(cursor + 5); // pessimistic
+    }
+    int cursorBefore = cursor;
+    Leb128Utils.writeUnsignedLeb128(this, value);
+    return (cursor - cursorBefore);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int writeSleb128(int value) {
+    if (stretchy) {
+      ensureCapacity(cursor + 5); // pessimistic
+    }
+    int cursorBefore = cursor;
+    Leb128Utils.writeSignedLeb128(this, value);
+    return (cursor - cursorBefore);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void write(ByteArray bytes) {
+    int blen = bytes.size();
+    int writeAt = cursor;
+    int end = writeAt + blen;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    bytes.getBytes(data, writeAt);
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void write(byte[] bytes, int offset, int length) {
+    int writeAt = cursor;
+    int end = writeAt + length;
+    int bytesEnd = offset + length;
+
+    // twos-complement math trick: ((x < 0) || (y < 0)) <=> ((x|y) < 0)
+    if (((offset | length | end) < 0) || (bytesEnd > bytes.length)) {
+      throw new IndexOutOfBoundsException(
+          "bytes.length " + bytes.length + "; " + offset + "..!" + end);
+    }
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    System.arraycopy(bytes, offset, data, writeAt, length);
+    cursor = end;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void write(byte[] bytes) {
+    write(bytes, 0, bytes.length);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void writeZeroes(int count) {
+    if (count < 0) {
+      throw new IllegalArgumentException("count < 0");
+    }
+
+    int end = cursor + count;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    /*
+     * There is no need to actually write zeroes, since the array is
+     * already preinitialized with zeroes.
      */
-    private final boolean stretchy;
 
-    /** {@code non-null;} the data itself */
-    private byte[] data;
+cursor = end;
+  }
 
-    /** {@code >= 0;} current output cursor */
-    private int cursor;
+  /** {@inheritDoc} */
+  @Override
+  public void alignTo(int alignment) {
+    int mask = alignment - 1;
 
-    /** whether annotations are to be verbose */
-    private boolean verbose;
+    if ((alignment < 0) || ((mask & alignment) != 0)) {
+      throw new IllegalArgumentException("bogus alignment");
+    }
 
-    /**
-     * {@code null-ok;} list of annotations, or {@code null} if this instance
-     * isn't keeping them
+    int end = (cursor + mask) & ~mask;
+
+    if (stretchy) {
+      ensureCapacity(end);
+    } else if (end > data.length) {
+      throwBounds();
+      return;
+    }
+
+    /*
+     * There is no need to actually write zeroes, since the array is
+     * already preinitialized with zeroes.
      */
-    private ArrayList<Annotation> annotations;
 
-    /** {@code >= 40 (if used);} the desired maximum annotation width */
-    private int annotationWidth;
+cursor = end;
+  }
 
-    /**
-     * {@code >= 8 (if used);} the number of bytes of hex output to use
-     * in annotations
-     */
-    private int hexCols;
+  /** {@inheritDoc} */
+  @Override
+  public boolean annotates() {
+    return (annotations != null);
+  }
 
-    /**
-     * Constructs an instance with a fixed maximum size. Note that the
-     * given array is the only one that will be used to store data. In
-     * particular, no reallocation will occur in order to expand the
-     * capacity of the resulting instance. Also, the constructed
-     * instance does not keep annotations by default.
-     *
-     * @param data {@code non-null;} data array to use for output
-     */
-    public ByteArrayAnnotatedOutput(byte[] data) {
-        this(data, false);
+  /** {@inheritDoc} */
+  @Override
+  public boolean isVerbose() {
+    return verbose;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void annotate(String msg) {
+    if (annotations == null) {
+      return;
     }
 
-    /**
-     * Constructs a "stretchy" instance. The underlying array may be
-     * reallocated. The constructed instance does not keep annotations
-     * by default.
-     */
-    public ByteArrayAnnotatedOutput() {
-        this(DEFAULT_SIZE);
+    endAnnotation();
+    annotations.add(new Annotation(cursor, msg));
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void annotate(int amt, String msg) {
+    if (annotations == null) {
+      return;
     }
 
-    /**
-     * Constructs a "stretchy" instance with initial size {@code size}. The
-     * underlying array may be reallocated. The constructed instance does not
-     * keep annotations by default.
-     */
-    public ByteArrayAnnotatedOutput(int size) {
-        this(new byte[size], true);
+    endAnnotation();
+
+    int asz = annotations.size();
+    int lastEnd = (asz == 0) ? 0 : annotations.get(asz - 1).getEnd();
+    int startAt;
+
+    if (lastEnd <= cursor) {
+      startAt = cursor;
+    } else {
+      startAt = lastEnd;
     }
 
-    /**
-     * Internal constructor.
-     *
-     * @param data {@code non-null;} data array to use for output
-     * @param stretchy whether the instance is to be stretchy
-     */
-    private ByteArrayAnnotatedOutput(byte[] data, boolean stretchy) {
-        if (data == null) {
-            throw new NullPointerException("data == null");
-        }
+    annotations.add(new Annotation(startAt, startAt + amt, msg));
+  }
 
-        this.stretchy = stretchy;
-        this.data = data;
-        this.cursor = 0;
-        this.verbose = false;
-        this.annotations = null;
-        this.annotationWidth = 0;
-        this.hexCols = 0;
+  /** {@inheritDoc} */
+  @Override
+  public void endAnnotation() {
+    if (annotations == null) {
+      return;
     }
 
-    /**
-     * Gets the underlying {@code byte[]} of this instance, which
-     * may be larger than the number of bytes written
-     *
-     * @see #toByteArray
-     *
-     * @return {@code non-null;} the {@code byte[]}
-     */
-    public byte[] getArray() {
-        return data;
+    int sz = annotations.size();
+
+    if (sz != 0) {
+      annotations.get(sz - 1).setEndIfUnset(cursor);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int getAnnotationWidth() {
+    int leftWidth = 8 + (hexCols * 2) + (hexCols / 2);
+
+    return annotationWidth - leftWidth;
+  }
+
+  /**
+   * Indicates that this instance should keep annotations. This method may
+   * be called only once per instance, and only before any data has been
+   * written to the it.
+   *
+   * @param annotationWidth {@code >= 40;} the desired maximum annotation width
+   * @param verbose whether or not to indicate verbose annotations
+   */
+  public void enableAnnotations(int annotationWidth, boolean verbose) {
+    if ((annotations != null) || (cursor != 0)) {
+      throw new RuntimeException("cannot enable annotations");
     }
 
-    /**
-     * Constructs and returns a new {@code byte[]} that contains
-     * the written contents exactly (that is, with no extra unwritten
-     * bytes at the end).
-     *
-     * @see #getArray
-     *
-     * @return {@code non-null;} an appropriately-constructed array
-     */
-    public byte[] toByteArray() {
-        byte[] result = new byte[cursor];
-        System.arraycopy(data, 0, result, 0, cursor);
-        return result;
+    if (annotationWidth < 40) {
+      throw new IllegalArgumentException("annotationWidth < 40");
     }
 
-    /** {@inheritDoc} */
-    public int getCursor() {
-        return cursor;
+    int hexCols = (((annotationWidth - 7) / 15) + 1) & ~1;
+    if (hexCols < 6) {
+      hexCols = 6;
+    } else if (hexCols > 10) {
+      hexCols = 10;
     }
 
-    /** {@inheritDoc} */
-    public void assertCursor(int expectedCursor) {
-        if (cursor != expectedCursor) {
-            throw new ExceptionWithContext("expected cursor " +
-                    expectedCursor + "; actual value: " + cursor);
-        }
-    }
+    this.annotations = new ArrayList<Annotation>(1000);
+    this.annotationWidth = annotationWidth;
+    this.hexCols = hexCols;
+    this.verbose = verbose;
+  }
 
-    /** {@inheritDoc} */
-    public void writeByte(int value) {
-        int writeAt = cursor;
-        int end = writeAt + 1;
+  /**
+   * Finishes up annotation processing. This closes off any open
+   * annotations and removes annotations that don't refer to written
+   * data.
+   */
+  public void finishAnnotating() {
+    // Close off the final annotation, if any.
+    endAnnotation();
 
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        data[writeAt] = (byte) value;
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void writeShort(int value) {
-        int writeAt = cursor;
-        int end = writeAt + 2;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        data[writeAt] = (byte) value;
-        data[writeAt + 1] = (byte) (value >> 8);
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void writeInt(int value) {
-        int writeAt = cursor;
-        int end = writeAt + 4;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        data[writeAt] = (byte) value;
-        data[writeAt + 1] = (byte) (value >> 8);
-        data[writeAt + 2] = (byte) (value >> 16);
-        data[writeAt + 3] = (byte) (value >> 24);
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void writeLong(long value) {
-        int writeAt = cursor;
-        int end = writeAt + 8;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        int half = (int) value;
-        data[writeAt] = (byte) half;
-        data[writeAt + 1] = (byte) (half >> 8);
-        data[writeAt + 2] = (byte) (half >> 16);
-        data[writeAt + 3] = (byte) (half >> 24);
-
-        half = (int) (value >> 32);
-        data[writeAt + 4] = (byte) half;
-        data[writeAt + 5] = (byte) (half >> 8);
-        data[writeAt + 6] = (byte) (half >> 16);
-        data[writeAt + 7] = (byte) (half >> 24);
-
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public int writeUleb128(int value) {
-        if (stretchy) {
-            ensureCapacity(cursor + 5); // pessimistic
-        }
-        int cursorBefore = cursor;
-        Leb128Utils.writeUnsignedLeb128(this, value);
-        return (cursor - cursorBefore);
-    }
-
-    /** {@inheritDoc} */
-    public int writeSleb128(int value) {
-        if (stretchy) {
-            ensureCapacity(cursor + 5); // pessimistic
-        }
-        int cursorBefore = cursor;
-        Leb128Utils.writeSignedLeb128(this, value);
-        return (cursor - cursorBefore);
-    }
-
-    /** {@inheritDoc} */
-    public void write(ByteArray bytes) {
-        int blen = bytes.size();
-        int writeAt = cursor;
-        int end = writeAt + blen;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        bytes.getBytes(data, writeAt);
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void write(byte[] bytes, int offset, int length) {
-        int writeAt = cursor;
-        int end = writeAt + length;
-        int bytesEnd = offset + length;
-
-        // twos-complement math trick: ((x < 0) || (y < 0)) <=> ((x|y) < 0)
-        if (((offset | length | end) < 0) || (bytesEnd > bytes.length)) {
-            throw new IndexOutOfBoundsException("bytes.length " +
-                                                bytes.length + "; " +
-                                                offset + "..!" + end);
-        }
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        System.arraycopy(bytes, offset, data, writeAt, length);
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void write(byte[] bytes) {
-        write(bytes, 0, bytes.length);
-    }
-
-    /** {@inheritDoc} */
-    public void writeZeroes(int count) {
-        if (count < 0) {
-            throw new IllegalArgumentException("count < 0");
-        }
-
-        int end = cursor + count;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        /*
-         * There is no need to actually write zeroes, since the array is
-         * already preinitialized with zeroes.
-         */
-
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public void alignTo(int alignment) {
-        int mask = alignment - 1;
-
-        if ((alignment < 0) || ((mask & alignment) != 0)) {
-            throw new IllegalArgumentException("bogus alignment");
-        }
-
-        int end = (cursor + mask) & ~mask;
-
-        if (stretchy) {
-            ensureCapacity(end);
-        } else if (end > data.length) {
-            throwBounds();
-            return;
-        }
-
-        /*
-         * There is no need to actually write zeroes, since the array is
-         * already preinitialized with zeroes.
-         */
-
-        cursor = end;
-    }
-
-    /** {@inheritDoc} */
-    public boolean annotates() {
-        return (annotations != null);
-    }
-
-    /** {@inheritDoc} */
-    public boolean isVerbose() {
-        return verbose;
-    }
-
-    /** {@inheritDoc} */
-    public void annotate(String msg) {
-        if (annotations == null) {
-            return;
-        }
-
-        endAnnotation();
-        annotations.add(new Annotation(cursor, msg));
-    }
-
-    /** {@inheritDoc} */
-    public void annotate(int amt, String msg) {
-        if (annotations == null) {
-            return;
-        }
-
-        endAnnotation();
-
-        int asz = annotations.size();
-        int lastEnd = (asz == 0) ? 0 : annotations.get(asz - 1).getEnd();
-        int startAt;
-
-        if (lastEnd <= cursor) {
-            startAt = cursor;
+    // Remove annotations that refer to unwritten data.
+    if (annotations != null) {
+      int asz = annotations.size();
+      while (asz > 0) {
+        Annotation last = annotations.get(asz - 1);
+        if (last.getStart() > cursor) {
+          annotations.remove(asz - 1);
+          asz--;
+        } else if (last.getEnd() > cursor) {
+          last.setEnd(cursor);
+          break;
         } else {
-            startAt = lastEnd;
+          break;
         }
+      }
+    }
+  }
 
-        annotations.add(new Annotation(startAt, startAt + amt, msg));
+  /**
+   * Writes the annotated content of this instance to the given writer.
+   *
+   * @param out {@code non-null;} where to write to
+   */
+  public void writeAnnotationsTo(Writer out) throws IOException {
+    int width2 = getAnnotationWidth();
+    int width1 = annotationWidth - width2 - 1;
+
+    TwoColumnOutput twoc = new TwoColumnOutput(out, width1, width2, "|");
+    Writer left = twoc.getLeft();
+    Writer right = twoc.getRight();
+    int leftAt = 0; // left-hand byte output cursor
+    int rightAt = 0; // right-hand annotation index
+    int rightSz = annotations.size();
+
+    while ((leftAt < cursor) && (rightAt < rightSz)) {
+      Annotation a = annotations.get(rightAt);
+      int start = a.getStart();
+      int end;
+      String text;
+
+      if (leftAt < start) {
+        // This is an area with no annotation.
+        end = start;
+        start = leftAt;
+        text = "";
+      } else {
+        // This is an area with an annotation.
+        end = a.getEnd();
+        text = a.getText();
+        rightAt++;
+      }
+
+      left.write(Hex.dump(data, start, end - start, start, hexCols, 6));
+      right.write(text);
+      twoc.flush();
+      leftAt = end;
     }
 
-    /** {@inheritDoc} */
-    public void endAnnotation() {
-        if (annotations == null) {
-            return;
-        }
-
-        int sz = annotations.size();
-
-        if (sz != 0) {
-            annotations.get(sz - 1).setEndIfUnset(cursor);
-        }
+    if (leftAt < cursor) {
+      // There is unannotated output at the end.
+      left.write(Hex.dump(data, leftAt, cursor - leftAt, leftAt, hexCols, 6));
     }
 
-    /** {@inheritDoc} */
-    public int getAnnotationWidth() {
-        int leftWidth = 8 + (hexCols * 2) + (hexCols / 2);
-
-        return annotationWidth - leftWidth;
+    while (rightAt < rightSz) {
+      // There are zero-byte annotations at the end.
+      right.write(annotations.get(rightAt).getText());
+      rightAt++;
     }
 
+    twoc.flush();
+  }
+
+  /**
+   * Throws the excpetion for when an attempt is made to write past the
+   * end of the instance.
+   */
+  private static void throwBounds() {
+    throw new IndexOutOfBoundsException("attempt to write past the end");
+  }
+
+  /**
+   * Reallocates the underlying array if necessary. Calls to this method
+   * should be guarded by a test of {@link #stretchy}.
+   *
+   * @param desiredSize {@code >= 0;} the desired minimum total size of the array
+   */
+  private void ensureCapacity(int desiredSize) {
+    if (data.length < desiredSize) {
+      byte[] newData = new byte[desiredSize * 2 + 1000];
+      System.arraycopy(data, 0, newData, 0, cursor);
+      data = newData;
+    }
+  }
+
+  /**
+   * Annotation on output.
+   */
+  private static class Annotation {
+    /** {@code >= 0;} start of annotated range (inclusive) */
+    private final int start;
+
     /**
-     * Indicates that this instance should keep annotations. This method may
-     * be called only once per instance, and only before any data has been
-     * written to the it.
+     * {@code >= 0;} end of annotated range (exclusive);
+     * {@code Integer.MAX_VALUE} if unclosed
+     */
+    private int end;
+
+    /** {@code non-null;} annotation text */
+    private final String text;
+
+    /**
+     * Constructs an instance.
      *
-     * @param annotationWidth {@code >= 40;} the desired maximum annotation width
-     * @param verbose whether or not to indicate verbose annotations
+     * @param start {@code >= 0;} start of annotated range
+     * @param end {@code >= start;} end of annotated range (exclusive) or
+     * {@code Integer.MAX_VALUE} if unclosed
+     * @param text {@code non-null;} annotation text
      */
-    public void enableAnnotations(int annotationWidth, boolean verbose) {
-        if ((annotations != null) || (cursor != 0)) {
-            throw new RuntimeException("cannot enable annotations");
-        }
-
-        if (annotationWidth < 40) {
-            throw new IllegalArgumentException("annotationWidth < 40");
-        }
-
-        int hexCols = (((annotationWidth - 7) / 15) + 1) & ~1;
-        if (hexCols < 6) {
-            hexCols = 6;
-        } else if (hexCols > 10) {
-            hexCols = 10;
-        }
-
-        this.annotations = new ArrayList<Annotation>(1000);
-        this.annotationWidth = annotationWidth;
-        this.hexCols = hexCols;
-        this.verbose = verbose;
+    public Annotation(int start, int end, String text) {
+      this.start = start;
+      this.end = end;
+      this.text = text;
     }
 
     /**
-     * Finishes up annotation processing. This closes off any open
-     * annotations and removes annotations that don't refer to written
-     * data.
-     */
-    public void finishAnnotating() {
-        // Close off the final annotation, if any.
-        endAnnotation();
-
-        // Remove annotations that refer to unwritten data.
-        if (annotations != null) {
-            int asz = annotations.size();
-            while (asz > 0) {
-                Annotation last = annotations.get(asz - 1);
-                if (last.getStart() > cursor) {
-                    annotations.remove(asz - 1);
-                    asz--;
-                } else if (last.getEnd() > cursor) {
-                    last.setEnd(cursor);
-                    break;
-                } else {
-                    break;
-                }
-            }
-        }
-    }
-
-    /**
-     * Writes the annotated content of this instance to the given writer.
+     * Constructs an instance. It is initally unclosed.
      *
-     * @param out {@code non-null;} where to write to
+     * @param start {@code >= 0;} start of annotated range
+     * @param text {@code non-null;} annotation text
      */
-    public void writeAnnotationsTo(Writer out) throws IOException {
-        int width2 = getAnnotationWidth();
-        int width1 = annotationWidth - width2 - 1;
-
-        TwoColumnOutput twoc = new TwoColumnOutput(out, width1, width2, "|");
-        Writer left = twoc.getLeft();
-        Writer right = twoc.getRight();
-        int leftAt = 0; // left-hand byte output cursor
-        int rightAt = 0; // right-hand annotation index
-        int rightSz = annotations.size();
-
-        while ((leftAt < cursor) && (rightAt < rightSz)) {
-            Annotation a = annotations.get(rightAt);
-            int start = a.getStart();
-            int end;
-            String text;
-
-            if (leftAt < start) {
-                // This is an area with no annotation.
-                end = start;
-                start = leftAt;
-                text = "";
-            } else {
-                // This is an area with an annotation.
-                end = a.getEnd();
-                text = a.getText();
-                rightAt++;
-            }
-
-            left.write(Hex.dump(data, start, end - start, start, hexCols, 6));
-            right.write(text);
-            twoc.flush();
-            leftAt = end;
-        }
-
-        if (leftAt < cursor) {
-            // There is unannotated output at the end.
-            left.write(Hex.dump(data, leftAt, cursor - leftAt, leftAt,
-                                hexCols, 6));
-        }
-
-        while (rightAt < rightSz) {
-            // There are zero-byte annotations at the end.
-            right.write(annotations.get(rightAt).getText());
-            rightAt++;
-        }
-
-        twoc.flush();
+    public Annotation(int start, String text) {
+      this(start, Integer.MAX_VALUE, text);
     }
 
     /**
-     * Throws the excpetion for when an attempt is made to write past the
-     * end of the instance.
-     */
-    private static void throwBounds() {
-        throw new IndexOutOfBoundsException("attempt to write past the end");
-    }
-
-    /**
-     * Reallocates the underlying array if necessary. Calls to this method
-     * should be guarded by a test of {@link #stretchy}.
+     * Sets the end as given, but only if the instance is unclosed;
+     * otherwise, do nothing.
      *
-     * @param desiredSize {@code >= 0;} the desired minimum total size of the array
+     * @param end {@code >= start;} the end
      */
-    private void ensureCapacity(int desiredSize) {
-        if (data.length < desiredSize) {
-            byte[] newData = new byte[desiredSize * 2 + 1000];
-            System.arraycopy(data, 0, newData, 0, cursor);
-            data = newData;
-        }
+    public void setEndIfUnset(int end) {
+      if (this.end == Integer.MAX_VALUE) {
+        this.end = end;
+      }
     }
 
     /**
-     * Annotation on output.
+     * Sets the end as given.
+     *
+     * @param end {@code >= start;} the end
      */
-    private static class Annotation {
-        /** {@code >= 0;} start of annotated range (inclusive) */
-        private final int start;
-
-        /**
-         * {@code >= 0;} end of annotated range (exclusive);
-         * {@code Integer.MAX_VALUE} if unclosed
-         */
-        private int end;
-
-        /** {@code non-null;} annotation text */
-        private final String text;
-
-        /**
-         * Constructs an instance.
-         *
-         * @param start {@code >= 0;} start of annotated range
-         * @param end {@code >= start;} end of annotated range (exclusive) or
-         * {@code Integer.MAX_VALUE} if unclosed
-         * @param text {@code non-null;} annotation text
-         */
-        public Annotation(int start, int end, String text) {
-            this.start = start;
-            this.end = end;
-            this.text = text;
-        }
-
-        /**
-         * Constructs an instance. It is initally unclosed.
-         *
-         * @param start {@code >= 0;} start of annotated range
-         * @param text {@code non-null;} annotation text
-         */
-        public Annotation(int start, String text) {
-            this(start, Integer.MAX_VALUE, text);
-        }
-
-        /**
-         * Sets the end as given, but only if the instance is unclosed;
-         * otherwise, do nothing.
-         *
-         * @param end {@code >= start;} the end
-         */
-        public void setEndIfUnset(int end) {
-            if (this.end == Integer.MAX_VALUE) {
-                this.end = end;
-            }
-        }
-
-        /**
-         * Sets the end as given.
-         *
-         * @param end {@code >= start;} the end
-         */
-        public void setEnd(int end) {
-            this.end = end;
-        }
-
-        /**
-         * Gets the start.
-         *
-         * @return the start
-         */
-        public int getStart() {
-            return start;
-        }
-
-        /**
-         * Gets the end.
-         *
-         * @return the end
-         */
-        public int getEnd() {
-            return end;
-        }
-
-        /**
-         * Gets the text.
-         *
-         * @return {@code non-null;} the text
-         */
-        public String getText() {
-            return text;
-        }
+    public void setEnd(int end) {
+      this.end = end;
     }
+
+    /**
+     * Gets the start.
+     *
+     * @return the start
+     */
+    public int getStart() {
+      return start;
+    }
+
+    /**
+     * Gets the end.
+     *
+     * @return the end
+     */
+    public int getEnd() {
+      return end;
+    }
+
+    /**
+     * Gets the text.
+     *
+     * @return {@code non-null;} the text
+     */
+    public String getText() {
+      return text;
+    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ByteArrayByteInput.java b/dx/src/com/android/jack/dx/util/ByteArrayByteInput.java
index 8908997..4d7c7ba 100644
--- a/dx/src/com/android/jack/dx/util/ByteArrayByteInput.java
+++ b/dx/src/com/android/jack/dx/util/ByteArrayByteInput.java
@@ -16,16 +16,20 @@
 
 package com.android.jack.dx.util;
 
+/**
+ * TODO(jack team)
+ */
 public final class ByteArrayByteInput implements ByteInput {
 
-    private final byte[] bytes;
-    private int position;
+  private final byte[] bytes;
+  private int position;
 
-    public ByteArrayByteInput(byte... bytes) {
-        this.bytes = bytes;
-    }
+  public ByteArrayByteInput(byte... bytes) {
+    this.bytes = bytes;
+  }
 
-    @Override public byte readByte() {
-        return bytes[position++];
-    }
+  @Override
+  public byte readByte() {
+    return bytes[position++];
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ByteInput.java b/dx/src/com/android/jack/dx/util/ByteInput.java
index 00246e6..7abba45 100644
--- a/dx/src/com/android/jack/dx/util/ByteInput.java
+++ b/dx/src/com/android/jack/dx/util/ByteInput.java
@@ -21,10 +21,10 @@
  */
 public interface ByteInput {
 
-    /**
-     * Returns a byte.
-     *
-     * @throws IndexOutOfBoundsException if all bytes have been read.
-     */
-    byte readByte();
+  /**
+   * Returns a byte.
+   *
+   * @throws IndexOutOfBoundsException if all bytes have been read.
+   */
+  byte readByte();
 }
diff --git a/dx/src/com/android/jack/dx/util/ByteOutput.java b/dx/src/com/android/jack/dx/util/ByteOutput.java
index 1a2b8f4..7ff9457 100644
--- a/dx/src/com/android/jack/dx/util/ByteOutput.java
+++ b/dx/src/com/android/jack/dx/util/ByteOutput.java
@@ -21,10 +21,10 @@
  */
 public interface ByteOutput {
 
-    /**
-     * Writes a byte.
-     *
-     * @throws IndexOutOfBoundsException if all bytes have been written.
-     */
-    void writeByte(int i);
+  /**
+   * Writes a byte.
+   *
+   * @throws IndexOutOfBoundsException if all bytes have been written.
+   */
+  void writeByte(int i);
 }
diff --git a/dx/src/com/android/jack/dx/util/DexException.java b/dx/src/com/android/jack/dx/util/DexException.java
index c06c9f3..d03b92c 100644
--- a/dx/src/com/android/jack/dx/util/DexException.java
+++ b/dx/src/com/android/jack/dx/util/DexException.java
@@ -21,11 +21,14 @@
  * processing a dex file.
  */
 public final class DexException extends ExceptionWithContext {
-    public DexException(String message) {
-        super(message);
-    }
 
-    public DexException(Throwable cause) {
-        super(cause);
-    }
+  private static final long serialVersionUID = 1L;
+
+  public DexException(String message) {
+    super(message);
+  }
+
+  public DexException(Throwable cause) {
+    super(cause);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ExceptionWithContext.java b/dx/src/com/android/jack/dx/util/ExceptionWithContext.java
index 8951eaf..028e917 100644
--- a/dx/src/com/android/jack/dx/util/ExceptionWithContext.java
+++ b/dx/src/com/android/jack/dx/util/ExceptionWithContext.java
@@ -22,128 +22,128 @@
 /**
  * Exception which carries around structured context.
  */
-public class ExceptionWithContext
-        extends RuntimeException {
-    /** {@code non-null;} human-oriented context of the exception */
-    private StringBuffer context;
+public class ExceptionWithContext extends RuntimeException {
 
-    /**
-     * Augments the given exception with the given context, and return the
-     * result. The result is either the given exception if it was an
-     * {@link ExceptionWithContext}, or a newly-constructed exception if it
-     * was not.
-     *
-     * @param ex {@code non-null;} the exception to augment
-     * @param str {@code non-null;} context to add
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static ExceptionWithContext withContext(Throwable ex, String str) {
-        ExceptionWithContext ewc;
+  private static final long serialVersionUID = 1L;
 
-        if (ex instanceof ExceptionWithContext) {
-            ewc = (ExceptionWithContext) ex;
-        } else {
-            ewc = new ExceptionWithContext(ex);
-        }
+  /** {@code non-null;} human-oriented context of the exception */
+  private StringBuffer context;
 
-        ewc.addContext(str);
-        return ewc;
+  /**
+   * Augments the given exception with the given context, and return the
+   * result. The result is either the given exception if it was an
+   * {@link ExceptionWithContext}, or a newly-constructed exception if it
+   * was not.
+   *
+   * @param ex {@code non-null;} the exception to augment
+   * @param str {@code non-null;} context to add
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static ExceptionWithContext withContext(Throwable ex, String str) {
+    ExceptionWithContext ewc;
+
+    if (ex instanceof ExceptionWithContext) {
+      ewc = (ExceptionWithContext) ex;
+    } else {
+      ewc = new ExceptionWithContext(ex);
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param message human-oriented message
-     */
-    public ExceptionWithContext(String message) {
-        this(message, null);
+    ewc.addContext(str);
+    return ewc;
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param message human-oriented message
+   */
+  public ExceptionWithContext(String message) {
+    this(message, null);
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param cause {@code null-ok;} exception that caused this one
+   */
+  public ExceptionWithContext(Throwable cause) {
+    this(null, cause);
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param message human-oriented message
+   * @param cause {@code null-ok;} exception that caused this one
+   */
+  public ExceptionWithContext(String message, Throwable cause) {
+    super((message != null) ? message : (cause != null) ? cause.getMessage() : null, cause);
+
+    if (cause instanceof ExceptionWithContext) {
+      String ctx = ((ExceptionWithContext) cause).context.toString();
+      context = new StringBuffer(ctx.length() + 200);
+      context.append(ctx);
+    } else {
+      context = new StringBuffer(200);
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void printStackTrace(PrintStream out) {
+    super.printStackTrace(out);
+    out.println(context);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void printStackTrace(PrintWriter out) {
+    super.printStackTrace(out);
+    out.println(context);
+  }
+
+  /**
+   * Adds a line of context to this instance.
+   *
+   * @param str {@code non-null;} new context
+   */
+  public void addContext(String str) {
+    if (str == null) {
+      throw new NullPointerException("str == null");
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param cause {@code null-ok;} exception that caused this one
-     */
-    public ExceptionWithContext(Throwable cause) {
-        this(null, cause);
+    context.append(str);
+    if (!str.endsWith("\n")) {
+      context.append('\n');
     }
+  }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param message human-oriented message
-     * @param cause {@code null-ok;} exception that caused this one
-     */
-    public ExceptionWithContext(String message, Throwable cause) {
-        super((message != null) ? message :
-              (cause != null) ? cause.getMessage() : null,
-              cause);
+  /**
+   * Gets the context.
+   *
+   * @return {@code non-null;} the context
+   */
+  public String getContext() {
+    return context.toString();
+  }
 
-        if (cause instanceof ExceptionWithContext) {
-            String ctx = ((ExceptionWithContext) cause).context.toString();
-            context = new StringBuffer(ctx.length() + 200);
-            context.append(ctx);
-        } else {
-            context = new StringBuffer(200);
-        }
-    }
+  /**
+   * Prints the message and context.
+   *
+   * @param out {@code non-null;} where to print to
+   */
+  public void printContext(PrintStream out) {
+    out.println(getMessage());
+    out.print(context);
+  }
 
-    /** {@inheritDoc} */
-    @Override
-    public void printStackTrace(PrintStream out) {
-        super.printStackTrace(out);
-        out.println(context);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void printStackTrace(PrintWriter out) {
-        super.printStackTrace(out);
-        out.println(context);
-    }
-
-    /**
-     * Adds a line of context to this instance.
-     *
-     * @param str {@code non-null;} new context
-     */
-    public void addContext(String str) {
-        if (str == null) {
-            throw new NullPointerException("str == null");
-        }
-
-        context.append(str);
-        if (!str.endsWith("\n")) {
-            context.append('\n');
-        }
-    }
-
-    /**
-     * Gets the context.
-     *
-     * @return {@code non-null;} the context
-     */
-    public String getContext() {
-        return context.toString();
-    }
-
-    /**
-     * Prints the message and context.
-     *
-     * @param out {@code non-null;} where to print to
-     */
-    public void printContext(PrintStream out) {
-        out.println(getMessage());
-        out.print(context);
-    }
-
-    /**
-     * Prints the message and context.
-     *
-     * @param out {@code non-null;} where to print to
-     */
-    public void printContext(PrintWriter out) {
-        out.println(getMessage());
-        out.print(context);
-    }
+  /**
+   * Prints the message and context.
+   *
+   * @param out {@code non-null;} where to print to
+   */
+  public void printContext(PrintWriter out) {
+    out.println(getMessage());
+    out.print(context);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/FileUtils.java b/dx/src/com/android/jack/dx/util/FileUtils.java
index 4c71d52..061f27e 100644
--- a/dx/src/com/android/jack/dx/util/FileUtils.java
+++ b/dx/src/com/android/jack/dx/util/FileUtils.java
@@ -24,78 +24,84 @@
  * File I/O utilities.
  */
 public final class FileUtils {
-    /**
-     * This class is uninstantiable.
-     */
-    private FileUtils() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private FileUtils() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Reads the named file, translating {@link IOException} to a
+   * {@link RuntimeException} of some sort.
+   *
+   * @param fileName {@code non-null;} name of the file to read
+   * @return {@code non-null;} contents of the file
+   */
+  public static byte[] readFile(String fileName) {
+    File file = new File(fileName);
+    return readFile(file);
+  }
+
+  /**
+   * Reads the given file, translating {@link IOException} to a
+   * {@link RuntimeException} of some sort.
+   *
+   * @param file {@code non-null;} the file to read
+   * @return {@code non-null;} contents of the file
+   */
+  public static byte[] readFile(File file) {
+    if (!file.exists()) {
+      throw new RuntimeException(file + ": file not found");
     }
 
-    /**
-     * Reads the named file, translating {@link IOException} to a
-     * {@link RuntimeException} of some sort.
-     *
-     * @param fileName {@code non-null;} name of the file to read
-     * @return {@code non-null;} contents of the file
-     */
-    public static byte[] readFile(String fileName) {
-        File file = new File(fileName);
-        return readFile(file);
+    if (!file.isFile()) {
+      throw new RuntimeException(file + ": not a file");
     }
 
-    /**
-     * Reads the given file, translating {@link IOException} to a
-     * {@link RuntimeException} of some sort.
-     *
-     * @param file {@code non-null;} the file to read
-     * @return {@code non-null;} contents of the file
-     */
-    public static byte[] readFile(File file) {
-        if (!file.exists()) {
-            throw new RuntimeException(file + ": file not found");
+    if (!file.canRead()) {
+      throw new RuntimeException(file + ": file not readable");
+    }
+
+    long longLength = file.length();
+    int length = (int) longLength;
+    if (length != longLength) {
+      throw new RuntimeException(file + ": file too long");
+    }
+
+    byte[] result = new byte[length];
+
+    FileInputStream in = null;
+    try {
+      in = new FileInputStream(file);
+      int at = 0;
+      while (length > 0) {
+        int amt = in.read(result, at, length);
+        if (amt == -1) {
+          throw new RuntimeException(file + ": unexpected EOF");
         }
-
-        if (!file.isFile()) {
-            throw new RuntimeException(file + ": not a file");
-        }
-
-        if (!file.canRead()) {
-            throw new RuntimeException(file + ": file not readable");
-        }
-
-        long longLength = file.length();
-        int length = (int) longLength;
-        if (length != longLength) {
-            throw new RuntimeException(file + ": file too long");
-        }
-
-        byte[] result = new byte[length];
-
+        at += amt;
+        length -= amt;
+      }
+    } catch (IOException ex) {
+      throw new RuntimeException(file + ": trouble reading", ex);
+    } finally {
+      if (in != null) {
         try {
-            FileInputStream in = new FileInputStream(file);
-            int at = 0;
-            while (length > 0) {
-                int amt = in.read(result, at, length);
-                if (amt == -1) {
-                    throw new RuntimeException(file + ": unexpected EOF");
-                }
-                at += amt;
-                length -= amt;
-            }
-            in.close();
+          in.close();
         } catch (IOException ex) {
-            throw new RuntimeException(file + ": trouble reading", ex);
+          throw new RuntimeException(file + ": trouble reading", ex);
         }
-
-        return result;
+      }
     }
 
-    /**
-     * Returns true if {@code fileName} names a .zip, .jar, or .apk.
-     */
-    public static boolean hasArchiveSuffix(String fileName) {
-        return fileName.endsWith(".zip")
-                || fileName.endsWith(".jar")
-                || fileName.endsWith(".apk");
-    }
+    return result;
+  }
+
+  /**
+   * Returns true if {@code fileName} names a .zip, .jar, or .apk.
+   */
+  public static boolean hasArchiveSuffix(String fileName) {
+    return fileName.endsWith(".zip") || fileName.endsWith(".jar") || fileName.endsWith(".apk");
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/FixedSizeList.java b/dx/src/com/android/jack/dx/util/FixedSizeList.java
index a8badf0..9463877 100644
--- a/dx/src/com/android/jack/dx/util/FixedSizeList.java
+++ b/dx/src/com/android/jack/dx/util/FixedSizeList.java
@@ -21,256 +21,249 @@
 /**
  * Simple (mostly) fixed-size list of objects, which may be made immutable.
  */
-public class FixedSizeList
-        extends MutabilityControl implements ToHuman {
-    /** {@code non-null;} array of elements */
-    private Object[] arr;
+public class FixedSizeList extends MutabilityControl implements ToHuman {
+  /** {@code non-null;} array of elements */
+  private Object[] arr;
 
-    /**
-     * Constructs an instance. All indices initially contain {@code null}.
-     *
-     * @param size the size of the list
-     */
-    public FixedSizeList(int size) {
-        super(size != 0);
+  /**
+   * Constructs an instance. All indices initially contain {@code null}.
+   *
+   * @param size the size of the list
+   */
+  public FixedSizeList(int size) {
+    super(size != 0);
 
-        try {
-            arr = new Object[size];
-        } catch (NegativeArraySizeException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("size < 0");
-        }
+    try {
+      arr = new Object[size];
+    } catch (NegativeArraySizeException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("size < 0");
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (this == other) {
+      // Easy out.
+      return true;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (this == other) {
-            // Easy out.
-            return true;
-        }
-
-        if ((other == null) || (getClass() != other.getClass())) {
-            // Another easy out.
-            return false;
-        }
-
-        FixedSizeList list = (FixedSizeList) other;
-        return Arrays.equals(arr, list.arr);
+    if ((other == null) || (getClass() != other.getClass())) {
+      // Another easy out.
+      return false;
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        return Arrays.hashCode(arr);
+    FixedSizeList list = (FixedSizeList) other;
+    return Arrays.equals(arr, list.arr);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    return Arrays.hashCode(arr);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    String name = getClass().getName();
+
+    return toString0(name.substring(name.lastIndexOf('.') + 1) + '{', ", ", "}", false);
+  }
+
+  /**
+   * {@inheritDoc}
+   *
+   * This method will only work if every element of the list
+   * implements {@link ToHuman}.
+   */
+  @Override
+  public String toHuman() {
+    String name = getClass().getName();
+
+    return toString0(name.substring(name.lastIndexOf('.') + 1) + '{', ", ", "}", true);
+  }
+
+  /**
+   * Gets a customized string form for this instance.
+   *
+   * @param prefix {@code null-ok;} prefix for the start of the result
+   * @param separator {@code null-ok;} separator to insert between each item
+   * @param suffix {@code null-ok;} suffix for the end of the result
+   * @return {@code non-null;} the custom string
+   */
+  public String toString(String prefix, String separator, String suffix) {
+    return toString0(prefix, separator, suffix, false);
+  }
+
+  /**
+   * Gets a customized human string for this instance. This method will
+   * only work if every element of the list implements {@link
+   * ToHuman}.
+   *
+   * @param prefix {@code null-ok;} prefix for the start of the result
+   * @param separator {@code null-ok;} separator to insert between each item
+   * @param suffix {@code null-ok;} suffix for the end of the result
+   * @return {@code non-null;} the custom string
+   */
+  public String toHuman(String prefix, String separator, String suffix) {
+    return toString0(prefix, separator, suffix, true);
+  }
+
+  /**
+   * Gets the number of elements in this list.
+   */
+  public final int size() {
+    return arr.length;
+  }
+
+  /**
+   * Shrinks this instance to fit, by removing any unset
+   * ({@code null}) elements, leaving the remaining elements in
+   * their original order.
+   */
+  public void shrinkToFit() {
+    int sz = arr.length;
+    int newSz = 0;
+
+    for (int i = 0; i < sz; i++) {
+      if (arr[i] != null) {
+        newSz++;
+      }
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        String name = getClass().getName();
-
-        return toString0(name.substring(name.lastIndexOf('.') + 1) + '{',
-                         ", ",
-                         "}",
-                         false);
+    if (sz == newSz) {
+      return;
     }
 
-    /**
-     * {@inheritDoc}
-     *
-     * This method will only work if every element of the list
-     * implements {@link ToHuman}.
-     */
-    public String toHuman() {
-        String name = getClass().getName();
+    throwIfImmutable();
 
-        return toString0(name.substring(name.lastIndexOf('.') + 1) + '{',
-                         ", ",
-                         "}",
-                         true);
+    Object[] newa = new Object[newSz];
+    int at = 0;
+
+    for (int i = 0; i < sz; i++) {
+      Object one = arr[i];
+      if (one != null) {
+        newa[at] = one;
+        at++;
+      }
     }
 
-    /**
-     * Gets a customized string form for this instance.
-     *
-     * @param prefix {@code null-ok;} prefix for the start of the result
-     * @param separator {@code null-ok;} separator to insert between each item
-     * @param suffix {@code null-ok;} suffix for the end of the result
-     * @return {@code non-null;} the custom string
-     */
-    public String toString(String prefix, String separator, String suffix) {
-        return toString0(prefix, separator, suffix, false);
+    arr = newa;
+    if (newSz == 0) {
+      setImmutable();
+    }
+  }
+
+  /**
+   * Gets the indicated element. It is an error to call this with the
+   * index for an element which was never set; if you do that, this
+   * will throw {@code NullPointerException}. This method is
+   * protected so that subclasses may offer a safe type-checked
+   * public interface to their clients.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return {@code non-null;} the indicated element
+   */
+  protected final Object get0(int n) {
+    try {
+      Object result = arr[n];
+
+      if (result == null) {
+        throw new NullPointerException("unset: " + n);
+      }
+
+      return result;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      return throwIndex(n);
+    }
+  }
+
+  /**
+   * Gets the indicated element, allowing {@code null}s to be
+   * returned. This method is protected so that subclasses may
+   * (optionally) offer a safe type-checked public interface to
+   * their clients.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return {@code null-ok;} the indicated element
+   */
+  protected final Object getOrNull0(int n) {
+    return arr[n];
+  }
+
+  /**
+   * Sets the element at the given index, but without doing any type
+   * checks on the element. This method is protected so that
+   * subclasses may offer a safe type-checked public interface to
+   * their clients.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @param obj {@code null-ok;} the value to store
+   */
+  protected final void set0(int n, Object obj) {
+    throwIfImmutable();
+
+    try {
+      arr[n] = obj;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      throwIndex(n);
+    }
+  }
+
+  /**
+   * Throws the appropriate exception for the given index value.
+   *
+   * @param n the index value
+   * @return never
+   * @throws IndexOutOfBoundsException always thrown
+   */
+  private Object throwIndex(int n) {
+    if (n < 0) {
+      throw new IndexOutOfBoundsException("n < 0");
     }
 
-    /**
-     * Gets a customized human string for this instance. This method will
-     * only work if every element of the list implements {@link
-     * ToHuman}.
-     *
-     * @param prefix {@code null-ok;} prefix for the start of the result
-     * @param separator {@code null-ok;} separator to insert between each item
-     * @param suffix {@code null-ok;} suffix for the end of the result
-     * @return {@code non-null;} the custom string
-     */
-    public String toHuman(String prefix, String separator, String suffix) {
-        return toString0(prefix, separator, suffix, true);
+    throw new IndexOutOfBoundsException("n >= size()");
+  }
+
+  /**
+   * Helper for {@link #toString} and {@link #toHuman}, which both of
+   * those call to pretty much do everything.
+   *
+   * @param prefix {@code null-ok;} prefix for the start of the result
+   * @param separator {@code null-ok;} separator to insert between each item
+   * @param suffix {@code null-ok;} suffix for the end of the result
+   * @param human whether the output is to be human
+   * @return {@code non-null;} the custom string
+   */
+  private String toString0(String prefix, String separator, String suffix, boolean human) {
+    int len = arr.length;
+    StringBuffer sb = new StringBuffer(len * 10 + 10);
+
+    if (prefix != null) {
+      sb.append(prefix);
     }
 
-    /**
-     * Gets the number of elements in this list.
-     */
-    public final int size() {
-        return arr.length;
+    for (int i = 0; i < len; i++) {
+      if ((i != 0) && (separator != null)) {
+        sb.append(separator);
+      }
+
+      if (human) {
+        sb.append(((ToHuman) arr[i]).toHuman());
+      } else {
+        sb.append(arr[i]);
+      }
     }
 
-    /**
-     * Shrinks this instance to fit, by removing any unset
-     * ({@code null}) elements, leaving the remaining elements in
-     * their original order.
-     */
-    public void shrinkToFit() {
-        int sz = arr.length;
-        int newSz = 0;
-
-        for (int i = 0; i < sz; i++) {
-            if (arr[i] != null) {
-                newSz++;
-            }
-        }
-
-        if (sz == newSz) {
-            return;
-        }
-
-        throwIfImmutable();
-
-        Object[] newa = new Object[newSz];
-        int at = 0;
-
-        for (int i = 0; i < sz; i++) {
-            Object one = arr[i];
-            if (one != null) {
-                newa[at] = one;
-                at++;
-            }
-        }
-
-        arr = newa;
-        if (newSz == 0) {
-            setImmutable();
-        }
+    if (suffix != null) {
+      sb.append(suffix);
     }
 
-    /**
-     * Gets the indicated element. It is an error to call this with the
-     * index for an element which was never set; if you do that, this
-     * will throw {@code NullPointerException}. This method is
-     * protected so that subclasses may offer a safe type-checked
-     * public interface to their clients.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return {@code non-null;} the indicated element
-     */
-    protected final Object get0(int n) {
-        try {
-            Object result = arr[n];
-
-            if (result == null) {
-                throw new NullPointerException("unset: " + n);
-            }
-
-            return result;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            return throwIndex(n);
-        }
-    }
-
-    /**
-     * Gets the indicated element, allowing {@code null}s to be
-     * returned. This method is protected so that subclasses may
-     * (optionally) offer a safe type-checked public interface to
-     * their clients.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return {@code null-ok;} the indicated element
-     */
-    protected final Object getOrNull0(int n) {
-        return arr[n];
-    }
-
-    /**
-     * Sets the element at the given index, but without doing any type
-     * checks on the element. This method is protected so that
-     * subclasses may offer a safe type-checked public interface to
-     * their clients.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @param obj {@code null-ok;} the value to store
-     */
-    protected final void set0(int n, Object obj) {
-        throwIfImmutable();
-
-        try {
-            arr[n] = obj;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            throwIndex(n);
-        }
-    }
-
-    /**
-     * Throws the appropriate exception for the given index value.
-     *
-     * @param n the index value
-     * @return never
-     * @throws IndexOutOfBoundsException always thrown
-     */
-    private Object throwIndex(int n) {
-        if (n < 0) {
-            throw new IndexOutOfBoundsException("n < 0");
-        }
-
-        throw new IndexOutOfBoundsException("n >= size()");
-    }
-
-    /**
-     * Helper for {@link #toString} and {@link #toHuman}, which both of
-     * those call to pretty much do everything.
-     *
-     * @param prefix {@code null-ok;} prefix for the start of the result
-     * @param separator {@code null-ok;} separator to insert between each item
-     * @param suffix {@code null-ok;} suffix for the end of the result
-     * @param human whether the output is to be human
-     * @return {@code non-null;} the custom string
-     */
-    private String toString0(String prefix, String separator, String suffix,
-                             boolean human) {
-        int len = arr.length;
-        StringBuffer sb = new StringBuffer(len * 10 + 10);
-
-        if (prefix != null) {
-            sb.append(prefix);
-        }
-
-        for (int i = 0; i < len; i++) {
-            if ((i != 0) && (separator != null)) {
-                sb.append(separator);
-            }
-
-            if (human) {
-                sb.append(((ToHuman) arr[i]).toHuman());
-            } else {
-                sb.append(arr[i]);
-            }
-        }
-
-        if (suffix != null) {
-            sb.append(suffix);
-        }
-
-        return sb.toString();
-    }
+    return sb.toString();
+  }
 
 }
diff --git a/dx/src/com/android/jack/dx/util/Hex.java b/dx/src/com/android/jack/dx/util/Hex.java
index e928265..740c03c 100644
--- a/dx/src/com/android/jack/dx/util/Hex.java
+++ b/dx/src/com/android/jack/dx/util/Hex.java
@@ -20,284 +20,293 @@
  * Utilities for formatting numbers as hexadecimal.
  */
 public final class Hex {
-    /**
-     * This class is uninstantiable.
-     */
-    private Hex() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private Hex() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Formats a {@code long} as an 8-byte unsigned hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u8(long v) {
+    char[] result = new char[16];
+    for (int i = 0; i < 16; i++) {
+      result[15 - i] = Character.forDigit((int) v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats a {@code long} as an 8-byte unsigned hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u8(long v) {
-        char[] result = new char[16];
-        for (int i = 0; i < 16; i++) {
-            result[15 - i] = Character.forDigit((int) v & 0x0f, 16);
-            v >>= 4;
-        }
+    return new String(result);
+  }
 
-        return new String(result);
+  /**
+   * Formats an {@code int} as a 4-byte unsigned hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u4(int v) {
+    char[] result = new char[8];
+    for (int i = 0; i < 8; i++) {
+      result[7 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 4-byte unsigned hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u4(int v) {
-        char[] result = new char[8];
-        for (int i = 0; i < 8; i++) {
-            result[7 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
+    return new String(result);
+  }
 
-        return new String(result);
+  /**
+   * Formats an {@code int} as a 3-byte unsigned hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u3(int v) {
+    char[] result = new char[6];
+    for (int i = 0; i < 6; i++) {
+      result[5 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 3-byte unsigned hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u3(int v) {
-        char[] result = new char[6];
-        for (int i = 0; i < 6; i++) {
-            result[5 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
+    return new String(result);
+  }
 
-        return new String(result);
+  /**
+   * Formats an {@code int} as a 2-byte unsigned hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u2(int v) {
+    char[] result = new char[4];
+    for (int i = 0; i < 4; i++) {
+      result[3 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 2-byte unsigned hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u2(int v) {
-        char[] result = new char[4];
-        for (int i = 0; i < 4; i++) {
-            result[3 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
+    return new String(result);
+  }
 
-        return new String(result);
+  /**
+   * Formats an {@code int} as either a 2-byte unsigned hex value
+   * (if the value is small enough) or a 4-byte unsigned hex value (if
+   * not).
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u2or4(int v) {
+    if (v == (char) v) {
+      return u2(v);
+    } else {
+      return u4(v);
+    }
+  }
+
+  /**
+   * Formats an {@code int} as a 1-byte unsigned hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String u1(int v) {
+    char[] result = new char[2];
+    for (int i = 0; i < 2; i++) {
+      result[1 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as either a 2-byte unsigned hex value
-     * (if the value is small enough) or a 4-byte unsigned hex value (if
-     * not).
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u2or4(int v) {
-        if (v == (char) v) {
-            return u2(v);
-        } else {
-            return u4(v);
-        }
+    return new String(result);
+  }
+
+  /**
+   * Formats an {@code int} as a 4-bit unsigned hex nibble.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String uNibble(int v) {
+    char[] result = new char[1];
+
+    result[0] = Character.forDigit(v & 0x0f, 16);
+    return new String(result);
+  }
+
+  /**
+   * Formats a {@code long} as an 8-byte signed hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String s8(long v) {
+    char[] result = new char[17];
+
+    if (v < 0) {
+      result[0] = '-';
+      v = -v;
+    } else {
+      result[0] = '+';
     }
 
-    /**
-     * Formats an {@code int} as a 1-byte unsigned hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String u1(int v) {
-        char[] result = new char[2];
-        for (int i = 0; i < 2; i++) {
-            result[1 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
-
-        return new String(result);
+    for (int i = 0; i < 16; i++) {
+      result[16 - i] = Character.forDigit((int) v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 4-bit unsigned hex nibble.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String uNibble(int v) {
-        char[] result = new char[1];
+    return new String(result);
+  }
 
-        result[0] = Character.forDigit(v & 0x0f, 16);
-        return new String(result);
+  /**
+   * Formats an {@code int} as a 4-byte signed hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String s4(int v) {
+    char[] result = new char[9];
+
+    if (v < 0) {
+      result[0] = '-';
+      v = -v;
+    } else {
+      result[0] = '+';
     }
 
-    /**
-     * Formats a {@code long} as an 8-byte signed hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String s8(long v) {
-        char[] result = new char[17];
-
-        if (v < 0) {
-            result[0] = '-';
-            v = -v;
-        } else {
-            result[0] = '+';
-        }
-
-        for (int i = 0; i < 16; i++) {
-            result[16 - i] = Character.forDigit((int) v & 0x0f, 16);
-            v >>= 4;
-        }
-
-        return new String(result);
+    for (int i = 0; i < 8; i++) {
+      result[8 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 4-byte signed hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String s4(int v) {
-        char[] result = new char[9];
+    return new String(result);
+  }
 
-        if (v < 0) {
-            result[0] = '-';
-            v = -v;
-        } else {
-            result[0] = '+';
-        }
+  /**
+   * Formats an {@code int} as a 2-byte signed hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String s2(int v) {
+    char[] result = new char[5];
 
-        for (int i = 0; i < 8; i++) {
-            result[8 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
-
-        return new String(result);
+    if (v < 0) {
+      result[0] = '-';
+      v = -v;
+    } else {
+      result[0] = '+';
     }
 
-    /**
-     * Formats an {@code int} as a 2-byte signed hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String s2(int v) {
-        char[] result = new char[5];
-
-        if (v < 0) {
-            result[0] = '-';
-            v = -v;
-        } else {
-            result[0] = '+';
-        }
-
-        for (int i = 0; i < 4; i++) {
-            result[4 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
-
-        return new String(result);
+    for (int i = 0; i < 4; i++) {
+      result[4 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
 
-    /**
-     * Formats an {@code int} as a 1-byte signed hex value.
-     *
-     * @param v value to format
-     * @return {@code non-null;} formatted form
-     */
-    public static String s1(int v) {
-        char[] result = new char[3];
+    return new String(result);
+  }
 
-        if (v < 0) {
-            result[0] = '-';
-            v = -v;
-        } else {
-            result[0] = '+';
-        }
+  /**
+   * Formats an {@code int} as a 1-byte signed hex value.
+   *
+   * @param v value to format
+   * @return {@code non-null;} formatted form
+   */
+  public static String s1(int v) {
+    char[] result = new char[3];
 
-        for (int i = 0; i < 2; i++) {
-            result[2 - i] = Character.forDigit(v & 0x0f, 16);
-            v >>= 4;
-        }
-
-        return new String(result);
+    if (v < 0) {
+      result[0] = '-';
+      v = -v;
+    } else {
+      result[0] = '+';
     }
 
-    /**
-     * Formats a hex dump of a portion of a {@code byte[]}. The result
-     * is always newline-terminated, unless the passed-in length was zero,
-     * in which case the result is always the empty string ({@code ""}).
-     *
-     * @param arr {@code non-null;} array to format
-     * @param offset {@code >= 0;} offset to the part to dump
-     * @param length {@code >= 0;} number of bytes to dump
-     * @param outOffset {@code >= 0;} first output offset to print
-     * @param bpl {@code >= 0;} number of bytes of output per line
-     * @param addressLength {@code {2,4,6,8};} number of characters for each address
-     * header
-     * @return {@code non-null;} a string of the dump
-     */
-    public static String dump(byte[] arr, int offset, int length,
-                              int outOffset, int bpl, int addressLength) {
-        int end = offset + length;
-
-        // twos-complement math trick: ((x < 0) || (y < 0)) <=> ((x|y) < 0)
-        if (((offset | length | end) < 0) || (end > arr.length)) {
-            throw new IndexOutOfBoundsException("arr.length " +
-                                                arr.length + "; " +
-                                                offset + "..!" + end);
-        }
-
-        if (outOffset < 0) {
-            throw new IllegalArgumentException("outOffset < 0");
-        }
-
-        if (length == 0) {
-            return "";
-        }
-
-        StringBuffer sb = new StringBuffer(length * 4 + 6);
-        boolean bol = true;
-        int col = 0;
-
-        while (length > 0) {
-            if (col == 0) {
-                String astr;
-                switch (addressLength) {
-                    case 2:  astr = Hex.u1(outOffset); break;
-                    case 4:  astr = Hex.u2(outOffset); break;
-                    case 6:  astr = Hex.u3(outOffset); break;
-                    default: astr = Hex.u4(outOffset); break;
-                }
-                sb.append(astr);
-                sb.append(": ");
-            } else if ((col & 1) == 0) {
-                sb.append(' ');
-            }
-            sb.append(Hex.u1(arr[offset]));
-            outOffset++;
-            offset++;
-            col++;
-            if (col == bpl) {
-                sb.append('\n');
-                col = 0;
-            }
-            length--;
-        }
-
-        if (col != 0) {
-            sb.append('\n');
-        }
-
-        return sb.toString();
+    for (int i = 0; i < 2; i++) {
+      result[2 - i] = Character.forDigit(v & 0x0f, 16);
+      v >>= 4;
     }
+
+    return new String(result);
+  }
+
+  /**
+   * Formats a hex dump of a portion of a {@code byte[]}. The result
+   * is always newline-terminated, unless the passed-in length was zero,
+   * in which case the result is always the empty string ({@code ""}).
+   *
+   * @param arr {@code non-null;} array to format
+   * @param offset {@code >= 0;} offset to the part to dump
+   * @param length {@code >= 0;} number of bytes to dump
+   * @param outOffset {@code >= 0;} first output offset to print
+   * @param bpl {@code >= 0;} number of bytes of output per line
+   * @param addressLength {@code {2,4,6,8};} number of characters for each address
+   * header
+   * @return {@code non-null;} a string of the dump
+   */
+  public static String dump(byte[] arr,
+      int offset,
+      int length,
+      int outOffset,
+      int bpl,
+      int addressLength) {
+    int end = offset + length;
+
+    // twos-complement math trick: ((x < 0) || (y < 0)) <=> ((x|y) < 0)
+    if (((offset | length | end) < 0) || (end > arr.length)) {
+      throw new IndexOutOfBoundsException("arr.length " + arr.length + "; " + offset + "..!" + end);
+    }
+
+    if (outOffset < 0) {
+      throw new IllegalArgumentException("outOffset < 0");
+    }
+
+    if (length == 0) {
+      return "";
+    }
+
+    StringBuffer sb = new StringBuffer(length * 4 + 6);
+    int col = 0;
+
+    while (length > 0) {
+      if (col == 0) {
+        String astr;
+        switch (addressLength) {
+          case 2:
+            astr = Hex.u1(outOffset);
+            break;
+          case 4:
+            astr = Hex.u2(outOffset);
+            break;
+          case 6:
+            astr = Hex.u3(outOffset);
+            break;
+          default:
+            astr = Hex.u4(outOffset);
+            break;
+        }
+        sb.append(astr);
+        sb.append(": ");
+      } else if ((col & 1) == 0) {
+        sb.append(' ');
+      }
+      sb.append(Hex.u1(arr[offset]));
+      outOffset++;
+      offset++;
+      col++;
+      if (col == bpl) {
+        sb.append('\n');
+        col = 0;
+      }
+      length--;
+    }
+
+    if (col != 0) {
+      sb.append('\n');
+    }
+
+    return sb.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/HexParser.java b/dx/src/com/android/jack/dx/util/HexParser.java
index 551180a..71ed283 100644
--- a/dx/src/com/android/jack/dx/util/HexParser.java
+++ b/dx/src/com/android/jack/dx/util/HexParser.java
@@ -20,126 +20,120 @@
  * Utilities for parsing hexadecimal text.
  */
 public final class HexParser {
-    /**
-     * This class is uninstantiable.
-     */
-    private HexParser() {
-        // This space intentionally left blank.
-    }
+  /**
+   * This class is uninstantiable.
+   */
+  private HexParser() {
+    // This space intentionally left blank.
+  }
 
-    /**
-     * Parses the given text as hex, returning a {@code byte[]}
-     * corresponding to the text. The format is simple: Each line may
-     * start with a hex offset followed by a colon (which is verified
-     * and presumably used just as a comment), and then consists of
-     * hex digits freely interspersed with whitespace. If a pound sign
-     * is encountered, it and the rest of the line are ignored as a
-     * comment. If a double quote is encountered, then the ASCII value
-     * of the subsequent characters is used, until the next double
-     * quote. Quoted strings may not span multiple lines.
-     *
-     * @param src {@code non-null;} the source string
-     * @return {@code non-null;} the parsed form
-     */
-    public static byte[] parse(String src) {
-        int len = src.length();
-        byte[] result = new byte[len / 2];
-        int at = 0;
-        int outAt = 0;
+  /**
+   * Parses the given text as hex, returning a {@code byte[]}
+   * corresponding to the text. The format is simple: Each line may
+   * start with a hex offset followed by a colon (which is verified
+   * and presumably used just as a comment), and then consists of
+   * hex digits freely interspersed with whitespace. If a pound sign
+   * is encountered, it and the rest of the line are ignored as a
+   * comment. If a double quote is encountered, then the ASCII value
+   * of the subsequent characters is used, until the next double
+   * quote. Quoted strings may not span multiple lines.
+   *
+   * @param src {@code non-null;} the source string
+   * @return {@code non-null;} the parsed form
+   */
+  public static byte[] parse(String src) {
+    int len = src.length();
+    byte[] result = new byte[len / 2];
+    int at = 0;
+    int outAt = 0;
 
-        while (at < len) {
-            int nlAt = src.indexOf('\n', at);
-            if (nlAt < 0) {
-                nlAt = len;
-            }
-            int poundAt = src.indexOf('#', at);
+    while (at < len) {
+      int nlAt = src.indexOf('\n', at);
+      if (nlAt < 0) {
+        nlAt = len;
+      }
+      int poundAt = src.indexOf('#', at);
 
-            String line;
-            if ((poundAt >= 0) && (poundAt < nlAt)) {
-                line = src.substring(at, poundAt);
-            } else {
-                line = src.substring(at, nlAt);
-            }
-            at = nlAt + 1;
+      String line;
+      if ((poundAt >= 0) && (poundAt < nlAt)) {
+        line = src.substring(at, poundAt);
+      } else {
+        line = src.substring(at, nlAt);
+      }
+      at = nlAt + 1;
 
-            int colonAt = line.indexOf(':');
+      int colonAt = line.indexOf(':');
 
-            atCheck:
-            if (colonAt != -1) {
-                int quoteAt = line.indexOf('\"');
-                if ((quoteAt != -1) && (quoteAt < colonAt)) {
-                    break atCheck;
-                }
-
-                String atStr = line.substring(0, colonAt).trim();
-                line = line.substring(colonAt + 1);
-                int alleged = Integer.parseInt(atStr, 16);
-                if (alleged != outAt) {
-                    throw new RuntimeException("bogus offset marker: " +
-                                               atStr);
-                }
-            }
-
-            int lineLen = line.length();
-            int value = -1;
-            boolean quoteMode = false;
-
-            for (int i = 0; i < lineLen; i++) {
-                char c = line.charAt(i);
-
-                if (quoteMode) {
-                    if (c == '\"') {
-                        quoteMode = false;
-                    } else {
-                        result[outAt] = (byte) c;
-                        outAt++;
-                    }
-                    continue;
-                }
-
-                if (c <= ' ') {
-                    continue;
-                }
-                if (c == '\"') {
-                    if (value != -1) {
-                        throw new RuntimeException("spare digit around " +
-                                                   "offset " + Hex.u4(outAt));
-                    }
-                    quoteMode = true;
-                    continue;
-                }
-
-                int digVal = Character.digit(c, 16);
-                if (digVal == -1) {
-                    throw new RuntimeException("bogus digit character: \"" +
-                                               c + "\"");
-                }
-                if (value == -1) {
-                    value = digVal;
-                } else {
-                    result[outAt] = (byte) ((value << 4) | digVal);
-                    outAt++;
-                    value = -1;
-                }
-            }
-
-            if (value != -1) {
-                throw new RuntimeException("spare digit around offset " +
-                                           Hex.u4(outAt));
-            }
-
-            if (quoteMode) {
-                throw new RuntimeException("unterminated quote around " +
-                                           "offset " + Hex.u4(outAt));
-            }
+      atCheck: if (colonAt != -1) {
+        int quoteAt = line.indexOf('\"');
+        if ((quoteAt != -1) && (quoteAt < colonAt)) {
+          break atCheck;
         }
 
-        if (outAt < result.length) {
-            byte[] newr = new byte[outAt];
-            System.arraycopy(result, 0, newr, 0, outAt);
-            result = newr;
+        String atStr = line.substring(0, colonAt).trim();
+        line = line.substring(colonAt + 1);
+        int alleged = Integer.parseInt(atStr, 16);
+        if (alleged != outAt) {
+          throw new RuntimeException("bogus offset marker: " + atStr);
+        }
+      }
+
+      int lineLen = line.length();
+      int value = -1;
+      boolean quoteMode = false;
+
+      for (int i = 0; i < lineLen; i++) {
+        char c = line.charAt(i);
+
+        if (quoteMode) {
+          if (c == '\"') {
+            quoteMode = false;
+          } else {
+            result[outAt] = (byte) c;
+            outAt++;
+          }
+          continue;
         }
 
-        return result;
+        if (c <= ' ') {
+          continue;
+        }
+        if (c == '\"') {
+          if (value != -1) {
+            throw new RuntimeException("spare digit around " + "offset " + Hex.u4(outAt));
+          }
+          quoteMode = true;
+          continue;
+        }
+
+        int digVal = Character.digit(c, 16);
+        if (digVal == -1) {
+          throw new RuntimeException("bogus digit character: \"" + c + "\"");
+        }
+        if (value == -1) {
+          value = digVal;
+        } else {
+          result[outAt] = (byte) ((value << 4) | digVal);
+          outAt++;
+          value = -1;
+        }
+      }
+
+      if (value != -1) {
+        throw new RuntimeException("spare digit around offset " + Hex.u4(outAt));
+      }
+
+      if (quoteMode) {
+        throw new RuntimeException("unterminated quote around " + "offset " + Hex.u4(outAt));
+      }
     }
+
+    if (outAt < result.length) {
+      byte[] newr = new byte[outAt];
+      System.arraycopy(result, 0, newr, 0, outAt);
+      result = newr;
+    }
+
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/IndentingWriter.java b/dx/src/com/android/jack/dx/util/IndentingWriter.java
index 5fa042a..b7a8e41 100644
--- a/dx/src/com/android/jack/dx/util/IndentingWriter.java
+++ b/dx/src/com/android/jack/dx/util/IndentingWriter.java
@@ -27,143 +27,143 @@
  * line.
  */
 public final class IndentingWriter extends FilterWriter {
-    /** {@code null-ok;} optional prefix for every line */
-    private final String prefix;
+  /** {@code null-ok;} optional prefix for every line */
+  private final String prefix;
 
-    /** {@code > 0;} the maximum output width */
-    private final int width;
+  /** {@code > 0;} the maximum output width */
+  private final int width;
 
-    /** {@code > 0;} the maximum indent */
-    private final int maxIndent;
+  /** {@code > 0;} the maximum indent */
+  private final int maxIndent;
 
-    /** {@code >= 0;} current output column (zero-based) */
-    private int column;
+  /** {@code >= 0;} current output column (zero-based) */
+  private int column;
 
-    /** whether indent spaces are currently being collected */
-    private boolean collectingIndent;
+  /** whether indent spaces are currently being collected */
+  private boolean collectingIndent;
 
-    /** {@code >= 0;} current indent amount */
-    private int indent;
+  /** {@code >= 0;} current indent amount */
+  private int indent;
 
-    /**
-     * Constructs an instance.
-     *
-     * @param out {@code non-null;} writer to send final output to
-     * @param width {@code >= 0;} the maximum output width (not including
-     * {@code prefix}), or {@code 0} for no maximum
-     * @param prefix {@code non-null;} the prefix for each line
-     */
-    public IndentingWriter(Writer out, int width, String prefix) {
-        super(out);
+  /**
+   * Constructs an instance.
+   *
+   * @param out {@code non-null;} writer to send final output to
+   * @param width {@code >= 0;} the maximum output width (not including
+   * {@code prefix}), or {@code 0} for no maximum
+   * @param prefix {@code non-null;} the prefix for each line
+   */
+  public IndentingWriter(Writer out, int width, String prefix) {
+    super(out);
 
-        if (out == null) {
-            throw new NullPointerException("out == null");
-        }
-
-        if (width < 0) {
-            throw new IllegalArgumentException("width < 0");
-        }
-
-        if (prefix == null) {
-            throw new NullPointerException("prefix == null");
-        }
-
-        this.width = (width != 0) ? width : Integer.MAX_VALUE;
-        this.maxIndent = width >> 1;
-        this.prefix = (prefix.length() == 0) ? null : prefix;
-
-        bol();
+    if (out == null) {
+      throw new NullPointerException("out == null");
     }
 
-    /**
-     * Constructs a no-prefix instance.
-     *
-     * @param out {@code non-null;} writer to send final output to
-     * @param width {@code >= 0;} the maximum output width (not including
-     * {@code prefix}), or {@code 0} for no maximum
-     */
-    public IndentingWriter(Writer out, int width) {
-        this(out, width, "");
+    if (width < 0) {
+      throw new IllegalArgumentException("width < 0");
     }
 
-    /** {@inheritDoc} */
-    @Override
-    public void write(int c) throws IOException {
-        synchronized (lock) {
-            if (collectingIndent) {
-                if (c == ' ') {
-                    indent++;
-                    if (indent >= maxIndent) {
-                        indent = maxIndent;
-                        collectingIndent = false;
-                    }
-                } else {
-                    collectingIndent = false;
-                }
-            }
+    if (prefix == null) {
+      throw new NullPointerException("prefix == null");
+    }
 
-            if ((column == width) && (c != '\n')) {
-                out.write('\n');
-                column = 0;
-                /*
-                 * Note: No else, so this should fall through to the next
-                 * if statement.
-                 */
-            }
+    this.width = (width != 0) ? width : Integer.MAX_VALUE;
+    this.maxIndent = width >> 1;
+    this.prefix = (prefix.length() == 0) ? null : prefix;
 
-            if (column == 0) {
-                if (prefix != null) {
-                    out.write(prefix);
-                }
+    bol();
+  }
 
-                if (!collectingIndent) {
-                    for (int i = 0; i < indent; i++) {
-                        out.write(' ');
-                    }
-                    column = indent;
-                }
-            }
+  /**
+   * Constructs a no-prefix instance.
+   *
+   * @param out {@code non-null;} writer to send final output to
+   * @param width {@code >= 0;} the maximum output width (not including
+   * {@code prefix}), or {@code 0} for no maximum
+   */
+  public IndentingWriter(Writer out, int width) {
+    this(out, width, "");
+  }
 
-            out.write(c);
-
-            if (c == '\n') {
-                bol();
-            } else {
-                column++;
-            }
+  /** {@inheritDoc} */
+  @Override
+  public void write(int c) throws IOException {
+    synchronized (lock) {
+      if (collectingIndent) {
+        if (c == ' ') {
+          indent++;
+          if (indent >= maxIndent) {
+            indent = maxIndent;
+            collectingIndent = false;
+          }
+        } else {
+          collectingIndent = false;
         }
-    }
+      }
 
-    /** {@inheritDoc} */
-    @Override
-    public void write(char[] cbuf, int off, int len) throws IOException {
-        synchronized (lock) {
-            while (len > 0) {
-                write(cbuf[off]);
-                off++;
-                len--;
-            }
-        }
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void write(String str, int off, int len) throws IOException {
-        synchronized (lock) {
-            while (len > 0) {
-                write(str.charAt(off));
-                off++;
-                len--;
-            }
-        }
-    }
-
-    /**
-     * Indicates that output is at the beginning of a line.
-     */
-    private void bol() {
+      if ((column == width) && (c != '\n')) {
+        out.write('\n');
         column = 0;
-        collectingIndent = (maxIndent != 0);
-        indent = 0;
+        /*
+         * Note: No else, so this should fall through to the next
+         * if statement.
+         */
+      }
+
+      if (column == 0) {
+        if (prefix != null) {
+          out.write(prefix);
+        }
+
+        if (!collectingIndent) {
+          for (int i = 0; i < indent; i++) {
+            out.write(' ');
+          }
+          column = indent;
+        }
+      }
+
+      out.write(c);
+
+      if (c == '\n') {
+        bol();
+      } else {
+        column++;
+      }
     }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void write(char[] cbuf, int off, int len) throws IOException {
+    synchronized (lock) {
+      while (len > 0) {
+        write(cbuf[off]);
+        off++;
+        len--;
+      }
+    }
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public void write(String str, int off, int len) throws IOException {
+    synchronized (lock) {
+      while (len > 0) {
+        write(str.charAt(off));
+        off++;
+        len--;
+      }
+    }
+  }
+
+  /**
+   * Indicates that output is at the beginning of a line.
+   */
+  private void bol() {
+    column = 0;
+    collectingIndent = (maxIndent != 0);
+    indent = 0;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/IntIterator.java b/dx/src/com/android/jack/dx/util/IntIterator.java
index cd28378..8fca6fc 100644
--- a/dx/src/com/android/jack/dx/util/IntIterator.java
+++ b/dx/src/com/android/jack/dx/util/IntIterator.java
@@ -21,18 +21,18 @@
  */
 public interface IntIterator {
 
-    /**
-     * Checks to see if the iterator has a next value.
-     *
-     * @return true if next() will succeed
-     */
-    boolean hasNext();
+  /**
+   * Checks to see if the iterator has a next value.
+   *
+   * @return true if next() will succeed
+   */
+  boolean hasNext();
 
-    /**
-     * Returns the next value in the iterator.
-     *
-     * @return next value
-     * @throws java.util.NoSuchElementException if no next element exists
-     */
-    int next();
+  /**
+   * Returns the next value in the iterator.
+   *
+   * @return next value
+   * @throws java.util.NoSuchElementException if no next element exists
+   */
+  int next();
 }
diff --git a/dx/src/com/android/jack/dx/util/IntList.java b/dx/src/com/android/jack/dx/util/IntList.java
index 0a7ce7c..36e96d0 100644
--- a/dx/src/com/android/jack/dx/util/IntList.java
+++ b/dx/src/com/android/jack/dx/util/IntList.java
@@ -22,432 +22,431 @@
  * Simple list of {@code int}s.
  */
 public final class IntList extends MutabilityControl {
-    /** {@code non-null;} immutable, no-element instance */
-    public static final IntList EMPTY = new IntList(0);
+  /** {@code non-null;} immutable, no-element instance */
+  public static final IntList EMPTY = new IntList(0);
 
-    /** {@code non-null;} array of elements */
-    private int[] values;
+  /** {@code non-null;} array of elements */
+  private int[] values;
 
-    /** {@code >= 0;} current size of the list */
-    private int size;
+  /** {@code >= 0;} current size of the list */
+  private int size;
 
-    /** whether the values are currently sorted */
-    private boolean sorted;
+  /** whether the values are currently sorted */
+  private boolean sorted;
 
-    static {
-        EMPTY.setImmutable();
+  static {
+    EMPTY.setImmutable();
+  }
+
+  /**
+   * Constructs a new immutable instance with the given element.
+   *
+   * @param value the sole value in the list
+   */
+  public static IntList makeImmutable(int value) {
+    IntList result = new IntList(1);
+
+    result.add(value);
+    result.setImmutable();
+
+    return result;
+  }
+
+  /**
+   * Constructs a new immutable instance with the given elements.
+   *
+   * @param value0 the first value in the list
+   * @param value1 the second value in the list
+   */
+  public static IntList makeImmutable(int value0, int value1) {
+    IntList result = new IntList(2);
+
+    result.add(value0);
+    result.add(value1);
+    result.setImmutable();
+
+    return result;
+  }
+
+  /**
+   * Constructs an empty instance with a default initial capacity.
+   */
+  public IntList() {
+    this(4);
+  }
+
+  /**
+   * Constructs an empty instance.
+   *
+   * @param initialCapacity {@code >= 0;} initial capacity of the list
+   */
+  public IntList(int initialCapacity) {
+    super(true);
+
+    try {
+      values = new int[initialCapacity];
+    } catch (NegativeArraySizeException ex) {
+      // Translate the exception.
+      throw new IllegalArgumentException("size < 0");
     }
 
-    /**
-     * Constructs a new immutable instance with the given element.
-     *
-     * @param value the sole value in the list
+    size = 0;
+    sorted = true;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public int hashCode() {
+    int result = 0;
+
+    for (int i = 0; i < size; i++) {
+      result = (result * 31) + values[i];
+    }
+
+    return result;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean equals(Object other) {
+    if (other == this) {
+      return true;
+    }
+
+    if (!(other instanceof IntList)) {
+      return false;
+    }
+
+    IntList otherList = (IntList) other;
+
+    if (sorted != otherList.sorted) {
+      return false;
+    }
+
+    if (size != otherList.size) {
+      return false;
+    }
+
+    for (int i = 0; i < size; i++) {
+      if (values[i] != otherList.values[i]) {
+        return false;
+      }
+    }
+
+    return true;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public String toString() {
+    StringBuffer sb = new StringBuffer(size * 5 + 10);
+
+    sb.append('{');
+
+    for (int i = 0; i < size; i++) {
+      if (i != 0) {
+        sb.append(", ");
+      }
+      sb.append(values[i]);
+    }
+
+    sb.append('}');
+
+    return sb.toString();
+  }
+
+  /**
+   * Gets the number of elements in this list.
+   */
+  public int size() {
+    return size;
+  }
+
+  /**
+   * Gets the indicated value.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @return the indicated element's value
+   */
+  public int get(int n) {
+    if (n >= size) {
+      throw new IndexOutOfBoundsException("n >= size()");
+    }
+
+    try {
+      return values[n];
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate exception.
+      throw new IndexOutOfBoundsException("n < 0");
+    }
+  }
+
+  /**
+   * Sets the value at the given index.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @param value value to store
+   */
+  public void set(int n, int value) {
+    throwIfImmutable();
+
+    if (n >= size) {
+      throw new IndexOutOfBoundsException("n >= size()");
+    }
+
+    try {
+      values[n] = value;
+      sorted = false;
+    } catch (ArrayIndexOutOfBoundsException ex) {
+      // Translate the exception.
+      if (n < 0) {
+        throw new IllegalArgumentException("n < 0");
+      }
+    }
+  }
+
+  /**
+   * Adds an element to the end of the list. This will increase the
+   * list's capacity if necessary.
+   *
+   * @param value the value to add
+   */
+  public void add(int value) {
+    throwIfImmutable();
+
+    growIfNeeded();
+
+    values[size++] = value;
+
+    if (sorted && (size > 1)) {
+      sorted = (value >= values[size - 2]);
+    }
+  }
+
+  /**
+   * Inserts element into specified index, moving elements at and above
+   * that index up one. May not be used to insert at an index beyond the
+   * current size (that is, insertion as a last element is legal but
+   * no further).
+   *
+   * @param n {@code >= 0, <=size();} index of where to insert
+   * @param value value to insert
+   */
+  public void insert(int n, int value) {
+    if (n > size) {
+      throw new IndexOutOfBoundsException("n > size()");
+    }
+
+    growIfNeeded();
+
+    System.arraycopy(values, n, values, n + 1, size - n);
+    values[n] = value;
+    size++;
+
+    sorted =
+        sorted && (n == 0 || value > values[n - 1]) && (n == (size - 1) || value < values[n + 1]);
+  }
+
+  /**
+   * Removes an element at a given index, shifting elements at greater
+   * indicies down one.
+   *
+   * @param n  {@code >=0, < size();} index of element to remove
+   */
+  public void removeIndex(int n) {
+    if (n >= size) {
+      throw new IndexOutOfBoundsException("n >= size()");
+    }
+
+    System.arraycopy(values, n + 1, values, n, size - n - 1);
+    size--;
+
+    // sort status is unchanged
+  }
+
+  /**
+   * Increases size of array if needed
+   */
+  private void growIfNeeded() {
+    if (size == values.length) {
+      // Resize.
+      int[] newv = new int[size * 3 / 2 + 10];
+      System.arraycopy(values, 0, newv, 0, size);
+      values = newv;
+    }
+  }
+
+  /**
+   * Returns the last element in the array without modifying the array
+   *
+   * @return last value in the array
+   * @throws IndexOutOfBoundsException if stack is empty
+   */
+  public int top() {
+    return get(size - 1);
+  }
+
+  /**
+   * Pops an element off the end of the list and decreasing the size by one.
+   *
+   * @return value from what was the last element
+   * @throws IndexOutOfBoundsException if stack is empty
+   */
+  public int pop() {
+    throwIfImmutable();
+
+    int result;
+
+    result = get(size - 1);
+    size--;
+
+    return result;
+  }
+
+  /**
+   * Pops N elements off the end of the list and decreasing the size by N.
+   *
+   * @param n {@code >= 0;} number of elements to remove from end
+   * @throws IndexOutOfBoundsException if stack is smaller than N
+   */
+  public void pop(int n) {
+    throwIfImmutable();
+
+    size -= n;
+  }
+
+  /**
+   * Shrinks the size of the list.
+   *
+   * @param newSize {@code >= 0;} the new size
+   */
+  public void shrink(int newSize) {
+    if (newSize < 0) {
+      throw new IllegalArgumentException("newSize < 0");
+    }
+
+    if (newSize > size) {
+      throw new IllegalArgumentException("newSize > size");
+    }
+
+    throwIfImmutable();
+
+    size = newSize;
+  }
+
+  /**
+   * Makes and returns a mutable copy of the list.
+   *
+   * @return {@code non-null;} an appropriately-constructed instance
+   */
+  public IntList mutableCopy() {
+    int sz = size;
+    IntList result = new IntList(sz);
+
+    for (int i = 0; i < sz; i++) {
+      result.add(values[i]);
+    }
+
+    return result;
+  }
+
+  /**
+   * Sorts the elements in the list in-place.
+   */
+  public void sort() {
+    throwIfImmutable();
+
+    if (!sorted) {
+      Arrays.sort(values, 0, size);
+      sorted = true;
+    }
+  }
+
+  /**
+   * Returns the index of the given value, or -1 if the value does not
+   * appear in the list.  This will do a binary search if the list is
+   * sorted or a linear search if not.
+   *
+   * @param value value to find
+   * @return index of value or -1
+   */
+  public int indexOf(int value) {
+    int ret = binarysearch(value);
+
+    return ret >= 0 ? ret : -1;
+
+  }
+
+  /**
+   * Performs a binary search on a sorted list, returning the index of
+   * the given value if it is present or
+   * {@code (-(insertion point) - 1)} if the value is not present.
+   * If the list is not sorted, then reverts to linear search and returns
+   * {@code -size()} if the element is not found.
+   *
+   * @param value value to find
+   * @return index of value or {@code (-(insertion point) - 1)} if the
+   * value is not present
+   */
+  public int binarysearch(int value) {
+    int sz = size;
+
+    if (!sorted) {
+      // Linear search.
+      for (int i = 0; i < sz; i++) {
+        if (values[i] == value) {
+          return i;
+        }
+      }
+
+      return -sz;
+    }
+
+    /*
+     * Binary search. This variant does only one value comparison
+     * per iteration but does one more iteration on average than
+     * the variant that includes a value equality check per
+     * iteration.
      */
-    public static IntList makeImmutable(int value) {
-        IntList result = new IntList(1);
 
-        result.add(value);
-        result.setImmutable();
+int min = -1;
+    int max = sz;
 
-        return result;
+    while (max > (min + 1)) {
+      /*
+       * The guessIdx calculation is equivalent to ((min + max)
+       * / 2) but won't go wonky when min and max are close to
+       * Integer.MAX_VALUE.
+       */
+      int guessIdx = min + ((max - min) >> 1);
+      int guess = values[guessIdx];
+
+      if (value <= guess) {
+        max = guessIdx;
+      } else {
+        min = guessIdx;
+      }
     }
 
-    /**
-     * Constructs a new immutable instance with the given elements.
-     *
-     * @param value0 the first value in the list
-     * @param value1 the second value in the list
-     */
-    public static IntList makeImmutable(int value0, int value1) {
-        IntList result = new IntList(2);
-
-        result.add(value0);
-        result.add(value1);
-        result.setImmutable();
-
-        return result;
+    if ((max != sz)) {
+      return (value == values[max]) ? max : (-max - 1);
+    } else {
+      return -sz - 1;
     }
+  }
 
-    /**
-     * Constructs an empty instance with a default initial capacity.
-     */
-    public IntList() {
-        this(4);
-    }
 
-    /**
-     * Constructs an empty instance.
-     *
-     * @param initialCapacity {@code >= 0;} initial capacity of the list
-     */
-    public IntList(int initialCapacity) {
-        super(true);
-
-        try {
-            values = new int[initialCapacity];
-        } catch (NegativeArraySizeException ex) {
-            // Translate the exception.
-            throw new IllegalArgumentException("size < 0");
-        }
-
-        size = 0;
-        sorted = true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int hashCode() {
-        int result = 0;
-
-        for (int i = 0; i < size; i++) {
-            result = (result * 31) + values[i];
-        }
-
-        return result;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public boolean equals(Object other) {
-        if (other == this) {
-            return true;
-        }
-
-        if (! (other instanceof IntList)) {
-            return false;
-        }
-
-        IntList otherList = (IntList) other;
-
-        if (sorted != otherList.sorted) {
-            return false;
-        }
-
-        if (size != otherList.size) {
-            return false;
-        }
-
-        for (int i = 0; i < size; i++) {
-            if (values[i] != otherList.values[i]) {
-                return false;
-            }
-        }
-
-        return true;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public String toString() {
-        StringBuffer sb = new StringBuffer(size * 5 + 10);
-
-        sb.append('{');
-
-        for (int i = 0; i < size; i++) {
-            if (i != 0) {
-                sb.append(", ");
-            }
-            sb.append(values[i]);
-        }
-
-        sb.append('}');
-
-        return sb.toString();
-    }
-
-    /**
-     * Gets the number of elements in this list.
-     */
-    public int size() {
-        return size;
-    }
-
-    /**
-     * Gets the indicated value.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @return the indicated element's value
-     */
-    public int get(int n) {
-        if (n >= size) {
-            throw new IndexOutOfBoundsException("n >= size()");
-        }
-
-        try {
-            return values[n];
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate exception.
-            throw new IndexOutOfBoundsException("n < 0");
-        }
-    }
-
-    /**
-     * Sets the value at the given index.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @param value value to store
-     */
-    public void set(int n, int value) {
-        throwIfImmutable();
-
-        if (n >= size) {
-            throw new IndexOutOfBoundsException("n >= size()");
-        }
-
-        try {
-            values[n] = value;
-            sorted = false;
-        } catch (ArrayIndexOutOfBoundsException ex) {
-            // Translate the exception.
-            if (n < 0) {
-                throw new IllegalArgumentException("n < 0");
-            }
-        }
-    }
-
-    /**
-     * Adds an element to the end of the list. This will increase the
-     * list's capacity if necessary.
-     *
-     * @param value the value to add
-     */
-    public void add(int value) {
-        throwIfImmutable();
-
-        growIfNeeded();
-
-        values[size++] = value;
-
-        if (sorted && (size > 1)) {
-            sorted = (value >= values[size - 2]);
-        }
-    }
-
-    /**
-     * Inserts element into specified index, moving elements at and above
-     * that index up one. May not be used to insert at an index beyond the
-     * current size (that is, insertion as a last element is legal but
-     * no further).
-     *
-     * @param n {@code >= 0, <=size();} index of where to insert
-     * @param value value to insert
-     */
-    public void insert(int n, int value) {
-        if (n > size) {
-            throw new IndexOutOfBoundsException("n > size()");
-        }
-
-        growIfNeeded();
-
-        System.arraycopy (values, n, values, n+1, size - n);
-        values[n] = value;
-        size++;
-
-        sorted = sorted
-                && (n == 0 || value > values[n-1])
-                && (n == (size - 1) || value < values[n+1]);
-    }
-
-    /**
-     * Removes an element at a given index, shifting elements at greater
-     * indicies down one.
-     *
-     * @param n  {@code >=0, < size();} index of element to remove
-     */
-    public void removeIndex(int n) {
-        if (n >= size) {
-            throw new IndexOutOfBoundsException("n >= size()");
-        }
-
-        System.arraycopy (values, n + 1, values, n, size - n - 1);
-        size--;
-
-        // sort status is unchanged
-    }
-
-    /**
-     * Increases size of array if needed
-     */
-    private void growIfNeeded() {
-        if (size == values.length) {
-            // Resize.
-            int[] newv = new int[size * 3 / 2 + 10];
-            System.arraycopy(values, 0, newv, 0, size);
-            values = newv;
-        }
-    }
-
-    /**
-     * Returns the last element in the array without modifying the array
-     *
-     * @return last value in the array
-     * @throws IndexOutOfBoundsException if stack is empty
-     */
-    public int top() {
-        return get(size - 1);
-    }
-
-    /**
-     * Pops an element off the end of the list and decreasing the size by one.
-     *
-     * @return value from what was the last element
-     * @throws IndexOutOfBoundsException if stack is empty
-     */
-    public int pop() {
-        throwIfImmutable();
-
-        int result;
-
-        result = get(size-1);
-        size--;
-
-        return result;
-    }
-
-    /**
-     * Pops N elements off the end of the list and decreasing the size by N.
-     *
-     * @param n {@code >= 0;} number of elements to remove from end
-     * @throws IndexOutOfBoundsException if stack is smaller than N
-     */
-    public void pop(int n) {
-        throwIfImmutable();
-
-        size -= n;
-    }
-
-    /**
-     * Shrinks the size of the list.
-     *
-     * @param newSize {@code >= 0;} the new size
-     */
-    public void shrink(int newSize) {
-        if (newSize < 0) {
-            throw new IllegalArgumentException("newSize < 0");
-        }
-
-        if (newSize > size) {
-            throw new IllegalArgumentException("newSize > size");
-        }
-
-        throwIfImmutable();
-
-        size = newSize;
-    }
-
-    /**
-     * Makes and returns a mutable copy of the list.
-     *
-     * @return {@code non-null;} an appropriately-constructed instance
-     */
-    public IntList mutableCopy() {
-        int sz = size;
-        IntList result = new IntList(sz);
-
-        for (int i = 0; i < sz; i++) {
-            result.add(values[i]);
-        }
-
-        return result;
-    }
-
-    /**
-     * Sorts the elements in the list in-place.
-     */
-    public void sort() {
-        throwIfImmutable();
-
-        if (!sorted) {
-            Arrays.sort(values, 0, size);
-            sorted = true;
-        }
-    }
-
-    /**
-     * Returns the index of the given value, or -1 if the value does not
-     * appear in the list.  This will do a binary search if the list is
-     * sorted or a linear search if not.
-     *
-     * @param value value to find
-     * @return index of value or -1
-     */
-    public int indexOf(int value) {
-        int ret = binarysearch(value);
-
-        return ret >= 0 ? ret : -1;
-
-    }
-
-    /**
-     * Performs a binary search on a sorted list, returning the index of
-     * the given value if it is present or
-     * {@code (-(insertion point) - 1)} if the value is not present.
-     * If the list is not sorted, then reverts to linear search and returns
-     * {@code -size()} if the element is not found.
-     *
-     * @param value value to find
-     * @return index of value or {@code (-(insertion point) - 1)} if the
-     * value is not present
-     */
-    public int binarysearch(int value) {
-        int sz = size;
-
-        if (!sorted) {
-            // Linear search.
-            for (int i = 0; i < sz; i++) {
-                if (values[i] == value) {
-                    return i;
-                }
-            }
-
-            return -sz;
-        }
-
-        /*
-         * Binary search. This variant does only one value comparison
-         * per iteration but does one more iteration on average than
-         * the variant that includes a value equality check per
-         * iteration.
-         */
-
-        int min = -1;
-        int max = sz;
-
-        while (max > (min + 1)) {
-            /*
-             * The guessIdx calculation is equivalent to ((min + max)
-             * / 2) but won't go wonky when min and max are close to
-             * Integer.MAX_VALUE.
-             */
-            int guessIdx = min + ((max - min) >> 1);
-            int guess = values[guessIdx];
-
-            if (value <= guess) {
-                max = guessIdx;
-            } else {
-                min = guessIdx;
-            }
-        }
-
-        if ((max != sz)) {
-            return (value == values[max]) ? max : (-max - 1);
-        } else {
-            return -sz - 1;
-        }
-    }
-
-
-    /**
-     * Returns whether or not the given value appears in the list.
-     * This will do a binary search if the list is sorted or a linear
-     * search if not.
-     *
-     * @see #sort
-     *
-     * @param value value to look for
-     * @return whether the list contains the given value
-     */
-    public boolean contains(int value) {
-        return indexOf(value) >= 0;
-    }
+  /**
+   * Returns whether or not the given value appears in the list.
+   * This will do a binary search if the list is sorted or a linear
+   * search if not.
+   *
+   * @see #sort
+   *
+   * @param value value to look for
+   * @return whether the list contains the given value
+   */
+  public boolean contains(int value) {
+    return indexOf(value) >= 0;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/IntSet.java b/dx/src/com/android/jack/dx/util/IntSet.java
index 9d056fe..71fc7d3 100644
--- a/dx/src/com/android/jack/dx/util/IntSet.java
+++ b/dx/src/com/android/jack/dx/util/IntSet.java
@@ -21,47 +21,47 @@
  */
 public interface IntSet {
 
-    /**
-     * Adds an int to a set
-     *
-     * @param value int to add
-     */
-    void add(int value);
+  /**
+   * Adds an int to a set
+   *
+   * @param value int to add
+   */
+  void add(int value);
 
-    /**
-     * Removes an int from a set.
-     *
-     * @param value int to remove
-     */
-    void remove(int value);
+  /**
+   * Removes an int from a set.
+   *
+   * @param value int to remove
+   */
+  void remove(int value);
 
-    /**
-     * Checks to see if a value is in the set
-     *
-     * @param value int to check
-     * @return true if in set
-     */
-    boolean has(int value);
+  /**
+   * Checks to see if a value is in the set
+   *
+   * @param value int to check
+   * @return true if in set
+   */
+  boolean has(int value);
 
-    /**
-     * Merges {@code other} into this set, so this set becomes the
-     * union of the two.
-     *
-     * @param other {@code non-null;} other set to merge with.
-     */
-    void merge(IntSet other);
+  /**
+   * Merges {@code other} into this set, so this set becomes the
+   * union of the two.
+   *
+   * @param other {@code non-null;} other set to merge with.
+   */
+  void merge(IntSet other);
 
-    /**
-     * Returns the count of unique elements in this set.
-     *
-     * @return {@code > = 0;} count of unique elements
-     */
-    int elements();
+  /**
+   * Returns the count of unique elements in this set.
+   *
+   * @return {@code > = 0;} count of unique elements
+   */
+  int elements();
 
-    /**
-     * Iterates the set
-     *
-     * @return {@code non-null;} a set iterator
-     */
-    IntIterator iterator();
+  /**
+   * Iterates the set
+   *
+   * @return {@code non-null;} a set iterator
+   */
+  IntIterator iterator();
 }
diff --git a/dx/src/com/android/jack/dx/util/LabeledItem.java b/dx/src/com/android/jack/dx/util/LabeledItem.java
index 3883e38..d609c40 100644
--- a/dx/src/com/android/jack/dx/util/LabeledItem.java
+++ b/dx/src/com/android/jack/dx/util/LabeledItem.java
@@ -21,10 +21,10 @@
  */
 public interface LabeledItem {
 
-    /*
-     * Gets the label of this block.
-     *
-     * @return {@code >= 0;} the label
-     */
-    public int getLabel();
+  /*
+   * Gets the label of this block.
+   *
+   * @return {@code >= 0;} the label
+   */
+  public int getLabel();
 }
diff --git a/dx/src/com/android/jack/dx/util/LabeledList.java b/dx/src/com/android/jack/dx/util/LabeledList.java
index 323d997..3432e2c 100644
--- a/dx/src/com/android/jack/dx/util/LabeledList.java
+++ b/dx/src/com/android/jack/dx/util/LabeledList.java
@@ -22,166 +22,167 @@
  * A list of labeled items, allowing easy lookup by label.
  */
 public class LabeledList extends FixedSizeList {
-    /**
-     * Sparse array indexed by label to FixedSizeList index;
-     * {@code -1} for an invalid label.
-     */
-    private final IntList labelToIndex;
+  /**
+   * Sparse array indexed by label to FixedSizeList index;
+   * {@code -1} for an invalid label.
+   */
+  private final IntList labelToIndex;
 
-    /** @inheritDoc */
-    public LabeledList(int size) {
-        super(size);
+  /** @inheritDoc */
+  public LabeledList(int size) {
+    super(size);
 
-        labelToIndex = new IntList(size);
+    labelToIndex = new IntList(size);
+  }
+
+  /**
+   * Constructs a new instance that is a copy of the old instance.
+   *
+   * @param old instance to copy
+   */
+  public LabeledList(LabeledList old) {
+    super(old.size());
+    labelToIndex = old.labelToIndex.mutableCopy();
+
+    int sz = old.size();
+
+    for (int i = 0; i < sz; i++) {
+      Object one = old.get0(i);
+      if (one != null) {
+        set0(i, one);
+      }
+    }
+  }
+
+  /**
+   * Gets the maximum label (exclusive) of any block added to this instance.
+   *
+   * @return {@code >= 0;} the maximum label
+   */
+  public final int getMaxLabel() {
+    int sz = labelToIndex.size();
+
+    // Gobble any deleted labels that may be at the end.
+    int i;
+    for (i = sz - 1; (i >= 0) && (labelToIndex.get(i) < 0); i--) {
+      /* empty */
     }
 
-    /**
-     * Constructs a new instance that is a copy of the old instance.
-     *
-     * @param old instance to copy
-     */
-    public LabeledList(LabeledList old) {
-        super(old.size());
-        labelToIndex = old.labelToIndex.mutableCopy();
+    int newSize = i + 1;
 
-        int sz = old.size();
+    labelToIndex.shrink(newSize);
 
-        for (int i = 0; i < sz; i++) {
-            Object one = old.get0(i);
-            if (one != null) {
-                set0(i, one);
-            }
-        }
+    return newSize;
+  }
+
+  /**
+   * Removes a label from the label-to-index mapping.
+   *
+   * @param oldLabel label to remove
+   */
+  private void removeLabel(int oldLabel) {
+    labelToIndex.set(oldLabel, -1);
+  }
+
+  /**
+   * Adds a label and index to the label-to-index mapping.
+   *
+   * @param label new label
+   * @param index index of block.
+   */
+  private void addLabelIndex(int label, int index) {
+    int origSz = labelToIndex.size();
+
+    for (int i = 0; i <= (label - origSz); i++) {
+      labelToIndex.add(-1);
     }
 
-    /**
-     * Gets the maximum label (exclusive) of any block added to this instance.
-     *
-     * @return {@code >= 0;} the maximum label
-     */
-    public final int getMaxLabel() {
-        int sz = labelToIndex.size();
+    labelToIndex.set(label, index);
+  }
 
-        // Gobble any deleted labels that may be at the end.
-        int i;
-        for (i = sz - 1; (i >= 0) && (labelToIndex.get(i) < 0); i--)
-            /*empty*/ ;
+  /**
+   * Gets the index of the first item in the list with the given
+   * label, if any.
+   *
+   * @param label {@code >= 0;} the label to look for
+   * @return {@code >= -1;} the index of the so-labelled item, or {@code -1}
+   * if none is found
+   */
+  public final int indexOfLabel(int label) {
+    if (label >= labelToIndex.size()) {
+      return -1;
+    } else {
+      return labelToIndex.get(label);
+    }
+  }
 
-        int newSize = i + 1;
+  /**
+   * Gets an array containing all of the labels used in this instance,
+   * in order. The returned array is freshly-allocated and so may be
+   * modified safely by the caller without impacting this instance.
+   *
+   * @return {@code non-null;} ordered array of labels
+   * @throws NullPointerException thrown if there are any {@code null}
+   * items in this instance
+   */
+  public final int[] getLabelsInOrder() {
+    int sz = size();
+    int[] result = new int[sz];
 
-        labelToIndex.shrink(newSize);
-
-        return newSize;
+    for (int i = 0; i < sz; i++) {
+      LabeledItem li = (LabeledItem) get0(i);
+      if (li == null) {
+        throw new NullPointerException("null at index " + i);
+      }
+      result[i] = li.getLabel();
     }
 
-    /**
-     * Removes a label from the label-to-index mapping.
-     *
-     * @param oldLabel label to remove
-     */
-    private void removeLabel(int oldLabel) {
-        labelToIndex.set(oldLabel, -1);
+    Arrays.sort(result);
+    return result;
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void shrinkToFit() {
+    super.shrinkToFit();
+
+    rebuildLabelToIndex();
+  }
+
+  /**
+   * Rebuilds the label-to-index mapping after a {@code shrinkToFit()}.
+   * Note: This assumes that the labels that are in the list are the
+   * same, although the indicies may have changed.
+   */
+  private void rebuildLabelToIndex() {
+    int szItems = size();
+
+    for (int i = 0; i < szItems; i++) {
+      LabeledItem li = (LabeledItem) get0(i);
+
+      if (li != null) {
+        labelToIndex.set(li.getLabel(), i);
+      }
+    }
+  }
+
+  /**
+   * Sets the element at the given index.
+   *
+   * @param n {@code >= 0, < size();} which element
+   * @param item {@code null-ok;} the value to store
+   */
+  protected void set(int n, LabeledItem item) {
+    LabeledItem old = (LabeledItem) getOrNull0(n);
+
+    set0(n, item);
+
+    if (old != null) {
+      removeLabel(old.getLabel());
     }
 
-    /**
-     * Adds a label and index to the label-to-index mapping.
-     *
-     * @param label new label
-     * @param index index of block.
-     */
-    private void addLabelIndex(int label, int index) {
-        int origSz = labelToIndex.size();
-
-        for (int i = 0; i <= (label - origSz); i++) {
-            labelToIndex.add(-1);
-        }
-
-        labelToIndex.set(label, index);
+    if (item != null) {
+      addLabelIndex(item.getLabel(), n);
     }
-
-    /**
-     * Gets the index of the first item in the list with the given
-     * label, if any.
-     *
-     * @param label {@code >= 0;} the label to look for
-     * @return {@code >= -1;} the index of the so-labelled item, or {@code -1}
-     * if none is found
-     */
-    public final int indexOfLabel(int label) {
-        if (label >= labelToIndex.size()) {
-            return -1;
-        } else {
-            return labelToIndex.get(label);
-        }
-    }
-
-    /**
-     * Gets an array containing all of the labels used in this instance,
-     * in order. The returned array is freshly-allocated and so may be
-     * modified safely by the caller without impacting this instance.
-     *
-     * @return {@code non-null;} ordered array of labels
-     * @throws NullPointerException thrown if there are any {@code null}
-     * items in this instance
-     */
-    public final int[] getLabelsInOrder() {
-        int sz = size();
-        int[] result = new int[sz];
-
-        for (int i = 0; i < sz; i++) {
-            LabeledItem li = (LabeledItem) get0(i);
-            if (li == null) {
-                throw new NullPointerException("null at index " + i);
-            }
-            result[i] = li.getLabel();
-        }
-
-        Arrays.sort(result);
-        return result;
-    }
-
-    /** @inheritDoc */
-    @Override
-    public void shrinkToFit() {
-        super.shrinkToFit();
-
-        rebuildLabelToIndex();
-    }
-
-    /**
-     * Rebuilds the label-to-index mapping after a {@code shrinkToFit()}.
-     * Note: This assumes that the labels that are in the list are the
-     * same, although the indicies may have changed.
-     */
-    private void rebuildLabelToIndex() {
-        int szItems = size();
-
-        for (int i = 0; i < szItems; i++) {
-            LabeledItem li = (LabeledItem) get0(i);
-
-            if (li != null) {
-                labelToIndex.set(li.getLabel(), i);
-            }
-        }
-    }
-
-    /**
-     * Sets the element at the given index.
-     *
-     * @param n {@code >= 0, < size();} which element
-     * @param item {@code null-ok;} the value to store
-     */
-    protected void set(int n, LabeledItem item) {
-        LabeledItem old = (LabeledItem) getOrNull0(n);
-
-        set0(n, item);
-
-        if (old != null) {
-            removeLabel(old.getLabel());
-        }
-
-        if (item != null) {
-            addLabelIndex(item.getLabel(), n);
-        }
-    }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Leb128Utils.java b/dx/src/com/android/jack/dx/util/Leb128Utils.java
index f6d85d1..9b5ee78 100644
--- a/dx/src/com/android/jack/dx/util/Leb128Utils.java
+++ b/dx/src/com/android/jack/dx/util/Leb128Utils.java
@@ -21,142 +21,140 @@
  * section 7.6.
  */
 public final class Leb128Utils {
-    /**
-     * This class is uninstantiable.
-     */
-    private Leb128Utils() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private Leb128Utils() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Gets the number of bytes in the unsigned LEB128 encoding of the
+   * given value.
+   *
+   * @param value the value in question
+   * @return its write size, in bytes
+   */
+  public static int unsignedLeb128Size(int value) {
+    // TODO(dx team): This could be much cleverer.
+
+    int remaining = value >> 7;
+    int count = 0;
+
+    while (remaining != 0) {
+      remaining >>= 7;
+      count++;
     }
 
-    /**
-     * Gets the number of bytes in the unsigned LEB128 encoding of the
-     * given value.
-     *
-     * @param value the value in question
-     * @return its write size, in bytes
-     */
-    public static int unsignedLeb128Size(int value) {
-        // TODO: This could be much cleverer.
+    return count + 1;
+  }
 
-        int remaining = value >> 7;
-        int count = 0;
+  /**
+   * Gets the number of bytes in the signed LEB128 encoding of the
+   * given value.
+   *
+   * @param value the value in question
+   * @return its write size, in bytes
+   */
+  public static int signedLeb128Size(int value) {
+    // TODO(dx team): This could be much cleverer.
 
-        while (remaining != 0) {
-            remaining >>= 7;
-            count++;
-        }
+    int remaining = value >> 7;
+    int count = 0;
+    boolean hasMore = true;
+    int end = ((value & Integer.MIN_VALUE) == 0) ? 0 : -1;
 
-        return count + 1;
+    while (hasMore) {
+      hasMore = (remaining != end) || ((remaining & 1) != ((value >> 6) & 1));
+
+      value = remaining;
+      remaining >>= 7;
+      count++;
     }
 
-    /**
-     * Gets the number of bytes in the signed LEB128 encoding of the
-     * given value.
-     *
-     * @param value the value in question
-     * @return its write size, in bytes
-     */
-    public static int signedLeb128Size(int value) {
-        // TODO: This could be much cleverer.
+    return count;
+  }
 
-        int remaining = value >> 7;
-        int count = 0;
-        boolean hasMore = true;
-        int end = ((value & Integer.MIN_VALUE) == 0) ? 0 : -1;
+  /**
+   * Reads an signed integer from {@code in}.
+   */
+  public static int readSignedLeb128(ByteInput in) {
+    int result = 0;
+    int cur;
+    int count = 0;
+    int signBits = -1;
 
-        while (hasMore) {
-            hasMore = (remaining != end)
-                || ((remaining & 1) != ((value >> 6) & 1));
+    do {
+      cur = in.readByte() & 0xff;
+      result |= (cur & 0x7f) << (count * 7);
+      signBits <<= 7;
+      count++;
+    } while (((cur & 0x80) == 0x80) && count < 5);
 
-            value = remaining;
-            remaining >>= 7;
-            count++;
-        }
-
-        return count;
+    if ((cur & 0x80) == 0x80) {
+      throw new DexException("invalid LEB128 sequence");
     }
 
-    /**
-     * Reads an signed integer from {@code in}.
-     */
-    public static int readSignedLeb128(ByteInput in) {
-        int result = 0;
-        int cur;
-        int count = 0;
-        int signBits = -1;
-
-        do {
-            cur = in.readByte() & 0xff;
-            result |= (cur & 0x7f) << (count * 7);
-            signBits <<= 7;
-            count++;
-        } while (((cur & 0x80) == 0x80) && count < 5);
-
-        if ((cur & 0x80) == 0x80) {
-            throw new DexException("invalid LEB128 sequence");
-        }
-
-        // Sign extend if appropriate
-        if (((signBits >> 1) & result) != 0 ) {
-            result |= signBits;
-        }
-
-        return result;
+    // Sign extend if appropriate
+    if (((signBits >> 1) & result) != 0) {
+      result |= signBits;
     }
 
-    /**
-     * Reads an unsigned integer from {@code in}.
-     */
-    public static int readUnsignedLeb128(ByteInput in) {
-        int result = 0;
-        int cur;
-        int count = 0;
+    return result;
+  }
 
-        do {
-            cur = in.readByte() & 0xff;
-            result |= (cur & 0x7f) << (count * 7);
-            count++;
-        } while (((cur & 0x80) == 0x80) && count < 5);
+  /**
+   * Reads an unsigned integer from {@code in}.
+   */
+  public static int readUnsignedLeb128(ByteInput in) {
+    int result = 0;
+    int cur;
+    int count = 0;
 
-        if ((cur & 0x80) == 0x80) {
-            throw new DexException("invalid LEB128 sequence");
-        }
+    do {
+      cur = in.readByte() & 0xff;
+      result |= (cur & 0x7f) << (count * 7);
+      count++;
+    } while (((cur & 0x80) == 0x80) && count < 5);
 
-        return result;
+    if ((cur & 0x80) == 0x80) {
+      throw new DexException("invalid LEB128 sequence");
     }
 
-    /**
-     * Writes {@code value} as an unsigned integer to {@code out}, starting at
-     * {@code offset}. Returns the number of bytes written.
-     */
-    public static void writeUnsignedLeb128(ByteOutput out, int value) {
-        int remaining = value >>> 7;
+    return result;
+  }
 
-        while (remaining != 0) {
-            out.writeByte((byte) ((value & 0x7f) | 0x80));
-            value = remaining;
-            remaining >>>= 7;
-        }
+  /**
+   * Writes {@code value} as an unsigned integer to {@code out}, starting at
+   * {@code offset}. Returns the number of bytes written.
+   */
+  public static void writeUnsignedLeb128(ByteOutput out, int value) {
+    int remaining = value >>> 7;
 
-        out.writeByte((byte) (value & 0x7f));
+    while (remaining != 0) {
+      out.writeByte((byte) ((value & 0x7f) | 0x80));
+      value = remaining;
+      remaining >>>= 7;
     }
 
-    /**
-     * Writes {@code value} as a signed integer to {@code out}, starting at
-     * {@code offset}. Returns the number of bytes written.
-     */
-    public static void writeSignedLeb128(ByteOutput out, int value) {
-        int remaining = value >> 7;
-        boolean hasMore = true;
-        int end = ((value & Integer.MIN_VALUE) == 0) ? 0 : -1;
+    out.writeByte((byte) (value & 0x7f));
+  }
 
-        while (hasMore) {
-            hasMore = (remaining != end)
-                    || ((remaining & 1) != ((value >> 6) & 1));
+  /**
+   * Writes {@code value} as a signed integer to {@code out}, starting at
+   * {@code offset}. Returns the number of bytes written.
+   */
+  public static void writeSignedLeb128(ByteOutput out, int value) {
+    int remaining = value >> 7;
+    boolean hasMore = true;
+    int end = ((value & Integer.MIN_VALUE) == 0) ? 0 : -1;
 
-            out.writeByte((byte) ((value & 0x7f) | (hasMore ? 0x80 : 0)));
-            value = remaining;
-            remaining >>= 7;
-        }
+    while (hasMore) {
+      hasMore = (remaining != end) || ((remaining & 1) != ((value >> 6) & 1));
+
+      out.writeByte((byte) ((value & 0x7f) | (hasMore ? 0x80 : 0)));
+      value = remaining;
+      remaining >>= 7;
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/ListIntSet.java b/dx/src/com/android/jack/dx/util/ListIntSet.java
index 36f1891..bae44e8 100644
--- a/dx/src/com/android/jack/dx/util/ListIntSet.java
+++ b/dx/src/com/android/jack/dx/util/ListIntSet.java
@@ -23,110 +23,119 @@
  */
 public class ListIntSet implements IntSet {
 
-    /** also accessed in BitIntSet */
-    final IntList ints;
+  /** also accessed in BitIntSet */
+  final IntList ints;
 
-    /**
-     * Constructs an instance
-     */
-    public ListIntSet() {
-        ints = new IntList();
-        ints.sort();
+  /**
+   * Constructs an instance
+   */
+  public ListIntSet() {
+    ints = new IntList();
+    ints.sort();
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void add(int value) {
+    int index = ints.binarysearch(value);
+
+    if (index < 0) {
+      ints.insert(-(index + 1), value);
     }
+  }
 
-    /** @inheritDoc */
-    public void add(int value) {
-        int index = ints.binarysearch(value);
+  /** @inheritDoc */
+  @Override
+  public void remove(int value) {
+    int index = ints.indexOf(value);
 
-        if (index < 0) {
-            ints.insert(-(index + 1), value);
+    if (index >= 0) {
+      ints.removeIndex(index);
+    }
+  }
+
+  /** @inheritDoc */
+  @Override
+  public boolean has(int value) {
+    return ints.indexOf(value) >= 0;
+  }
+
+  /** @inheritDoc */
+  @Override
+  public void merge(IntSet other) {
+    if (other instanceof ListIntSet) {
+      ListIntSet o = (ListIntSet) other;
+      int szThis = ints.size();
+      int szOther = o.ints.size();
+
+      int i = 0;
+      int j = 0;
+
+      while (j < szOther && i < szThis) {
+        while (j < szOther && o.ints.get(j) < ints.get(i)) {
+          add(o.ints.get(j++));
         }
-    }
-
-    /** @inheritDoc */
-    public void remove(int value) {
-        int index = ints.indexOf(value);
-
-        if (index >= 0) {
-            ints.removeIndex(index);
+        if (j == szOther) {
+          break;
         }
-    }
-
-    /** @inheritDoc */
-    public boolean has(int value) {
-        return ints.indexOf(value) >= 0;
-    }
-
-    /** @inheritDoc */
-    public void merge(IntSet other) {
-        if (other instanceof ListIntSet) {
-            ListIntSet o = (ListIntSet) other;
-            int szThis = ints.size();
-            int szOther = o.ints.size();
-
-            int i = 0;
-            int j = 0;
-
-            while (j < szOther && i < szThis) {
-                while (j < szOther && o.ints.get(j) < ints.get(i)) {
-                    add(o.ints.get(j++));
-                }
-                if (j == szOther) {
-                    break;
-                }
-                while (i < szThis && o.ints.get(j) >= ints.get(i)) {
-                    i++;
-                }
-            }
-
-            while (j < szOther) {
-                add(o.ints.get(j++));
-            }
-
-            ints.sort();
-        } else if (other instanceof BitIntSet) {
-            BitIntSet o = (BitIntSet) other;
-
-            for (int i = 0; i >= 0; i = Bits.findFirst(o.bits, i + 1)) {
-                ints.add(i);
-            }
-            ints.sort();
-        } else {
-            IntIterator iter = other.iterator();
-            while (iter.hasNext()) {
-                add(iter.next());
-            }
+        while (i < szThis && o.ints.get(j) >= ints.get(i)) {
+          i++;
         }
+      }
+
+      while (j < szOther) {
+        add(o.ints.get(j++));
+      }
+
+      ints.sort();
+    } else if (other instanceof BitIntSet) {
+      BitIntSet o = (BitIntSet) other;
+
+      for (int i = 0; i >= 0; i = Bits.findFirst(o.bits, i + 1)) {
+        ints.add(i);
+      }
+      ints.sort();
+    } else {
+      IntIterator iter = other.iterator();
+      while (iter.hasNext()) {
+        add(iter.next());
+      }
     }
+  }
 
-    /** @inheritDoc */
-    public int elements() {
-        return ints.size();
-    }
+  /** @inheritDoc */
+  @Override
+  public int elements() {
+    return ints.size();
+  }
 
-    /** @inheritDoc */
-    public IntIterator iterator() {
-        return new IntIterator() {
-            private int idx = 0;
+  /** @inheritDoc */
+  @Override
+  public IntIterator iterator() {
+    return new IntIterator() {
+      private int idx = 0;
 
-            /** @inheritDoc */
-            public boolean hasNext() {
-                return idx < ints.size();
-            }
+      /** @inheritDoc */
+      @Override
+      public boolean hasNext() {
+        return idx < ints.size();
+      }
 
-            /** @inheritDoc */
-            public int next() {
-                if (!hasNext()) {
-                    throw new NoSuchElementException();
-                }
+      /** @inheritDoc */
+      @Override
+      public int next() {
+        if (!hasNext()) {
+          throw new NoSuchElementException();
+        }
 
-                return ints.get(idx++);
-            }
-        };
-    }
+        return ints.get(idx++);
+      }
+    };
+  }
 
-    /** @inheritDoc */
-    public String toString() {
-        return ints.toString();
-    }
+  /** @inheritDoc */
+  @Override
+  public String toString() {
+    return ints.toString();
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/MutabilityControl.java b/dx/src/com/android/jack/dx/util/MutabilityControl.java
index d716ffe..9e56656 100644
--- a/dx/src/com/android/jack/dx/util/MutabilityControl.java
+++ b/dx/src/com/android/jack/dx/util/MutabilityControl.java
@@ -23,67 +23,67 @@
  * to the checker in all the right places.
  */
 public class MutabilityControl {
-    /** whether this instance is mutable */
-    private boolean mutable;
+  /** whether this instance is mutable */
+  private boolean mutable;
 
-    /**
-     * Constructs an instance. It is initially mutable.
-     */
-    public MutabilityControl() {
-        mutable = true;
-    }
+  /**
+   * Constructs an instance. It is initially mutable.
+   */
+  public MutabilityControl() {
+    mutable = true;
+  }
 
-    /**
-     * Constructs an instance, explicitly indicating the mutability.
-     *
-     * @param mutable {@code true} iff this instance is mutable
-     */
-    public MutabilityControl(boolean mutable) {
-        this.mutable = mutable;
-    }
+  /**
+   * Constructs an instance, explicitly indicating the mutability.
+   *
+   * @param mutable {@code true} iff this instance is mutable
+   */
+  public MutabilityControl(boolean mutable) {
+    this.mutable = mutable;
+  }
 
-    /**
-     * Makes this instance immutable.
-     */
-    public void setImmutable() {
-        mutable = false;
-    }
+  /**
+   * Makes this instance immutable.
+   */
+  public void setImmutable() {
+    mutable = false;
+  }
 
-    /**
-     * Checks to see whether or not this instance is immutable. This is the
-     * same as calling {@code !isMutable()}.
-     *
-     * @return {@code true} iff this instance is immutable
-     */
-    public final boolean isImmutable() {
-        return !mutable;
-    }
+  /**
+   * Checks to see whether or not this instance is immutable. This is the
+   * same as calling {@code !isMutable()}.
+   *
+   * @return {@code true} iff this instance is immutable
+   */
+  public final boolean isImmutable() {
+    return !mutable;
+  }
 
-    /**
-     * Checks to see whether or not this instance is mutable.
-     *
-     * @return {@code true} iff this instance is mutable
-     */
-    public final boolean isMutable() {
-        return mutable;
-    }
+  /**
+   * Checks to see whether or not this instance is mutable.
+   *
+   * @return {@code true} iff this instance is mutable
+   */
+  public final boolean isMutable() {
+    return mutable;
+  }
 
-    /**
-     * Throws {@link MutabilityException} if this instance is
-     * immutable.
-     */
-    public final void throwIfImmutable() {
-        if (!mutable) {
-            throw new MutabilityException("immutable instance");
-        }
+  /**
+   * Throws {@link MutabilityException} if this instance is
+   * immutable.
+   */
+  public final void throwIfImmutable() {
+    if (!mutable) {
+      throw new MutabilityException("immutable instance");
     }
+  }
 
-    /**
-     * Throws {@link MutabilityException} if this instance is mutable.
-     */
-    public final void throwIfMutable() {
-        if (mutable) {
-            throw new MutabilityException("mutable instance");
-        }
+  /**
+   * Throws {@link MutabilityException} if this instance is mutable.
+   */
+  public final void throwIfMutable() {
+    if (mutable) {
+      throw new MutabilityException("mutable instance");
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/MutabilityException.java b/dx/src/com/android/jack/dx/util/MutabilityException.java
index 7e59883..b13a7d7 100644
--- a/dx/src/com/android/jack/dx/util/MutabilityException.java
+++ b/dx/src/com/android/jack/dx/util/MutabilityException.java
@@ -19,17 +19,19 @@
 /**
  * Exception due to a mutability problem.
  */
-public class MutabilityException
-        extends ExceptionWithContext {
-    public MutabilityException(String message) {
-        super(message);
-    }
+public class MutabilityException extends ExceptionWithContext {
 
-    public MutabilityException(Throwable cause) {
-        super(cause);
-    }
+  private static final long serialVersionUID = 1L;
 
-    public MutabilityException(String message, Throwable cause) {
-        super(message, cause);
-    }
+  public MutabilityException(String message) {
+    super(message);
+  }
+
+  public MutabilityException(Throwable cause) {
+    super(cause);
+  }
+
+  public MutabilityException(String message, Throwable cause) {
+    super(message, cause);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Mutf8.java b/dx/src/com/android/jack/dx/util/Mutf8.java
index 5f01693..e279525 100644
--- a/dx/src/com/android/jack/dx/util/Mutf8.java
+++ b/dx/src/com/android/jack/dx/util/Mutf8.java
@@ -24,91 +24,91 @@
  * <p>Derived from libcore's MUTF-8 encoder at java.nio.charset.ModifiedUtf8.
  */
 public final class Mutf8 {
-    private Mutf8() {}
+  private Mutf8() {}
 
-    /**
-     * Decodes bytes from {@code in} into {@code out} until a delimiter 0x00 is
-     * encountered. Returns a new string containing the decoded characters.
-     */
-    public static String decode(ByteInput in, char[] out) throws UTFDataFormatException {
-        int s = 0;
-        while (true) {
-            char a = (char) (in.readByte() & 0xff);
-            if (a == 0) {
-                return new String(out, 0, s);
-            }
-            out[s] = a;
-            if (a < '\u0080') {
-                s++;
-            } else if ((a & 0xe0) == 0xc0) {
-                int b = in.readByte() & 0xff;
-                if ((b & 0xC0) != 0x80) {
-                    throw new UTFDataFormatException("bad second byte");
-                }
-                out[s++] = (char) (((a & 0x1F) << 6) | (b & 0x3F));
-            } else if ((a & 0xf0) == 0xe0) {
-                int b = in.readByte() & 0xff;
-                int c = in.readByte() & 0xff;
-                if (((b & 0xC0) != 0x80) || ((c & 0xC0) != 0x80)) {
-                    throw new UTFDataFormatException("bad second or third byte");
-                }
-                out[s++] = (char) (((a & 0x0F) << 12) | ((b & 0x3F) << 6) | (c & 0x3F));
-            } else {
-                throw new UTFDataFormatException("bad byte");
-            }
+  /**
+   * Decodes bytes from {@code in} into {@code out} until a delimiter 0x00 is
+   * encountered. Returns a new string containing the decoded characters.
+   */
+  public static String decode(ByteInput in, char[] out) throws UTFDataFormatException {
+    int s = 0;
+    while (true) {
+      char a = (char) (in.readByte() & 0xff);
+      if (a == 0) {
+        return new String(out, 0, s);
+      }
+      out[s] = a;
+      if (a < '\u0080') {
+        s++;
+      } else if ((a & 0xe0) == 0xc0) {
+        int b = in.readByte() & 0xff;
+        if ((b & 0xC0) != 0x80) {
+          throw new UTFDataFormatException("bad second byte");
         }
-    }
-
-    /**
-     * Returns the number of bytes the modified UTF8 representation of 's' would take.
-     */
-    private static long countBytes(String s, boolean shortLength) throws UTFDataFormatException {
-        long result = 0;
-        final int length = s.length();
-        for (int i = 0; i < length; ++i) {
-            char ch = s.charAt(i);
-            if (ch != 0 && ch <= 127) { // U+0000 uses two bytes.
-                ++result;
-            } else if (ch <= 2047) {
-                result += 2;
-            } else {
-                result += 3;
-            }
-            if (shortLength && result > 65535) {
-                throw new UTFDataFormatException("String more than 65535 UTF bytes long");
-            }
+        out[s++] = (char) (((a & 0x1F) << 6) | (b & 0x3F));
+      } else if ((a & 0xf0) == 0xe0) {
+        int b = in.readByte() & 0xff;
+        int c = in.readByte() & 0xff;
+        if (((b & 0xC0) != 0x80) || ((c & 0xC0) != 0x80)) {
+          throw new UTFDataFormatException("bad second or third byte");
         }
-        return result;
+        out[s++] = (char) (((a & 0x0F) << 12) | ((b & 0x3F) << 6) | (c & 0x3F));
+      } else {
+        throw new UTFDataFormatException("bad byte");
+      }
     }
+  }
 
-    /**
-     * Encodes the modified UTF-8 bytes corresponding to {@code s} into  {@code
-     * dst}, starting at {@code offset}.
-     */
-    public static void encode(byte[] dst, int offset, String s) {
-        final int length = s.length();
-        for (int i = 0; i < length; i++) {
-            char ch = s.charAt(i);
-            if (ch != 0 && ch <= 127) { // U+0000 uses two bytes.
-                dst[offset++] = (byte) ch;
-            } else if (ch <= 2047) {
-                dst[offset++] = (byte) (0xc0 | (0x1f & (ch >> 6)));
-                dst[offset++] = (byte) (0x80 | (0x3f & ch));
-            } else {
-                dst[offset++] = (byte) (0xe0 | (0x0f & (ch >> 12)));
-                dst[offset++] = (byte) (0x80 | (0x3f & (ch >> 6)));
-                dst[offset++] = (byte) (0x80 | (0x3f & ch));
-            }
-        }
+  /**
+   * Returns the number of bytes the modified UTF8 representation of 's' would take.
+   */
+  private static long countBytes(String s, boolean shortLength) throws UTFDataFormatException {
+    long result = 0;
+    final int length = s.length();
+    for (int i = 0; i < length; ++i) {
+      char ch = s.charAt(i);
+      if (ch != 0 && ch <= 127) { // U+0000 uses two bytes.
+        ++result;
+      } else if (ch <= 2047) {
+        result += 2;
+      } else {
+        result += 3;
+      }
+      if (shortLength && result > 65535) {
+        throw new UTFDataFormatException("String more than 65535 UTF bytes long");
+      }
     }
+    return result;
+  }
 
-    /**
-     * Returns an array containing the <i>modified UTF-8</i> form of {@code s}.
-     */
-    public static byte[] encode(String s) throws UTFDataFormatException {
-        int utfCount = (int) countBytes(s, true);
-        byte[] result = new byte[utfCount];
-        encode(result, 0, s);
-        return result;
+  /**
+   * Encodes the modified UTF-8 bytes corresponding to {@code s} into  {@code
+   * dst}, starting at {@code offset}.
+   */
+  public static void encode(byte[] dst, int offset, String s) {
+    final int length = s.length();
+    for (int i = 0; i < length; i++) {
+      char ch = s.charAt(i);
+      if (ch != 0 && ch <= 127) { // U+0000 uses two bytes.
+        dst[offset++] = (byte) ch;
+      } else if (ch <= 2047) {
+        dst[offset++] = (byte) (0xc0 | (0x1f & (ch >> 6)));
+        dst[offset++] = (byte) (0x80 | (0x3f & ch));
+      } else {
+        dst[offset++] = (byte) (0xe0 | (0x0f & (ch >> 12)));
+        dst[offset++] = (byte) (0x80 | (0x3f & (ch >> 6)));
+        dst[offset++] = (byte) (0x80 | (0x3f & ch));
+      }
     }
+  }
+
+  /**
+   * Returns an array containing the <i>modified UTF-8</i> form of {@code s}.
+   */
+  public static byte[] encode(String s) throws UTFDataFormatException {
+    int utfCount = (int) countBytes(s, true);
+    byte[] result = new byte[utfCount];
+    encode(result, 0, s);
+    return result;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Output.java b/dx/src/com/android/jack/dx/util/Output.java
index 42640b7..d4a1a59 100644
--- a/dx/src/com/android/jack/dx/util/Output.java
+++ b/dx/src/com/android/jack/dx/util/Output.java
@@ -22,108 +22,109 @@
  * are declared, and multibyte output is defined to be little-endian.
  */
 public interface Output extends ByteOutput {
-    /**
-     * Gets the current cursor position. This is the same as the number of
-     * bytes written to this instance.
-     *
-     * @return {@code >= 0;} the cursor position
-     */
-    public int getCursor();
+  /**
+   * Gets the current cursor position. This is the same as the number of
+   * bytes written to this instance.
+   *
+   * @return {@code >= 0;} the cursor position
+   */
+  public int getCursor();
 
-    /**
-     * Asserts that the cursor is the given value.
-     *
-     * @param expectedCursor the expected cursor value
-     * @throws RuntimeException thrown if {@code getCursor() !=
-     * expectedCursor}
-     */
-    public void assertCursor(int expectedCursor);
+  /**
+   * Asserts that the cursor is the given value.
+   *
+   * @param expectedCursor the expected cursor value
+   * @throws RuntimeException thrown if {@code getCursor() !=
+   * expectedCursor}
+   */
+  public void assertCursor(int expectedCursor);
 
-    /**
-     * Writes a {@code byte} to this instance.
-     *
-     * @param value the value to write; all but the low 8 bits are ignored
-     */
-    public void writeByte(int value);
+  /**
+   * Writes a {@code byte} to this instance.
+   *
+   * @param value the value to write; all but the low 8 bits are ignored
+   */
+  @Override
+  public void writeByte(int value);
 
-    /**
-     * Writes a {@code short} to this instance.
-     *
-     * @param value the value to write; all but the low 16 bits are ignored
-     */
-    public void writeShort(int value);
+  /**
+   * Writes a {@code short} to this instance.
+   *
+   * @param value the value to write; all but the low 16 bits are ignored
+   */
+  public void writeShort(int value);
 
-    /**
-     * Writes an {@code int} to this instance.
-     *
-     * @param value the value to write
-     */
-    public void writeInt(int value);
+  /**
+   * Writes an {@code int} to this instance.
+   *
+   * @param value the value to write
+   */
+  public void writeInt(int value);
 
-    /**
-     * Writes a {@code long} to this instance.
-     *
-     * @param value the value to write
-     */
-    public void writeLong(long value);
+  /**
+   * Writes a {@code long} to this instance.
+   *
+   * @param value the value to write
+   */
+  public void writeLong(long value);
 
-    /**
-     * Writes a DWARFv3-style unsigned LEB128 integer. For details,
-     * see the "Dalvik Executable Format" document or DWARF v3 section
-     * 7.6.
-     *
-     * @param value value to write, treated as an unsigned value
-     * @return {@code 1..5;} the number of bytes actually written
-     */
-    public int writeUleb128(int value);
+  /**
+   * Writes a DWARFv3-style unsigned LEB128 integer. For details,
+   * see the "Dalvik Executable Format" document or DWARF v3 section
+   * 7.6.
+   *
+   * @param value value to write, treated as an unsigned value
+   * @return {@code 1..5;} the number of bytes actually written
+   */
+  public int writeUleb128(int value);
 
-    /**
-     * Writes a DWARFv3-style unsigned LEB128 integer. For details,
-     * see the "Dalvik Executable Format" document or DWARF v3 section
-     * 7.6.
-     *
-     * @param value value to write
-     * @return {@code 1..5;} the number of bytes actually written
-     */
-    public int writeSleb128(int value);
+  /**
+   * Writes a DWARFv3-style unsigned LEB128 integer. For details,
+   * see the "Dalvik Executable Format" document or DWARF v3 section
+   * 7.6.
+   *
+   * @param value value to write
+   * @return {@code 1..5;} the number of bytes actually written
+   */
+  public int writeSleb128(int value);
 
-    /**
-     * Writes a {@link ByteArray} to this instance.
-     *
-     * @param bytes {@code non-null;} the array to write
-     */
-    public void write(ByteArray bytes);
+  /**
+   * Writes a {@link ByteArray} to this instance.
+   *
+   * @param bytes {@code non-null;} the array to write
+   */
+  public void write(ByteArray bytes);
 
-    /**
-     * Writes a portion of a {@code byte[]} to this instance.
-     *
-     * @param bytes {@code non-null;} the array to write
-     * @param offset {@code >= 0;} offset into {@code bytes} for the first
-     * byte to write
-     * @param length {@code >= 0;} number of bytes to write
-     */
-    public void write(byte[] bytes, int offset, int length);
+  /**
+   * Writes a portion of a {@code byte[]} to this instance.
+   *
+   * @param bytes {@code non-null;} the array to write
+   * @param offset {@code >= 0;} offset into {@code bytes} for the first
+   * byte to write
+   * @param length {@code >= 0;} number of bytes to write
+   */
+  public void write(byte[] bytes, int offset, int length);
 
-    /**
-     * Writes a {@code byte[]} to this instance. This is just
-     * a convenient shorthand for {@code write(bytes, 0, bytes.length)}.
-     *
-     * @param bytes {@code non-null;} the array to write
-     */
-    public void write(byte[] bytes);
+  /**
+   * Writes a {@code byte[]} to this instance. This is just
+   * a convenient shorthand for {@code write(bytes, 0, bytes.length)}.
+   *
+   * @param bytes {@code non-null;} the array to write
+   */
+  public void write(byte[] bytes);
 
-    /**
-     * Writes the given number of {@code 0} bytes.
-     *
-     * @param count {@code >= 0;} the number of zeroes to write
-     */
-    public void writeZeroes(int count);
+  /**
+   * Writes the given number of {@code 0} bytes.
+   *
+   * @param count {@code >= 0;} the number of zeroes to write
+   */
+  public void writeZeroes(int count);
 
-    /**
-     * Adds extra bytes if necessary (with value {@code 0}) to
-     * force alignment of the output cursor as given.
-     *
-     * @param alignment {@code > 0;} the alignment; must be a power of two
-     */
-    public void alignTo(int alignment);
+  /**
+   * Adds extra bytes if necessary (with value {@code 0}) to
+   * force alignment of the output cursor as given.
+   *
+   * @param alignment {@code > 0;} the alignment; must be a power of two
+   */
+  public void alignTo(int alignment);
 }
diff --git a/dx/src/com/android/jack/dx/util/ToHuman.java b/dx/src/com/android/jack/dx/util/ToHuman.java
index a74e670..6158789 100644
--- a/dx/src/com/android/jack/dx/util/ToHuman.java
+++ b/dx/src/com/android/jack/dx/util/ToHuman.java
@@ -21,11 +21,11 @@
  * a complete but often hard to read) string form.
  */
 public interface ToHuman {
-    /**
-     * Return the "human" string form of this instance.  This is
-     * generally less "debuggy" than {@code toString()}.
-     *
-     * @return {@code non-null;} the human string form
-     */
-    public String toHuman();
+  /**
+   * Return the "human" string form of this instance.  This is
+   * generally less "debuggy" than {@code toString()}.
+   *
+   * @return {@code non-null;} the human string form
+   */
+  public String toHuman();
 }
diff --git a/dx/src/com/android/jack/dx/util/TwoColumnOutput.java b/dx/src/com/android/jack/dx/util/TwoColumnOutput.java
index afce5bb..204c20f 100644
--- a/dx/src/com/android/jack/dx/util/TwoColumnOutput.java
+++ b/dx/src/com/android/jack/dx/util/TwoColumnOutput.java
@@ -28,227 +28,220 @@
  * one which goes on the right.
  */
 public final class TwoColumnOutput {
-    /** {@code non-null;} underlying writer for final output */
-    private final Writer out;
+  /** {@code non-null;} underlying writer for final output */
+  private final Writer out;
 
-    /** {@code > 0;} the left column width */
-    private final int leftWidth;
+  /** {@code > 0;} the left column width */
+  private final int leftWidth;
 
-    /** {@code non-null;} pending left column output */
-    private final StringBuffer leftBuf;
+  /** {@code non-null;} pending left column output */
+  private final StringBuffer leftBuf;
 
-    /** {@code non-null;} pending right column output */
-    private final StringBuffer rightBuf;
+  /** {@code non-null;} pending right column output */
+  private final StringBuffer rightBuf;
 
-    /** {@code non-null;} left column writer */
-    private final IndentingWriter leftColumn;
+  /** {@code non-null;} left column writer */
+  private final IndentingWriter leftColumn;
 
-    /** {@code non-null;} right column writer */
-    private final IndentingWriter rightColumn;
+  /** {@code non-null;} right column writer */
+  private final IndentingWriter rightColumn;
 
-    /**
-     * Turns the given two strings (with widths) and spacer into a formatted
-     * two-column string.
-     *
-     * @param s1 {@code non-null;} first string
-     * @param width1 {@code > 0;} width of the first column
-     * @param spacer {@code non-null;} spacer string
-     * @param s2 {@code non-null;} second string
-     * @param width2 {@code > 0;} width of the second column
-     * @return {@code non-null;} an appropriately-formatted string
-     */
-    public static String toString(String s1, int width1, String spacer,
-                                  String s2, int width2) {
-        int len1 = s1.length();
-        int len2 = s2.length();
+  /**
+   * Turns the given two strings (with widths) and spacer into a formatted
+   * two-column string.
+   *
+   * @param s1 {@code non-null;} first string
+   * @param width1 {@code > 0;} width of the first column
+   * @param spacer {@code non-null;} spacer string
+   * @param s2 {@code non-null;} second string
+   * @param width2 {@code > 0;} width of the second column
+   * @return {@code non-null;} an appropriately-formatted string
+   */
+  public static String toString(String s1, int width1, String spacer, String s2, int width2) {
+    int len1 = s1.length();
+    int len2 = s2.length();
 
-        StringWriter sw = new StringWriter((len1 + len2) * 3);
-        TwoColumnOutput twoOut =
-            new TwoColumnOutput(sw, width1, width2, spacer);
+    StringWriter sw = new StringWriter((len1 + len2) * 3);
+    TwoColumnOutput twoOut = new TwoColumnOutput(sw, width1, width2, spacer);
 
-        try {
-            twoOut.getLeft().write(s1);
-            twoOut.getRight().write(s2);
-        } catch (IOException ex) {
-            throw new RuntimeException("shouldn't happen", ex);
-        }
-
-        twoOut.flush();
-        return sw.toString();
+    try {
+      twoOut.getLeft().write(s1);
+      twoOut.getRight().write(s2);
+    } catch (IOException ex) {
+      throw new RuntimeException("shouldn't happen", ex);
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param out {@code non-null;} writer to send final output to
-     * @param leftWidth {@code > 0;} width of the left column, in characters
-     * @param rightWidth {@code > 0;} width of the right column, in characters
-     * @param spacer {@code non-null;} spacer string to sit between the two columns
-     */
-    public TwoColumnOutput(Writer out, int leftWidth, int rightWidth,
-                           String spacer) {
-        if (out == null) {
-            throw new NullPointerException("out == null");
-        }
+    twoOut.flush();
+    return sw.toString();
+  }
 
-        if (leftWidth < 1) {
-            throw new IllegalArgumentException("leftWidth < 1");
-        }
-
-        if (rightWidth < 1) {
-            throw new IllegalArgumentException("rightWidth < 1");
-        }
-
-        if (spacer == null) {
-            throw new NullPointerException("spacer == null");
-        }
-
-        StringWriter leftWriter = new StringWriter(1000);
-        StringWriter rightWriter = new StringWriter(1000);
-
-        this.out = out;
-        this.leftWidth = leftWidth;
-        this.leftBuf = leftWriter.getBuffer();
-        this.rightBuf = rightWriter.getBuffer();
-        this.leftColumn = new IndentingWriter(leftWriter, leftWidth);
-        this.rightColumn =
-            new IndentingWriter(rightWriter, rightWidth, spacer);
+  /**
+   * Constructs an instance.
+   *
+   * @param out {@code non-null;} writer to send final output to
+   * @param leftWidth {@code > 0;} width of the left column, in characters
+   * @param rightWidth {@code > 0;} width of the right column, in characters
+   * @param spacer {@code non-null;} spacer string to sit between the two columns
+   */
+  public TwoColumnOutput(Writer out, int leftWidth, int rightWidth, String spacer) {
+    if (out == null) {
+      throw new NullPointerException("out == null");
     }
 
-    /**
-     * Constructs an instance.
-     *
-     * @param out {@code non-null;} stream to send final output to
-     * @param leftWidth {@code >= 1;} width of the left column, in characters
-     * @param rightWidth {@code >= 1;} width of the right column, in characters
-     * @param spacer {@code non-null;} spacer string to sit between the two columns
-     */
-    public TwoColumnOutput(OutputStream out, int leftWidth, int rightWidth,
-                           String spacer) {
-        this(new OutputStreamWriter(out), leftWidth, rightWidth, spacer);
+    if (leftWidth < 1) {
+      throw new IllegalArgumentException("leftWidth < 1");
     }
 
-    /**
-     * Gets the writer to use to write to the left column.
-     *
-     * @return {@code non-null;} the left column writer
-     */
-    public Writer getLeft() {
-        return leftColumn;
+    if (rightWidth < 1) {
+      throw new IllegalArgumentException("rightWidth < 1");
     }
 
-    /**
-     * Gets the writer to use to write to the right column.
-     *
-     * @return {@code non-null;} the right column writer
-     */
-    public Writer getRight() {
-        return rightColumn;
+    if (spacer == null) {
+      throw new NullPointerException("spacer == null");
     }
 
-    /**
-     * Flushes the output. If there are more lines of pending output in one
-     * column, then the other column will get filled with blank lines.
-     */
-    public void flush() {
-        try {
-            appendNewlineIfNecessary(leftBuf, leftColumn);
-            appendNewlineIfNecessary(rightBuf, rightColumn);
-            outputFullLines();
-            flushLeft();
-            flushRight();
-        } catch (IOException ex) {
-            throw new RuntimeException(ex);
-        }
+    StringWriter leftWriter = new StringWriter(1000);
+    StringWriter rightWriter = new StringWriter(1000);
+
+    this.out = out;
+    this.leftWidth = leftWidth;
+    this.leftBuf = leftWriter.getBuffer();
+    this.rightBuf = rightWriter.getBuffer();
+    this.leftColumn = new IndentingWriter(leftWriter, leftWidth);
+    this.rightColumn = new IndentingWriter(rightWriter, rightWidth, spacer);
+  }
+
+  /**
+   * Constructs an instance.
+   *
+   * @param out {@code non-null;} stream to send final output to
+   * @param leftWidth {@code >= 1;} width of the left column, in characters
+   * @param rightWidth {@code >= 1;} width of the right column, in characters
+   * @param spacer {@code non-null;} spacer string to sit between the two columns
+   */
+  public TwoColumnOutput(OutputStream out, int leftWidth, int rightWidth, String spacer) {
+    this(new OutputStreamWriter(out), leftWidth, rightWidth, spacer);
+  }
+
+  /**
+   * Gets the writer to use to write to the left column.
+   *
+   * @return {@code non-null;} the left column writer
+   */
+  public Writer getLeft() {
+    return leftColumn;
+  }
+
+  /**
+   * Gets the writer to use to write to the right column.
+   *
+   * @return {@code non-null;} the right column writer
+   */
+  public Writer getRight() {
+    return rightColumn;
+  }
+
+  /**
+   * Flushes the output. If there are more lines of pending output in one
+   * column, then the other column will get filled with blank lines.
+   */
+  public void flush() {
+    try {
+      appendNewlineIfNecessary(leftBuf, leftColumn);
+      appendNewlineIfNecessary(rightBuf, rightColumn);
+      outputFullLines();
+      flushLeft();
+      flushRight();
+    } catch (IOException ex) {
+      throw new RuntimeException(ex);
     }
+  }
 
-    /**
-     * Outputs to the final destination as many full line pairs as
-     * there are in the pending output, removing those lines from
-     * their respective buffers. This method terminates when at
-     * least one of the two column buffers is empty.
-     */
-    private void outputFullLines() throws IOException {
-        for (;;) {
-            int leftLen = leftBuf.indexOf("\n");
-            if (leftLen < 0) {
-                return;
-            }
+  /**
+   * Outputs to the final destination as many full line pairs as
+   * there are in the pending output, removing those lines from
+   * their respective buffers. This method terminates when at
+   * least one of the two column buffers is empty.
+   */
+  private void outputFullLines() throws IOException {
+    for (;;) {
+      int leftLen = leftBuf.indexOf("\n");
+      if (leftLen < 0) {
+        return;
+      }
 
-            int rightLen = rightBuf.indexOf("\n");
-            if (rightLen < 0) {
-                return;
-            }
+      int rightLen = rightBuf.indexOf("\n");
+      if (rightLen < 0) {
+        return;
+      }
 
-            if (leftLen != 0) {
-                out.write(leftBuf.substring(0, leftLen));
-            }
+      if (leftLen != 0) {
+        out.write(leftBuf.substring(0, leftLen));
+      }
 
-            if (rightLen != 0) {
-                writeSpaces(out, leftWidth - leftLen);
-                out.write(rightBuf.substring(0, rightLen));
-            }
+      if (rightLen != 0) {
+        writeSpaces(out, leftWidth - leftLen);
+        out.write(rightBuf.substring(0, rightLen));
+      }
 
-            out.write('\n');
+      out.write('\n');
 
-            leftBuf.delete(0, leftLen + 1);
-            rightBuf.delete(0, rightLen + 1);
-        }
+      leftBuf.delete(0, leftLen + 1);
+      rightBuf.delete(0, rightLen + 1);
     }
+  }
 
-    /**
-     * Flushes the left column buffer, printing it and clearing the buffer.
-     * If the buffer is already empty, this does nothing.
-     */
-    private void flushLeft() throws IOException {
-        appendNewlineIfNecessary(leftBuf, leftColumn);
+  /**
+   * Flushes the left column buffer, printing it and clearing the buffer.
+   * If the buffer is already empty, this does nothing.
+   */
+  private void flushLeft() throws IOException {
+    appendNewlineIfNecessary(leftBuf, leftColumn);
 
-        while (leftBuf.length() != 0) {
-            rightColumn.write('\n');
-            outputFullLines();
-        }
+    while (leftBuf.length() != 0) {
+      rightColumn.write('\n');
+      outputFullLines();
     }
+  }
 
-    /**
-     * Flushes the right column buffer, printing it and clearing the buffer.
-     * If the buffer is already empty, this does nothing.
-     */
-    private void flushRight() throws IOException {
-        appendNewlineIfNecessary(rightBuf, rightColumn);
+  /**
+   * Flushes the right column buffer, printing it and clearing the buffer.
+   * If the buffer is already empty, this does nothing.
+   */
+  private void flushRight() throws IOException {
+    appendNewlineIfNecessary(rightBuf, rightColumn);
 
-        while (rightBuf.length() != 0) {
-            leftColumn.write('\n');
-            outputFullLines();
-        }
+    while (rightBuf.length() != 0) {
+      leftColumn.write('\n');
+      outputFullLines();
     }
+  }
 
-    /**
-     * Appends a newline to the given buffer via the given writer, but
-     * only if it isn't empty and doesn't already end with one.
-     *
-     * @param buf {@code non-null;} the buffer in question
-     * @param out {@code non-null;} the writer to use
-     */
-    private static void appendNewlineIfNecessary(StringBuffer buf,
-                                                 Writer out)
-            throws IOException {
-        int len = buf.length();
+  /**
+   * Appends a newline to the given buffer via the given writer, but
+   * only if it isn't empty and doesn't already end with one.
+   *
+   * @param buf {@code non-null;} the buffer in question
+   * @param out {@code non-null;} the writer to use
+   */
+  private static void appendNewlineIfNecessary(StringBuffer buf, Writer out) throws IOException {
+    int len = buf.length();
 
-        if ((len != 0) && (buf.charAt(len - 1) != '\n')) {
-            out.write('\n');
-        }
+    if ((len != 0) && (buf.charAt(len - 1) != '\n')) {
+      out.write('\n');
     }
+  }
 
-    /**
-     * Writes the given number of spaces to the given writer.
-     *
-     * @param out {@code non-null;} where to write
-     * @param amt {@code >= 0;} the number of spaces to write
-     */
-    private static void writeSpaces(Writer out, int amt) throws IOException {
-        while (amt > 0) {
-            out.write(' ');
-            amt--;
-        }
+  /**
+   * Writes the given number of spaces to the given writer.
+   *
+   * @param out {@code non-null;} where to write
+   * @param amt {@code >= 0;} the number of spaces to write
+   */
+  private static void writeSpaces(Writer out, int amt) throws IOException {
+    while (amt > 0) {
+      out.write(' ');
+      amt--;
     }
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Uint.java b/dx/src/com/android/jack/dx/util/Uint.java
index f84a988..3bccc92 100644
--- a/dx/src/com/android/jack/dx/util/Uint.java
+++ b/dx/src/com/android/jack/dx/util/Uint.java
@@ -20,13 +20,14 @@
  * An unsigned integer.
  */
 public final class Uint implements Comparable<Uint> {
-    public final int intValue;
+  public final int intValue;
 
-    public Uint(int value) {
-        this.intValue = value;
-    }
+  public Uint(int value) {
+    this.intValue = value;
+  }
 
-    public int compareTo(Uint uint) {
-        return Unsigned.compare(intValue, uint.intValue);
-    }
+  @Override
+  public int compareTo(Uint uint) {
+    return Unsigned.compare(intValue, uint.intValue);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Unsigned.java b/dx/src/com/android/jack/dx/util/Unsigned.java
index 63c8e1d..cd20cde 100644
--- a/dx/src/com/android/jack/dx/util/Unsigned.java
+++ b/dx/src/com/android/jack/dx/util/Unsigned.java
@@ -20,23 +20,23 @@
  * Unsigned arithmetic over Java's signed types.
  */
 public final class Unsigned {
-    private Unsigned() {}
+  private Unsigned() {}
 
-    public static int compare(short ushortA, short ushortB) {
-        if (ushortA == ushortB) {
-            return 0;
-        }
-        int a = ushortA & 0xFFFF;
-        int b = ushortB & 0xFFFF;
-        return a < b ? -1 : 1;
+  public static int compare(short ushortA, short ushortB) {
+    if (ushortA == ushortB) {
+      return 0;
     }
+    int a = ushortA & 0xFFFF;
+    int b = ushortB & 0xFFFF;
+    return a < b ? -1 : 1;
+  }
 
-    public static int compare(int uintA, int uintB) {
-        if (uintA == uintB) {
-            return 0;
-        }
-        long a = uintA & 0xFFFFFFFFL;
-        long b = uintB & 0xFFFFFFFFL;
-        return a < b ? -1 : 1;
+  public static int compare(int uintA, int uintB) {
+    if (uintA == uintB) {
+      return 0;
     }
+    long a = uintA & 0xFFFFFFFFL;
+    long b = uintB & 0xFFFFFFFFL;
+    return a < b ? -1 : 1;
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Warning.java b/dx/src/com/android/jack/dx/util/Warning.java
index effb49f..b941091 100644
--- a/dx/src/com/android/jack/dx/util/Warning.java
+++ b/dx/src/com/android/jack/dx/util/Warning.java
@@ -20,12 +20,15 @@
  * Exception which is meant to indicate a non-fatal warning.
  */
 public class Warning extends RuntimeException {
-    /**
-     * Constructs an instance.
-     *
-     * @param message human-oriented message
-     */
-    public Warning(String message) {
-        super(message);
-    }
+
+  private static final long serialVersionUID = 1L;
+
+  /**
+   * Constructs an instance.
+   *
+   * @param message human-oriented message
+   */
+  public Warning(String message) {
+    super(message);
+  }
 }
diff --git a/dx/src/com/android/jack/dx/util/Writers.java b/dx/src/com/android/jack/dx/util/Writers.java
index 3d5c8d1..e13d7c7 100644
--- a/dx/src/com/android/jack/dx/util/Writers.java
+++ b/dx/src/com/android/jack/dx/util/Writers.java
@@ -23,26 +23,26 @@
  * Utilities for dealing with {@code Writer}s.
  */
 public final class Writers {
-    /**
-     * This class is uninstantiable.
-     */
-    private Writers() {
-        // This space intentionally left blank.
+  /**
+   * This class is uninstantiable.
+   */
+  private Writers() {
+    // This space intentionally left blank.
+  }
+
+  /**
+   * Makes a {@code PrintWriter} for the given {@code Writer},
+   * returning the given writer if it already happens to be the right
+   * class.
+   *
+   * @param writer {@code non-null;} writer to (possibly) wrap
+   * @return {@code non-null;} an appropriate instance
+   */
+  public static PrintWriter printWriterFor(Writer writer) {
+    if (writer instanceof PrintWriter) {
+      return (PrintWriter) writer;
     }
 
-    /**
-     * Makes a {@code PrintWriter} for the given {@code Writer},
-     * returning the given writer if it already happens to be the right
-     * class.
-     *
-     * @param writer {@code non-null;} writer to (possibly) wrap
-     * @return {@code non-null;} an appropriate instance
-     */
-    public static PrintWriter printWriterFor(Writer writer) {
-        if (writer instanceof PrintWriter) {
-            return (PrintWriter) writer;
-        }
-
-        return new PrintWriter(writer);
-    }
+    return new PrintWriter(writer);
+  }
 }
diff --git a/hamcrest-core/Android.mk b/hamcrest-core/Android.mk
index 776522b..023870c 100644
--- a/hamcrest-core/Android.mk
+++ b/hamcrest-core/Android.mk
@@ -38,3 +38,14 @@
 LOCAL_MODULE_TAGS := optional
 
 include $(BUILD_HOST_JAVA_LIBRARY)
+
+
+include $(CLEAR_VARS)
+
+LOCAL_SRC_FILES := $(call all-java-files-under, src)
+
+LOCAL_MODULE := hamcrest-core-jack
+
+LOCAL_MODULE_TAGS := optional
+
+include $(BUILD_HOST_JAVA_LIBRARY)
diff --git a/jack-tests/Android.mk b/jack-tests/Android.mk
index 7b358a3..bfefef6 100644
--- a/jack-tests/Android.mk
+++ b/jack-tests/Android.mk
@@ -59,6 +59,7 @@
 $(call declare-test-with-name,arithmetic/test001)
 $(call declare-test-with-name,arithmetic/test002)
 $(call declare-test-with-name,arithmetic/test003)
+$(call declare-test-with-name,arithmetic/test004)
 
 # Array
 $(call declare-test-with-name,array/test001)
diff --git a/jack-tests/tests/com/android/jack/arithmetic/test004/dx/Tests.java b/jack-tests/tests/com/android/jack/arithmetic/test004/dx/Tests.java
new file mode 100644
index 0000000..b3b13aa
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/arithmetic/test004/dx/Tests.java
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack.arithmetic.test004.dx;
+
+import junit.framework.Assert;
+
+import org.junit.Test;
+
+import com.android.jack.arithmetic.test004.jack.ArithmeticWithoutValue;
+
+/**
+ * Arithmetic with unary operator.
+ */
+public class Tests {
+
+  @Test
+  public void test1() {
+    Assert.assertEquals(2, ArithmeticWithoutValue.add1(1, 1));
+    Assert.assertEquals(2, ArithmeticWithoutValue.add2(1, 1));
+    Assert.assertEquals(0, ArithmeticWithoutValue.add3(1, 1));
+  }
+
+}
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/jack-tests/tests/com/android/jack/arithmetic/test004/jack/ArithmeticWithoutValue.java
similarity index 64%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to jack-tests/tests/com/android/jack/arithmetic/test004/jack/ArithmeticWithoutValue.java
index 0c967d9..27d032b 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/jack-tests/tests/com/android/jack/arithmetic/test004/jack/ArithmeticWithoutValue.java
@@ -14,18 +14,22 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
-
-import java.util.Collection;
-
-import javax.annotation.Nonnull;
+package com.android.jack.arithmetic.test004.jack;
 
 /**
- * Virtual directory.
+ * Arithmetic with unary operator.
  */
-public interface VDir extends VElement {
+public class ArithmeticWithoutValue {
 
-  @Nonnull
-  Collection<? extends VElement> list();
+  public static int add1(int a, int b) {
+    return a + - + - + b;
+  }
 
+  public static int add2(int a, int b) {
+    return a + - + - + + b;
+  }
+
+  public static int add3(int a, int b) {
+    return a + - + - - b;
+  }
 }
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/jack/A.java b/jack-tests/tests/com/android/jack/frontend/test001/jack/missing/MissingObject.java
similarity index 79%
rename from jack-tests/tests/com/android/jack/shrob/test027/jack/A.java
rename to jack-tests/tests/com/android/jack/frontend/test001/jack/missing/MissingObject.java
index 5a2caba..db9f020 100644
--- a/jack-tests/tests/com/android/jack/shrob/test027/jack/A.java
+++ b/jack-tests/tests/com/android/jack/frontend/test001/jack/missing/MissingObject.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2014 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,8 +14,8 @@
  * limitations under the License.
  */
 
-package com.android.jack.shrob.test027.jack;
+package com.android.jack.frontend.test001.jack.missing;
 
-public class A {
+public class MissingObject {
 
 }
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/SuperClass.java
similarity index 73%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/SuperClass.java
index 0c967d9..4571d8d 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/SuperClass.java
@@ -14,18 +14,15 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.jack.frontend.test001.jack.sub2;
 
-import java.util.Collection;
+import com.android.jack.frontend.test001.jack.missing.MissingObject;
 
-import javax.annotation.Nonnull;
+public class SuperClass extends TopClass {
 
-/**
- * Virtual directory.
- */
-public interface VDir extends VElement {
-
-  @Nonnull
-  Collection<? extends VElement> list();
+  @Override
+  MissingObject get() {
+    return null;
+  }
 
 }
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/jack/A.java b/jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/TopClass.java
similarity index 76%
copy from jack-tests/tests/com/android/jack/shrob/test027/jack/A.java
copy to jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/TopClass.java
index 5a2caba..fd3ae6c 100644
--- a/jack-tests/tests/com/android/jack/shrob/test027/jack/A.java
+++ b/jack-tests/tests/com/android/jack/frontend/test001/jack/sub2/TopClass.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2014 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,8 +14,12 @@
  * limitations under the License.
  */
 
-package com.android.jack.shrob.test027.jack;
+package com.android.jack.frontend.test001.jack.sub2;
 
-public class A {
+public class TopClass {
+
+  Object get() {
+    return null;
+  }
 
 }
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/jack-tests/tests/com/android/jack/frontend/test001/jack/test/SubClass.java
similarity index 73%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to jack-tests/tests/com/android/jack/frontend/test001/jack/test/SubClass.java
index 0c967d9..518837e 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/jack-tests/tests/com/android/jack/frontend/test001/jack/test/SubClass.java
@@ -14,18 +14,10 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.jack.frontend.test001.jack.test;
 
-import java.util.Collection;
+import com.android.jack.frontend.test001.jack.sub2.SuperClass;
 
-import javax.annotation.Nonnull;
-
-/**
- * Virtual directory.
- */
-public interface VDir extends VElement {
-
-  @Nonnull
-  Collection<? extends VElement> list();
+public class SubClass extends SuperClass {
 
 }
diff --git a/jack-tests/tests/com/android/jack/inner/test026/jack/D.java b/jack-tests/tests/com/android/jack/inner/test026/jack/D.java
index 5edfc73..e4178b9 100644
--- a/jack-tests/tests/com/android/jack/inner/test026/jack/D.java
+++ b/jack-tests/tests/com/android/jack/inner/test026/jack/D.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.inner.test026.jack;
 
 import com.android.jack.inner.test026.jack.pkg.C;
diff --git a/jack-tests/tests/com/android/jack/jarjar/test001/jack/DummyAnnot.java b/jack-tests/tests/com/android/jack/jarjar/test001/jack/DummyAnnot.java
index bbf8017..4134bec 100644
--- a/jack-tests/tests/com/android/jack/jarjar/test001/jack/DummyAnnot.java
+++ b/jack-tests/tests/com/android/jack/jarjar/test001/jack/DummyAnnot.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.jarjar.test001.jack;
 
 import java.lang.annotation.Retention;
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/jack-tests/tests/com/android/jack/resource/test001/jack/IrrelevantForTest.java
similarity index 73%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to jack-tests/tests/com/android/jack/resource/test001/jack/IrrelevantForTest.java
index 0c967d9..fc67d00 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/IrrelevantForTest.java
@@ -14,18 +14,15 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
-
-import java.util.Collection;
-
-import javax.annotation.Nonnull;
+package com.android.jack.resource.test001.jack;
 
 /**
- * Virtual directory.
+ * This class is irrelevant for the test, since what we test here is the handling of resources.
  */
-public interface VDir extends VElement {
+public class IrrelevantForTest {
 
-  @Nonnull
-  Collection<? extends VElement> list();
+  public int getInt() {
+    return 4;
+  }
 
 }
diff --git a/jack-tests/tests/com/android/jack/resource/test001/jack/Resource1 b/jack-tests/tests/com/android/jack/resource/test001/jack/Resource1
new file mode 100644
index 0000000..b98ccd9
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/Resource1
@@ -0,0 +1 @@
+Res1
diff --git a/jack-tests/tests/com/android/jack/resource/test001/jack/Resource2 b/jack-tests/tests/com/android/jack/resource/test001/jack/Resource2
new file mode 100644
index 0000000..1bcdbc0
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/Resource2
@@ -0,0 +1 @@
+Res2
diff --git a/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource3 b/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource3
new file mode 100644
index 0000000..d0da24e
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource3
@@ -0,0 +1 @@
+Res3
diff --git a/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource4 b/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource4
new file mode 100644
index 0000000..cf38257
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/pack/Resource4
@@ -0,0 +1 @@
+Res4
diff --git a/jack-tests/tests/com/android/jack/resource/test001/jack/proguard.flags b/jack-tests/tests/com/android/jack/resource/test001/jack/proguard.flags
new file mode 100644
index 0000000..a8d845e
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/resource/test001/jack/proguard.flags
@@ -0,0 +1 @@
+-keep class com.android.jack.resource.test001.jack.IrrelevantForTest
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags001.mapping
index 21fc0d4..dd71fd9 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags001.mapping
@@ -1,3 +1,2 @@
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
-    void m() -> a
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
+    void m() -> renamedM
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags002.mapping
index df84b16..0d80a32 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags002.mapping
@@ -1,4 +1,2 @@
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-    void privateFunc() -> privateFunc
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
-    void m() -> a
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
+    void m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags003.mapping
index 535ddb9..dd71fd9 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags003.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags003.mapping
@@ -1,4 +1,2 @@
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-    void m() -> m
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
-    void m() -> a
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
+    void m() -> renamedM
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags004.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags004.mapping
index cc3053b..963fef8 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags004.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags004.mapping
@@ -1,3 +1,2 @@
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
-    void keep() -> a
-    void main2(java.lang.String[]) -> main2
+    void keep() -> renamedKeep
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping
index 5a4f462..a8a6e5f 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping
@@ -1,5 +1,4 @@
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
-    void keep() -> a
-    void main(java.lang.String[]) -> main
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.a:
-    void keep() -> a
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
+    void keep() -> renamedKeep
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping002 b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping002
index 5a4f462..a8a6e5f 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping002
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping002
@@ -1,5 +1,4 @@
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
-    void keep() -> a
-    void main(java.lang.String[]) -> main
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.a:
-    void keep() -> a
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
+    void keep() -> renamedKeep
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping003 b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping003
index 5a4f462..a8a6e5f 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping003
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags005.mapping003
@@ -1,5 +1,4 @@
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
-    void keep() -> a
-    void main(java.lang.String[]) -> main
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.a:
-    void keep() -> a
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
+    void keep() -> renamedKeep
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags006.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags006.mapping
index 9723086..060dffb 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags006.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags006.mapping
@@ -1,6 +1,5 @@
 com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.G:
-    void m() -> a
-    void main(java.lang.String[]) -> main
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.a:
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.b:
-    void m() -> a
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.RenamedH:
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags007.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags007.mapping
deleted file mode 100644
index d1fc58b..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags007.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.J:
-    int[][][] m3() -> m3
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags008.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags008.mapping
index 52aad70..cafefd5 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags008.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags008.mapping
@@ -1,3 +1 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep() -> keep
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags009.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags009.mapping
index e2fa379..453ed82 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags009.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags009.mapping
@@ -1,5 +1,3 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep2() -> keep2
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
-    int fieldPrivate -> b
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
+    int fieldPrivate -> renamedFielPrivate
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags010.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags010.mapping
index 3570842..17428f7 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags010.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags010.mapping
@@ -1,5 +1,3 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep3() -> keep3
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
-    int fieldPrivate -> b
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
+    int fieldPrivate -> renamedFielPrivate
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags011.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags011.mapping
index 5d902a5..513bb72 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags011.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags011.mapping
@@ -1,6 +1,4 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep4() -> keep4
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.c:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> renamedM
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags012.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags012.mapping
index b474da0..513bb72 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags012.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags012.mapping
@@ -1,6 +1,4 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep5() -> keep5
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.c:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> renamedM
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags013.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags013.mapping
deleted file mode 100644
index 822a5dd..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags013.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags014.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags014.mapping
index 73c80ea..0de1868 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags014.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags014.mapping
@@ -1,5 +1,3 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep6() -> keep6
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
-    long fieldLong -> b
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
+    long fieldLong -> renamedFieldLong
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags015.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags015.mapping
index 33be300..a1c72c9 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags015.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags015.mapping
@@ -1,7 +1,5 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep7() -> keep7
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
-    long fieldLong -> b
-    long fieldLong3 -> c
-    long fieldLong4 -> d
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
+    long fieldLong -> renamedFieldLong
+    long fieldLong3 -> renamedFieldLong3
+    long fieldLong4 -> renamedFieldLong4
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags016.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags016.mapping
index 32dea38..d096156 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags016.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags016.mapping
@@ -1,6 +1,5 @@
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
-    void keep8() -> keep8
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> renamedA
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> renamedB
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags017.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags017.mapping
index 84e1c9b..aec0caf 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags017.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags017.mapping
@@ -1,8 +1,7 @@
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> a
-    int h -> b
-    int i2 -> c
-    int j -> d
-    java.lang.Object o -> e
-    java.lang.String TAG2 -> f
-    void keep() -> keep
+    int i -> renamedI
+    int h -> renamedH
+    int i2 -> renamedI2
+    int j -> renamedJ
+    java.lang.Object o -> renamedI
+    java.lang.String TAG2 -> renamedTAG2
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags018.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags018.mapping
deleted file mode 100644
index 52fca62..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags018.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test001.jack.L -> com.android.jack.shrob.test001.jack.L:
-    void onReceive() -> onReceive
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags019.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags019.mapping
deleted file mode 100644
index 14d06cd..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags019.mapping
+++ /dev/null
@@ -1,30 +0,0 @@
-com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
-    java.lang.String TAG -> TAG
-    java.lang.String TAG2 -> TAG2
-    void keep() -> keep
-com.android.jack.shrob.test001.jack.L -> com.android.jack.shrob.test001.jack.L:
-    java.lang.String TAG -> TAG
-    void onReceive() -> onReceive
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
-    long fieldLong -> fieldLong
-    long fieldLong2 -> fieldLong2
-    long fieldLong3 -> fieldLong3
-    long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
-    void calledMethod() -> calledMethod
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> m
-    void privateMethod(com.android.jack.shrob.test001.jack.Reflect2$B) -> privateMethod
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.Reflect2$B:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags020.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags020.mapping
deleted file mode 100644
index 1ba7b92..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags020.mapping
+++ /dev/null
@@ -1,25 +0,0 @@
-com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
-    java.lang.String TAG -> TAG
-    java.lang.String TAG2 -> TAG2
-com.android.jack.shrob.test001.jack.L -> com.android.jack.shrob.test001.jack.L:
-    java.lang.String TAG -> TAG
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
-    long fieldLong -> fieldLong
-    long fieldLong2 -> fieldLong2
-    long fieldLong3 -> fieldLong3
-    long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.Reflect2$B:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags021.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags021.mapping
index 48a2db6..ca830b9 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags021.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags021.mapping
@@ -1,67 +1,39 @@
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.a:
-    void m() -> a
-    void privateFunc() -> b
-com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.c:
-    void f() -> a
-    void m() -> b
-com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.d:
-    void keep() -> a
-    void main(java.lang.String[]) -> a
-    void main2(java.lang.String[]) -> b
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.e:
-    void keep() -> a
-com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.f:
-    void keep() -> a
-com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.g:
-    void m() -> a
-    void main(java.lang.String[]) -> a
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.h:
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.i:
-    void m() -> a
-com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.j:
-    int[][][] m5(int,boolean,long) -> a
-    int[][][] m3() -> a
-    int[][] m2() -> b
-    int[] m1() -> c
-    int m0() -> d
-    int[][][] m() -> e
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.RenamedH:
+com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.RenamedJ:
+    int[][][] m() -> renamedM
+    int m0() -> renamedM0
+    int[] m1() -> renamedM1
+    int[][] m2() -> renamedM2
+    int[][][] m3() -> renamedM3
+    int[][][] m5(int,boolean,long) -> renamedM5
+com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.RenamedF:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.RenamedB:
+com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.RenamedD:
+    void keep() -> renamedKeep
+    void main(java.lang.String[]) -> renamedMain
+    void main2(java.lang.String[]) -> renamedMain2
+com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.RenamedG:
+    void m() -> renamedM
+    void main(java.lang.String[]) -> renamedMain
+com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.RenamedReflect:
+    void keep() -> renamedKeep
+    void keep2() -> renamedKeep2
+    void keep3() -> renamedKeep3
+    void keep4() -> renamedKeep4
+    void keep5() -> renamedKeep5
+    void keep6() -> renamedKeep6
+    void keep7() -> renamedKeep7
+    void keep8() -> renamedKeep8
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
+    void f() -> renamedF
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.RenamedA:
+    void m() -> renamedM
+    void privateFunc() -> renamedPrivateFunc
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
-    java.lang.String TAG -> TAG
-    java.lang.String TAG2 -> TAG2
-    void keep() -> a
-com.android.jack.shrob.test001.jack.L -> com.android.jack.shrob.test001.jack.L:
-    java.lang.String TAG -> TAG
-    void onReceive() -> a
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.k:
-    void keep() -> a
-    void keep2() -> b
-    void keep3() -> c
-    void keep4() -> d
-    void keep5() -> e
-    void keep6() -> f
-    void keep7() -> g
-    void keep8() -> h
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
-    long fieldLong -> fieldLong
-    long fieldLong2 -> fieldLong2
-    long fieldLong3 -> fieldLong3
-    long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
-    void calledMethod() -> a
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-    void privateMethod(com.android.jack.shrob.test001.jack.Reflect2$B) -> a
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.Reflect2$B:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
+    void keep() -> renamedKeep
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags022.mapping b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags022.mapping
index 44c10d6..0b8ef10 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags022.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test001/proguard.flags022.mapping
@@ -1,67 +1,37 @@
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.a:
-    void m() -> a
-    void privateFunc() -> b
-com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.c:
-    void f() -> a
-    void m() -> b
-com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.d:
-    void keep() -> a
-    void main(java.lang.String[]) -> a
-    void main2(java.lang.String[]) -> b
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.e:
-    void keep() -> a
-com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.f:
-    void keep() -> a
-com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.g:
-    void m() -> a
-    void main(java.lang.String[]) -> a
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.h:
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.i:
-    void m() -> a
-com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.j:
-    int[][][] m5(int,boolean,long) -> a
-    int[][][] m3() -> a
-    int[][] m2() -> b
-    int[] m1() -> c
-    int m0() -> d
-    int[][][] m() -> e
-com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
-    java.lang.String TAG -> TAG
-    java.lang.String TAG2 -> TAG2
-    void keep() -> keep
-com.android.jack.shrob.test001.jack.L -> com.android.jack.shrob.test001.jack.L:
-    java.lang.String TAG -> TAG
-    void onReceive() -> onReceive
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.k:
-    void keep() -> a
-    void keep2() -> b
-    void keep3() -> c
-    void keep4() -> d
-    void keep5() -> e
-    void keep6() -> f
-    void keep7() -> g
-    void keep8() -> h
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
-    long fieldLong -> fieldLong
-    long fieldLong2 -> fieldLong2
-    long fieldLong3 -> fieldLong3
-    long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
-    void calledMethod() -> calledMethod
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> m
-    void privateMethod(com.android.jack.shrob.test001.jack.Reflect2$B) -> privateMethod
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.Reflect2$B:
-    com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.renamedH:
+com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.renamedJ:
+    int[][][] m5(int,boolean,long) -> renamedM5
+    int[][][] m3() -> renamedM3
+    int[][] m2() -> renamedM2
+    int[] m1() -> renamedM1
+    int m0() -> renamedM0
+    int[][][] m() -> renamedM
+com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.RenamedF:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.RenamedB:
+com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.RenamedD:
+    void keep() -> renamedKeep
+    void main(java.lang.String[]) -> renamedMain
+    void main2(java.lang.String[]) -> renamedMain2
+com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.RenamedG:
+    void m() -> renamedM
+    void main(java.lang.String[]) -> renamedMain
+com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.RenamedReflect:
+    void keep() -> renamedKeep
+    void keep2() -> renamedKeep2
+    void keep3() -> renamedKeep3
+    void keep4() -> renamedKeep4
+    void keep5() -> renamedKeep5
+    void keep6() -> renamedKeep6
+    void keep7() -> renamedKeep7
+    void keep8() -> renamedKeep8
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
+    void f() -> renamedF
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.RenamedA:
+    void m() -> renamedM
+    void privateFunc() -> renamedPrivateFunc
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-001.txt
index 51f1db2..6463a01 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-001.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
     void <init>() -> <init>
-    void m() -> a
+    void m() -> renamedM
 com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-    void <clinit>() -> <clinit>
     void <init>() -> <init>
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-002.txt
index b0049fe..f827dd9 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-002.txt
@@ -1,7 +1,7 @@
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
     void <init>() -> <init>
-    void m() -> a
+    void m() -> renamedM
 com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-    void <clinit>() -> <clinit>
     void <init>() -> <init>
     void privateFunc() -> privateFunc
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-003.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-003.txt
index acbe6d5..fa2b35a 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-003.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-003.txt
@@ -1,8 +1,8 @@
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
     void <init>() -> <init>
-    void m() -> a
+    void m() -> renamedM
 com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.A:
-    void <clinit>() -> <clinit>
     void <init>() -> <init>
     void <init>(int) -> <init>
     void m() -> m
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-004.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-004.txt
index 952f08d..4b9187a 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-004.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-004.txt
@@ -1,4 +1,4 @@
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
     void <init>() -> <init>
-    void keep() -> a
+    void keep() -> renamedKeep
     void main2(java.lang.String[]) -> main2
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-005.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-005.txt
index 9882dfa..d2f22ee 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-005.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-005.txt
@@ -1,7 +1,7 @@
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
     void <init>() -> <init>
-    void keep() -> a
+    void keep() -> renamedKeep
 com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.D:
     void <init>() -> <init>
-    void keep() -> a
+    void keep() -> renamedKeep
     void main(java.lang.String[]) -> main
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-006.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-006.txt
index 8c2943a..5d053cc 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-006.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-006.txt
@@ -1,7 +1,7 @@
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.b:
-    void m() -> a
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.RenamedH:
 com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.G:
     void <init>() -> <init>
-    void m() -> a
+    void m() -> renamedM
     void main(java.lang.String[]) -> main
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-008.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-008.txt
index 0965567..d3a17fc 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-008.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-008.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep() -> keep
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-009.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-009.txt
index 23e4011..1350955 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-009.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-009.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep2() -> keep2
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-010.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-010.txt
index 28402c5..1c70c36 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-010.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-010.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep3() -> keep3
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-011.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-011.txt
index 0287a94..8dcc0e0 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-011.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-011.txt
@@ -1,8 +1,8 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep4() -> keep4
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
     void <init>() -> <init>
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.c:
+    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> renamedM
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-012.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-012.txt
index c95a035..3810d94 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-012.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-012.txt
@@ -1,8 +1,8 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep5() -> keep5
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
     void <init>() -> <init>
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.c:
+    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> renamedM
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-014.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-014.txt
index 2967038..77808f5 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-014.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-014.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep6() -> keep6
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    int fieldPublic -> a
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    int fieldPublic -> renamedFieldPublic
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-015.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-015.txt
index 154a665..eb6fd7f 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-015.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-015.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep7() -> keep7
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    long fieldLong -> b
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    long fieldLong -> renamedFieldLong
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-016.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-016.txt
index 5ad9d9c..9bd0417 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-016.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-016.txt
@@ -1,9 +1,9 @@
 com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.Reflect:
     void <init>() -> <init>
     void keep8() -> keep8
-com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.a:
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
+com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.RenamedReflect2:
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> renamedA
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> renamedB
     void <init>() -> <init>
-com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.b:
-com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.c:
+com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.RenamedReflect2$A:
+com.android.jack.shrob.test001.jack.Reflect2$B -> com.android.jack.shrob.test001.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-017.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-017.txt
index ccfdc41..fd3cb91 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-017.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-017.txt
@@ -1,10 +1,10 @@
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> a
-    int h -> b
-    int i2 -> c
-    int j -> d
-    java.lang.Object o -> e
-    java.lang.String TAG2 -> f
-    void <clinit>() -> <clinit>
+    java.lang.String TAG2 -> renamedTAG2
+    int h -> renamedH
+    int i -> renamedI
+    int i2 -> renamedI2
+    int j -> renamedJ
+    java.lang.Object o -> renamedI
     void <init>() -> <init>
     void keep() -> keep
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-019.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-019.txt
index 93a7c09..345010d 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-019.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-019.txt
@@ -1,13 +1,13 @@
 com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
+    java.lang.Object c -> c
     long fieldLong -> fieldLong
     long fieldLong2 -> fieldLong2
     long fieldLong3 -> fieldLong3
     long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
+    int fieldPrivate -> fieldPrivate
+    int fieldPublic -> fieldPublic
     void <init>() -> <init>
     void calledMethod() -> calledMethod
     void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> m
@@ -23,14 +23,14 @@
     void <init>() -> <init>
     void onReceive() -> onReceive
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
     java.lang.String TAG -> TAG
     java.lang.String TAG2 -> TAG2
-    void <clinit>() -> <clinit>
+    int h -> h
+    int i -> i
+    int i2 -> i2
+    int i3 -> i3
+    int j -> j
+    java.lang.Object o -> o
     void <init>() -> <init>
     void keep() -> keep
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-020.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-020.txt
index a68d609..3123550 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-020.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-020.txt
@@ -1,13 +1,13 @@
 com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
+    java.lang.Object c -> c
     long fieldLong -> fieldLong
     long fieldLong2 -> fieldLong2
     long fieldLong3 -> fieldLong3
     long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
+    int fieldPrivate -> fieldPrivate
+    int fieldPublic -> fieldPublic
     void <init>() -> <init>
 com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
     com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
@@ -17,13 +17,13 @@
     java.lang.String TAG -> TAG
     void <init>() -> <init>
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
     java.lang.String TAG -> TAG
     java.lang.String TAG2 -> TAG2
-    void <clinit>() -> <clinit>
+    int h -> h
+    int i -> i
+    int i2 -> i2
+    int i3 -> i3
+    int j -> j
+    java.lang.Object o -> o
     void <init>() -> <init>
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-021.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-021.txt
index 350f38a..58b7103 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-021.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-021.txt
@@ -1,65 +1,65 @@
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.e:
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
     void <init>() -> <init>
-    void keep() -> a
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.i:
-    void m() -> a
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.h:
-com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.j:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.RenamedH:
+com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.RenamedJ:
     void <init>() -> <init>
-    int[][][] m5(int,boolean,long) -> a
-    int[][][] m3() -> a
-    int[][] m2() -> b
-    int[] m1() -> c
-    int m0() -> d
-    int[][][] m() -> e
-com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.f:
+    int[][][] m() -> renamedM
+    int m0() -> renamedM0
+    int[] m1() -> renamedM1
+    int[][] m2() -> renamedM2
+    int[][][] m3() -> renamedM3
+    int[][][] m5(int,boolean,long) -> renamedM5
+com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.RenamedF:
     void <init>() -> <init>
-    void keep() -> a
-com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.b:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.d:
+com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.RenamedD:
     void <init>() -> <init>
-    void keep() -> a
-    void main(java.lang.String[]) -> a
-    void main2(java.lang.String[]) -> b
-com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.g:
+    void keep() -> renamedKeep
+    void main(java.lang.String[]) -> renamedMain
+    void main2(java.lang.String[]) -> renamedMain2
+com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.RenamedG:
     void <init>() -> <init>
-    void m() -> a
-    void main(java.lang.String[]) -> a
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.k:
+    void m() -> renamedM
+    void main(java.lang.String[]) -> renamedMain
+com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.RenamedReflect:
     void <init>() -> <init>
-    void keep() -> a
-    void keep2() -> b
-    void keep3() -> c
-    void keep4() -> d
-    void keep5() -> e
-    void keep6() -> f
-    void keep7() -> g
-    void keep8() -> h
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.c:
+    void keep() -> renamedKeep
+    void keep2() -> renamedKeep2
+    void keep3() -> renamedKeep3
+    void keep4() -> renamedKeep4
+    void keep5() -> renamedKeep5
+    void keep6() -> renamedKeep6
+    void keep7() -> renamedKeep7
+    void keep8() -> renamedKeep8
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
     void <init>() -> <init>
-    void f() -> a
-    void m() -> b
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.a:
-    void <clinit>() -> <clinit>
+    void f() -> renamedF
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.RenamedA:
     void <init>() -> <init>
     void <init>(int) -> <init>
-    void m() -> a
-    void privateFunc() -> b
+    void m() -> renamedM
+    void privateFunc() -> renamedPrivateFunc
+    void <clinit>() -> <clinit>
 com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
+    java.lang.Object c -> c
     long fieldLong -> fieldLong
     long fieldLong2 -> fieldLong2
     long fieldLong3 -> fieldLong3
     long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
+    int fieldPrivate -> fieldPrivate
+    int fieldPublic -> fieldPublic
     void <init>() -> <init>
     void calledMethod() -> a
-    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> a
-    void privateMethod(com.android.jack.shrob.test001.jack.Reflect2$B) -> a
+    void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> b
+    void privateMethod(com.android.jack.shrob.test001.jack.Reflect2$B) -> c
 com.android.jack.shrob.test001.jack.Reflect2$A -> com.android.jack.shrob.test001.jack.Reflect2$A:
     com.android.jack.shrob.test001.jack.Reflect2 this$0 -> this$0
     void <init>(com.android.jack.shrob.test001.jack.Reflect2) -> <init>
@@ -71,14 +71,14 @@
     void <init>() -> <init>
     void onReceive() -> a
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
     java.lang.String TAG -> TAG
     java.lang.String TAG2 -> TAG2
-    void <clinit>() -> <clinit>
+    int h -> h
+    int i -> i
+    int i2 -> i2
+    int i3 -> i3
+    int j -> j
+    java.lang.Object o -> o
     void <init>() -> <init>
-    void keep() -> a
+    void keep() -> renamedKeep
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-022.txt b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-022.txt
index 5f9de20..0e236ab 100644
--- a/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-022.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test001/refsObfuscationWithMapping/expected-022.txt
@@ -1,61 +1,61 @@
-com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.e:
+com.android.jack.shrob.test001.jack.E -> com.android.jack.shrob.test001.jack.RenamedE:
     void <init>() -> <init>
-    void keep() -> a
-com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.i:
-    void m() -> a
-com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.h:
-com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.j:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.I -> com.android.jack.shrob.test001.jack.RenamedI:
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.H -> com.android.jack.shrob.test001.jack.renamedH:
+com.android.jack.shrob.test001.jack.J -> com.android.jack.shrob.test001.jack.renamedJ:
     void <init>() -> <init>
-    int[][][] m5(int,boolean,long) -> a
-    int[][][] m3() -> a
-    int[][] m2() -> b
-    int[] m1() -> c
-    int m0() -> d
-    int[][][] m() -> e
-com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.f:
+    int[][][] m() -> renamedM
+    int m0() -> renamedM0
+    int[] m1() -> renamedM1
+    int[][] m2() -> renamedM2
+    int[][][] m3() -> renamedM3
+    int[][][] m5(int,boolean,long) -> renamedM5
+com.android.jack.shrob.test001.jack.F -> com.android.jack.shrob.test001.jack.RenamedF:
     void <init>() -> <init>
-    void keep() -> a
-com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.b:
+    void keep() -> renamedKeep
+com.android.jack.shrob.test001.jack.B -> com.android.jack.shrob.test001.jack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.d:
+com.android.jack.shrob.test001.jack.D -> com.android.jack.shrob.test001.jack.RenamedD:
     void <init>() -> <init>
-    void keep() -> a
-    void main(java.lang.String[]) -> a
-    void main2(java.lang.String[]) -> b
-com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.g:
+    void keep() -> renamedKeep
+    void main(java.lang.String[]) -> renamedMain
+    void main2(java.lang.String[]) -> renamedMain2
+com.android.jack.shrob.test001.jack.G -> com.android.jack.shrob.test001.jack.RenamedG:
     void <init>() -> <init>
-    void m() -> a
-    void main(java.lang.String[]) -> a
-com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.k:
+    void m() -> renamedM
+    void main(java.lang.String[]) -> renamedMain
+com.android.jack.shrob.test001.jack.Reflect -> com.android.jack.shrob.test001.jack.RenamedReflect:
     void <init>() -> <init>
-    void keep() -> a
-    void keep2() -> b
-    void keep3() -> c
-    void keep4() -> d
-    void keep5() -> e
-    void keep6() -> f
-    void keep7() -> g
-    void keep8() -> h
-com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.c:
+    void keep() -> renamedKeep
+    void keep2() -> renamedKeep2
+    void keep3() -> renamedKeep3
+    void keep4() -> renamedKeep4
+    void keep5() -> renamedKeep5
+    void keep6() -> renamedKeep6
+    void keep7() -> renamedKeep7
+    void keep8() -> renamedKeep8
+com.android.jack.shrob.test001.jack.C -> com.android.jack.shrob.test001.jack.RenamedC:
     void <init>() -> <init>
-    void f() -> a
-    void m() -> b
-com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.a:
-    void <clinit>() -> <clinit>
+    void f() -> renamedF
+    void m() -> renamedM
+com.android.jack.shrob.test001.jack.A -> com.android.jack.shrob.test001.jack.RenamedA:
     void <init>() -> <init>
     void <init>(int) -> <init>
-    void m() -> a
-    void privateFunc() -> b
+    void m() -> renamedM
+    void privateFunc() -> renamedPrivateFunc
+    void <clinit>() -> <clinit>
 com.android.jack.shrob.test001.jack.Reflect2 -> com.android.jack.shrob.test001.jack.Reflect2:
-    int fieldPublic -> fieldPublic
-    int fieldPrivate -> fieldPrivate
+    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
+    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
+    java.lang.Object c -> c
     long fieldLong -> fieldLong
     long fieldLong2 -> fieldLong2
     long fieldLong3 -> fieldLong3
     long fieldLong4 -> fieldLong4
-    com.android.jack.shrob.test001.jack.Reflect2$A a -> a
-    com.android.jack.shrob.test001.jack.Reflect2$B b -> b
-    java.lang.Object c -> c
+    int fieldPrivate -> fieldPrivate
+    int fieldPublic -> fieldPublic
     void <init>() -> <init>
     void calledMethod() -> calledMethod
     void m(com.android.jack.shrob.test001.jack.Reflect2$A) -> m
@@ -71,14 +71,14 @@
     void <init>() -> <init>
     void onReceive() -> onReceive
 com.android.jack.shrob.test001.jack.K -> com.android.jack.shrob.test001.jack.K:
-    int i -> i
-    int h -> h
-    int i2 -> i2
-    int j -> j
-    int i3 -> i3
-    java.lang.Object o -> o
     java.lang.String TAG -> TAG
     java.lang.String TAG2 -> TAG2
-    void <clinit>() -> <clinit>
+    int h -> h
+    int i -> i
+    int i2 -> i2
+    int i3 -> i3
+    int j -> j
+    java.lang.Object o -> o
     void <init>() -> <init>
     void keep() -> keep
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags002.mapping
deleted file mode 100644
index d184e76..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags002.mapping
+++ /dev/null
@@ -1 +0,0 @@
-com.android.jack.shrob.test002.jack.B -> com.android.jack.shrob.test002.jack.B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags003.mapping
deleted file mode 100644
index d184e76..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test002/proguard.flags003.mapping
+++ /dev/null
@@ -1 +0,0 @@
-com.android.jack.shrob.test002.jack.B -> com.android.jack.shrob.test002.jack.B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/info.txt b/jack-tests/tests/com/android/jack/shrob/test003/info.txt
new file mode 100644
index 0000000..ed6fc3d
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test003/info.txt
@@ -0,0 +1,3 @@
+This test was written to show the different behavior between using library jars or injars.
+The class in lib contains a Class.ForName with an existing class that should be kept when the
+lib is used as a injar.
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/lib/Test.class b/jack-tests/tests/com/android/jack/shrob/test003/lib/Test.class
new file mode 100644
index 0000000..bd9a8c9
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test003/lib/Test.class
Binary files differ
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags001.mapping
deleted file mode 100644
index f6b7dd6..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags001.mapping
+++ /dev/null
@@ -1 +0,0 @@
-com.android.jack.shrob.test003.jack.B -> com.android.jack.shrob.test003.jack.B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags002 b/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags002
new file mode 100644
index 0000000..320bdd0
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test003/proguard.flags002
@@ -0,0 +1,3 @@
+-keep class com.android.jack.shrob.test003.lib.Test {
+   void keep();
+}
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsFlattenPackage/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsFlattenPackage/expected-001.txt
deleted file mode 100644
index f231988..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/refsFlattenPackage/expected-001.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test003.jack.B -> com.android.jack.shrob.test003.jack.B:
-    void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithMapping/expected-001.txt
deleted file mode 100644
index f231988..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithMapping/expected-001.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test003.jack.B -> com.android.jack.shrob.test003.jack.B:
-    void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithoutMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithoutMapping/expected-001.txt
deleted file mode 100644
index f231988..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/refsObfuscationWithoutMapping/expected-001.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test003.jack.B -> com.android.jack.shrob.test003.jack.B:
-    void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsRepackageClasses/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsRepackageClasses/expected-001.txt
deleted file mode 100644
index f231988..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/refsRepackageClasses/expected-001.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test003.jack.B -> com.android.jack.shrob.test003.jack.B:
-    void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsSeed/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsSeed/expected-001.txt
deleted file mode 100644
index 90b2f3e..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/refsSeed/expected-001.txt
+++ /dev/null
@@ -1,3 +0,0 @@
-com.android.jack.shrob.test003.jack.B
-com.android.jack.shrob.test003.lib.Test
-com.android.jack.shrob.test003.lib.Test: void keep()
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/refsShrinking/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test003/refsShrinking/expected-002.txt
new file mode 100644
index 0000000..d285e15
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test003/refsShrinking/expected-002.txt
@@ -0,0 +1,5 @@
+Lcom/android/jack/shrob/test003/jack/A;:
+<init>()V
+Lcom/android/jack/shrob/test003/lib/Test;:
+<init>()V
+keep()V
diff --git a/jack-tests/tests/com/android/jack/shrob/test003/test.jar b/jack-tests/tests/com/android/jack/shrob/test003/test.jar
deleted file mode 100644
index c05fa6b..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test003/test.jar
+++ /dev/null
Binary files differ
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags001.mapping
index 95418dc..73c2c28 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags001.mapping
@@ -1,2 +1,2 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
-    void m() -> a
+    void m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags002.mapping
index 8441b1f..94a7eaf 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags002.mapping
@@ -1,3 +1,3 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
-    void m() -> a
-    void m2() -> b
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags003.mapping
index 8441b1f..94a7eaf 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags003.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test004/proguard.flags003.mapping
@@ -1,3 +1,3 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
-    void m() -> a
-    void m2() -> b
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-001.txt
index 3695723..dc8b051 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-001.txt
@@ -1,3 +1,3 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
     void <init>() -> <init>
-    void m() -> a
+    void m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-002.txt
index 6dd9c9b..e19d8c6 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-002.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
     void <init>() -> <init>
     void <init>(int) -> <init>
-    void m() -> a
-    void m2() -> b
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-003.txt b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-003.txt
index 6dd9c9b..e19d8c6 100644
--- a/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-003.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test004/refsObfuscationWithMapping/expected-003.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test004.jack.A -> com.android.jack.shrob.test004.jack.A:
     void <init>() -> <init>
     void <init>(int) -> <init>
-    void m() -> a
-    void m2() -> b
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags001.mapping
index d1ece21..5cd97ea 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags001.mapping
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
\ No newline at end of file
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags002.mapping
index ef90650..5cd97ea 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags002.mapping
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags003.mapping
index d1ece21..5cd97ea 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags003.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags003.mapping
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
\ No newline at end of file
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags004.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags004.mapping
deleted file mode 100644
index a01062b..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags004.mapping
+++ /dev/null
@@ -1 +0,0 @@
-com.android.jack.shrob.test005.jack.Annot -> com.android.jack.shrob.test005.jack.Annot:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags005.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags005.mapping
index 83f2fad..86e6525 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags005.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags005.mapping
@@ -1,13 +1,13 @@
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.b:
-    int intValue() -> a
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.d:
-com.android.jack.shrob.test005.jack.C -> a.a.a.a.a.a.e:
-com.android.jack.shrob.test005.jack.E -> a.a.a.a.a.a.f:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> d
-    com.android.jack.shrob.test005.jack.E valueOf(java.lang.String) -> a
-    com.android.jack.shrob.test005.jack.E[] values() -> b
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+    int intValue() -> renamedIntValue
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
+com.android.jack.shrob.test005.jack.C -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedC:
+com.android.jack.shrob.test005.jack.E -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedE:
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
+    com.android.jack.shrob.test005.jack.E valueOf(java.lang.String) -> renamedValueOf
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags006.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags006.mapping
index 2fe0e72..0a24e15 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags006.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags006.mapping
@@ -1,10 +1,6 @@
-com.android.jack.shrob.test005.jack.A -> com.android.jack.shrob.test005.jack.A:
-com.android.jack.shrob.test005.jack.Annot -> com.android.jack.shrob.test005.jack.Annot:
-com.android.jack.shrob.test005.jack.Annot2 -> com.android.jack.shrob.test005.jack.Annot2:
-com.android.jack.shrob.test005.jack.B -> com.android.jack.shrob.test005.jack.B:
-com.android.jack.shrob.test005.jack.C -> com.android.jack.shrob.test005.jack.C:
 com.android.jack.shrob.test005.jack.E -> com.android.jack.shrob.test005.jack.E:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> e
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags007.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags007.mapping
deleted file mode 100644
index 8692631..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags007.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test005.jack.Annot -> com.android.jack.shrob.test005.jack.Annot:
-com.android.jack.shrob.test005.jack.Annot2 -> com.android.jack.shrob.test005.jack.Annot2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags008.mapping b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags008.mapping
index 4808055..0a24e15 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags008.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test005/proguard.flags008.mapping
@@ -1,5 +1,6 @@
 com.android.jack.shrob.test005.jack.E -> com.android.jack.shrob.test005.jack.E:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> e
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-001.txt
index d31f1cf..a9c9020 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-001.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-002.txt
index d31f1cf..a9c9020 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-002.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-003.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-003.txt
index d31f1cf..a9c9020 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-003.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-003.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.c:
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.b:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.d:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-005.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-005.txt
index 38f0380..fded0e5 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-005.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-005.txt
@@ -1,18 +1,18 @@
-com.android.jack.shrob.test005.jack.Annot -> a.a.a.a.a.a.b:
-    int intValue() -> a
-com.android.jack.shrob.test005.jack.E -> a.a.a.a.a.a.f:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> d
-    void <clinit>() -> <clinit>
-    com.android.jack.shrob.test005.jack.E valueOf(java.lang.String) -> a
-    com.android.jack.shrob.test005.jack.E[] values() -> b
+com.android.jack.shrob.test005.jack.Annot -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot:
+    int intValue() -> renamedIntValue
+com.android.jack.shrob.test005.jack.E -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedE:
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
     void <init>(java.lang.String,int) -> <init>
-com.android.jack.shrob.test005.jack.A -> a.a.a.a.a.a.a:
+    com.android.jack.shrob.test005.jack.E valueOf(java.lang.String) -> renamedValueOf
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
+    void <clinit>() -> <clinit>
+com.android.jack.shrob.test005.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.B -> a.a.a.a.a.a.d:
+com.android.jack.shrob.test005.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.C -> a.a.a.a.a.a.e:
+com.android.jack.shrob.test005.jack.C -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedC:
     void <init>() -> <init>
-com.android.jack.shrob.test005.jack.Annot2 -> a.a.a.a.a.a.c:
+com.android.jack.shrob.test005.jack.Annot2 -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest005.renamedJack.RenamedAnnot2:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-006.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-006.txt
index 35a7a05..b2a5fa4 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-006.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-006.txt
@@ -1,12 +1,12 @@
 com.android.jack.shrob.test005.jack.Annot -> com.android.jack.shrob.test005.jack.Annot:
 com.android.jack.shrob.test005.jack.E -> com.android.jack.shrob.test005.jack.E:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> e
-    com.android.jack.shrob.test005.jack.E[] values() -> a
-    void <clinit>() -> <clinit>
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
     void <init>(java.lang.String,int) -> <init>
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
+    void <clinit>() -> <clinit>
 com.android.jack.shrob.test005.jack.A -> com.android.jack.shrob.test005.jack.A:
     void <init>() -> <init>
 com.android.jack.shrob.test005.jack.B -> com.android.jack.shrob.test005.jack.B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-008.txt b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-008.txt
index 723de19..99f600a 100644
--- a/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-008.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test005/refsObfuscationWithMapping/expected-008.txt
@@ -1,8 +1,8 @@
 com.android.jack.shrob.test005.jack.E -> com.android.jack.shrob.test005.jack.E:
-    com.android.jack.shrob.test005.jack.E A -> a
-    com.android.jack.shrob.test005.jack.E B -> b
-    com.android.jack.shrob.test005.jack.E C -> c
-    com.android.jack.shrob.test005.jack.E[] $VALUES -> e
-    com.android.jack.shrob.test005.jack.E[] values() -> a
-    void <clinit>() -> <clinit>
+    com.android.jack.shrob.test005.jack.E A -> renamedA
+    com.android.jack.shrob.test005.jack.E B -> renamedB
+    com.android.jack.shrob.test005.jack.E C -> renamedC
+    com.android.jack.shrob.test005.jack.E[] $VALUES -> renamed$VALUES
     void <init>(java.lang.String,int) -> <init>
+    com.android.jack.shrob.test005.jack.E[] values() -> renamedValues
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags001.mapping
deleted file mode 100644
index 2be876c..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags001.mapping
+++ /dev/null
@@ -1,4 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m1() -> m1
-    void m4() -> m4
-    void m5(java.lang.String[]) -> m5
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags002.mapping
deleted file mode 100644
index 542bff4..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags002.mapping
+++ /dev/null
@@ -1,4 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m() -> m
-    void m2() -> m2
-    int m8() -> m8
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags003.mapping
deleted file mode 100644
index 4aff1a6..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags003.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m5(java.lang.String[]) -> m5
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags004.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags004.mapping
deleted file mode 100644
index d7ecf53..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags004.mapping
+++ /dev/null
@@ -1,3 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m6() -> m6
-    void m7() -> m7
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags005.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags005.mapping
deleted file mode 100644
index e215817..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags005.mapping
+++ /dev/null
@@ -1,5 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m() -> m
-    void m2() -> m2
-    void m6() -> m6
-    int m8() -> m8
diff --git a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags006.mapping b/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags006.mapping
deleted file mode 100644
index 96b4c9d..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test006/proguard.flags006.mapping
+++ /dev/null
@@ -1,5 +0,0 @@
-com.android.jack.shrob.test006.jack.A -> com.android.jack.shrob.test006.jack.A:
-    void m1() -> m1
-    void m3() -> m3
-    void m4() -> m4
-    void m5(java.lang.String[]) -> m5
diff --git a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags001.mapping
deleted file mode 100644
index a420b6c..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags001.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test007.jack.A -> com.android.jack.shrob.test007.jack.A:
-    java.lang.Object getObject() -> getObject
diff --git a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags002.mapping
deleted file mode 100644
index d0a31d4..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags002.mapping
+++ /dev/null
@@ -1,4 +0,0 @@
-com.android.jack.shrob.test007.jack.A -> com.android.jack.shrob.test007.jack.A:
-    java.lang.Object getObject() -> getObject
-    float getFloat() -> getFloat
-    java.lang.Object[] getObjects() -> getObjects
diff --git a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags003.mapping
deleted file mode 100644
index b01ae59..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test007/proguard.flags003.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test007.jack.A -> com.android.jack.shrob.test007.jack.A:
-    float getFloat() -> getFloat
diff --git a/jack-tests/tests/com/android/jack/shrob/test007/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test007/refsObfuscationWithMapping/expected-002.txt
index 03e309f..12bf267 100644
--- a/jack-tests/tests/com/android/jack/shrob/test007/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test007/refsObfuscationWithMapping/expected-002.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test007.jack.A -> com.android.jack.shrob.test007.jack.A:
     void <init>() -> <init>
-    java.lang.Object getObject() -> getObject
     float getFloat() -> getFloat
+    java.lang.Object getObject() -> getObject
     java.lang.Object[] getObjects() -> getObjects
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags001.mapping
index 2b32885..b97a198 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags001.mapping
@@ -1,4 +1,3 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
-    void m() -> a
-    void keep() -> keep
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags002.mapping
index a10fae7..b97a198 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags002.mapping
@@ -1,4 +1,3 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
-    void m() -> a
-    void keep2() -> keep2
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags003.mapping
index b8617a4..b97a198 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags003.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags003.mapping
@@ -1,4 +1,3 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
-    void m() -> a
-    void keep3() -> keep3
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags004.mapping b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags004.mapping
index c2a969a..29a3a97 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags004.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test008/proguard.flags004.mapping
@@ -1,3 +1 @@
-com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
-    void keep4() -> keep4
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-001.txt
index d4eae97..3327d44 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-001.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
     void <init>() -> <init>
-    void m() -> a
     void keep() -> keep
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-002.txt
index 6fc69ba..422da79 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-002.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
     void <init>() -> <init>
-    void m() -> a
     void keep2() -> keep2
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-003.txt b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-003.txt
index d9bde3b..bf98e39 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-003.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-003.txt
@@ -1,6 +1,6 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
     void <init>() -> <init>
-    void m() -> a
     void keep3() -> keep3
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+    void m() -> renamedM
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-004.txt b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-004.txt
index 8f3f534..376accb 100644
--- a/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-004.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test008/refsObfuscationWithMapping/expected-004.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test008.jack.A -> com.android.jack.shrob.test008.jack.A:
     void <init>() -> <init>
     void keep4() -> keep4
-com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.a:
+com.android.jack.shrob.test008.jack.MyException -> com.android.jack.shrob.test008.jack.RenamedMyException:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags001.mapping
deleted file mode 100644
index 900362c..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags001.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test009.jack.A -> com.android.jack.shrob.test009.jack.A:
-    void m(int,boolean,float,long) -> m
diff --git a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags002.mapping
deleted file mode 100644
index 900362c..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags002.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test009.jack.A -> com.android.jack.shrob.test009.jack.A:
-    void m(int,boolean,float,long) -> m
diff --git a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags003.mapping
deleted file mode 100644
index 900362c..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test009/proguard.flags003.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test009.jack.A -> com.android.jack.shrob.test009.jack.A:
-    void m(int,boolean,float,long) -> m
diff --git a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags001.mapping
index fb83ecd..40d45af 100644
--- a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags001.mapping
@@ -1,2 +1 @@
-com.android.jack.shrob.test010.jack.B -> com.android.jack.shrob.test010.jack.B:
-    void keep() -> keep
+com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.RenamedA:
diff --git a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags002.mapping
deleted file mode 100644
index c66dc7a..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags002.mapping
+++ /dev/null
@@ -1,3 +0,0 @@
-com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.A:
-    java.lang.Object get() -> get
-    void set(java.lang.Object) -> set
diff --git a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags003.mapping b/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags003.mapping
index 6829e58..e32b485 100644
--- a/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags003.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test010/proguard.flags003.mapping
@@ -1,4 +1 @@
-com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.A:
-    java.lang.Object get() -> get
-    void set(com.android.jack.shrob.test010.jack.C) -> set
-com.android.jack.shrob.test010.jack.C -> com.android.jack.shrob.test010.jack.a:
+com.android.jack.shrob.test010.jack.C -> com.android.jack.shrob.test010.jack.RenamedC:
diff --git a/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-001.txt
index 370e43e..698145e 100644
--- a/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test010.jack.B -> com.android.jack.shrob.test010.jack.B:
     void <init>() -> <init>
     void keep() -> keep
-com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.a:
+com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.RenamedA:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-003.txt b/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-003.txt
index 415214d..92c67ea 100644
--- a/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-003.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test010/refsObfuscationWithMapping/expected-003.txt
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test010.jack.C -> com.android.jack.shrob.test010.jack.a:
+com.android.jack.shrob.test010.jack.C -> com.android.jack.shrob.test010.jack.RenamedC:
     void <init>() -> <init>
 com.android.jack.shrob.test010.jack.A -> com.android.jack.shrob.test010.jack.A:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags001.mapping
index 20cd8cd..cfd70e5 100644
--- a/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags001.mapping
@@ -1,3 +1,2 @@
-com.android.jack.shrob.test011.jack.A -> com.android.jack.shrob.test011.jack.A:
-    java.lang.Object keep1() -> keep1
-com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.a:
+com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.RenamedB:
+com.android.jack.shrob.test011.jack.C -> com.android.jack.shrob.test011.jack.RenamedC:
diff --git a/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags002.mapping
index b4d6638..b14d9cd 100644
--- a/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test011/proguard.flags002.mapping
@@ -1,4 +1,2 @@
-com.android.jack.shrob.test011.jack.A -> com.android.jack.shrob.test011.jack.A:
-    int keep2() -> keep2
-com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.a:
-    int value() -> a
+com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.RenamedB:
+    int value() -> renamedValue
diff --git a/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-001.txt
index 4b930bf..681f4ba 100644
--- a/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-001.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.a:
+com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test011.jack.C -> com.android.jack.shrob.test011.jack.b:
+com.android.jack.shrob.test011.jack.C -> com.android.jack.shrob.test011.jack.RenamedC:
     void <init>() -> <init>
 com.android.jack.shrob.test011.jack.A -> com.android.jack.shrob.test011.jack.A:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-002.txt
index a1dd7bc..7365948 100644
--- a/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test011/refsObfuscationWithMapping/expected-002.txt
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.a:
+com.android.jack.shrob.test011.jack.B -> com.android.jack.shrob.test011.jack.RenamedB:
     void <init>() -> <init>
-    int value() -> a
+    int value() -> renamedValue
 com.android.jack.shrob.test011.jack.A -> com.android.jack.shrob.test011.jack.A:
     void <init>() -> <init>
     int keep2() -> keep2
diff --git a/jack-tests/tests/com/android/jack/shrob/test012/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test012/proguard.flags001.mapping
deleted file mode 100644
index 904d812..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test012/proguard.flags001.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test012.jack.A -> com.android.jack.shrob.test012.jack.A:
-    void m(com.android.jack.shrob.test012.jack.A) -> m
diff --git a/jack-tests/tests/com/android/jack/shrob/test013/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test013/proguard.flags001.mapping
deleted file mode 100644
index 053e592..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test013/proguard.flags001.mapping
+++ /dev/null
@@ -1,2 +0,0 @@
-com.android.jack.shrob.test013.jack.A -> com.android.jack.shrob.test013.jack.A:
-    26:26:void m(com.android.jack.shrob.test013.jack.A) -> m
diff --git a/jack-tests/tests/com/android/jack/shrob/test014/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test014/proguard.flags001.mapping
index 9cede76..9bd0a54 100644
--- a/jack-tests/tests/com/android/jack/shrob/test014/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test014/proguard.flags001.mapping
@@ -1,18 +1,16 @@
 com.android.jack.shrob.test014.jack.A -> com.android.jack.shrob.test014.jack.A:
-    int a -> a
-    int m -> b
-    boolean b -> c
-    void m() -> b
-    void f() -> c
-    void m(int) -> a
-    void g() -> d
-    void keep() -> keep
+    int a -> renamedA
+    int m -> renamedM
+    boolean b -> renamedB
+    void m() -> renamedM
+    void f() -> renamedF
+    void m(int) -> renamedM
+    void g() -> renamedG
 com.android.jack.shrob.test014.jack.B -> com.android.jack.shrob.test014.jack.B:
-    char c -> d
-    boolean m -> e
-    void a() -> a
-    void r() -> e
-    void m() -> b
-    void l() -> f
-    void m(int) -> a
-    void keep() -> keep
+    char c -> renamedC
+    boolean m -> renamedM
+    void a() -> renamedA
+    void r() -> renamedR
+    void m() -> renamedM
+    void l() -> renamedL
+    void m(int) -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test014/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test014/refsObfuscationWithMapping/expected-001.txt
index 1572c2d..0790e02 100644
--- a/jack-tests/tests/com/android/jack/shrob/test014/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test014/refsObfuscationWithMapping/expected-001.txt
@@ -1,20 +1,20 @@
 com.android.jack.shrob.test014.jack.B -> com.android.jack.shrob.test014.jack.B:
-    char c -> d
-    boolean m -> e
+    char c -> renamedC
+    boolean m -> renamedM
     void <init>() -> <init>
-    void a() -> a
-    void r() -> e
-    void m() -> b
-    void l() -> f
-    void m(int) -> a
+    void a() -> renamedA
     void keep() -> keep
+    void l() -> renamedL
+    void m() -> renamedM
+    void m(int) -> renamedM
+    void r() -> renamedR
 com.android.jack.shrob.test014.jack.A -> com.android.jack.shrob.test014.jack.A:
-    int a -> a
-    int m -> b
-    boolean b -> c
+    int a -> renamedA
+    boolean b -> renamedB
+    int m -> renamedM
     void <init>() -> <init>
-    void m() -> b
-    void f() -> c
-    void m(int) -> a
-    void g() -> d
+    void f() -> renamedF
+    void g() -> renamedG
     void keep() -> keep
+    void m() -> renamedM
+    void m(int) -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test015/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test015/proguard.flags001.mapping
index 83bfd4a..76594dd 100644
--- a/jack-tests/tests/com/android/jack/shrob/test015/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test015/proguard.flags001.mapping
@@ -1,6 +1,6 @@
-com.android.jack.shrob.test015.jack.A -> a.a.a.a.a.a.a:
-    23:23:com.android.jack.shrob.test015.jack.B m() -> a
-    28:28:void m(com.android.jack.shrob.test015.jack.A) -> a
-com.android.jack.shrob.test015.jack.A$I -> a.a.a.a.a.a.a$a:
-com.android.jack.shrob.test015.jack.A$J -> a.a.a.a.a.a.a$b:
-com.android.jack.shrob.test015.jack.B -> a.a.a.a.a.a.b:
+com.android.jack.shrob.test015.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA:
+    23:23:com.android.jack.shrob.test015.jack.B m() -> renamedM
+    28:28:void m(com.android.jack.shrob.test015.jack.A) -> renamedM
+com.android.jack.shrob.test015.jack.A$I -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA$I:
+com.android.jack.shrob.test015.jack.A$J -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA$J:
+com.android.jack.shrob.test015.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedB:
diff --git a/jack-tests/tests/com/android/jack/shrob/test015/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test015/refsObfuscationWithMapping/expected-001.txt
index 41f353e..4f187a6 100644
--- a/jack-tests/tests/com/android/jack/shrob/test015/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test015/refsObfuscationWithMapping/expected-001.txt
@@ -1,8 +1,8 @@
-com.android.jack.shrob.test015.jack.B -> a.a.a.a.a.a.b:
+com.android.jack.shrob.test015.jack.B -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedB:
     void <init>() -> <init>
-com.android.jack.shrob.test015.jack.A -> a.a.a.a.a.a.a:
+com.android.jack.shrob.test015.jack.A -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA:
     void <init>() -> <init>
-    com.android.jack.shrob.test015.jack.B m() -> a
-    void m(com.android.jack.shrob.test015.jack.A) -> a
-com.android.jack.shrob.test015.jack.A$I -> a.a.a.a.a.a.a$a:
-com.android.jack.shrob.test015.jack.A$J -> a.a.a.a.a.a.a$b:
+    com.android.jack.shrob.test015.jack.B m() -> renamedM
+    void m(com.android.jack.shrob.test015.jack.A) -> renamedM
+com.android.jack.shrob.test015.jack.A$I -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA$I:
+com.android.jack.shrob.test015.jack.A$J -> renamedCom.renamedAndroid.renamedJack.renamedShrob.renamedTest015.renamedJack.RenamedA$J:
diff --git a/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags001.mapping
index 2a96f6c..74ff488 100644
--- a/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags001.mapping
@@ -1,17 +1,22 @@
-com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.a:
-com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.b:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.c:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.d:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.e:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.f:
-    java.lang.String value() -> value
+com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.RenamedAnnot:
+    java.lang.String value() -> renamedValue
 com.android.jack.shrob.test016.jack.KeepClass -> com.android.jack.shrob.test016.jack.KeepClass:
-    java.lang.String value() -> value
-    java.lang.String value2() -> value2
-    java.lang.String value3() -> value3
-    java.lang.String value4() -> value4
-    java.lang.String value5() -> value5
\ No newline at end of file
+    void <init>() -> <init>
+    java.lang.String value() -> renamedValue
+    java.lang.String value2() -> renamedValue2
+    java.lang.String value3() -> renamedValue3
+    java.lang.String value4() -> renamedValue4
+    java.lang.String value5() -> renamedValue5
+    java.lang.String value6() -> renamedValue6
+    java.lang.String value7() -> renamedValue7
+    java.lang.String value8() -> renamedValue8
+    java.lang.String value9() -> renamedValue9
+com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.RenamedAnnot4:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.RenamedAnnot5:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.RenamedA:
+com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.RenamedAnnot2:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.RenamedAnnot3:
+    java.lang.String value() -> renamedValue
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags002.mapping b/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags002.mapping
index 64c97e9..a7ca2bf 100644
--- a/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags002.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test016/proguard.flags002.mapping
@@ -1,21 +1,21 @@
-com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.a:
-com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.b:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.c:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.d:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.e:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.f:
-    java.lang.String value() -> a
+com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.RenamedA:
+com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.RenamedAnnot:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.RenamedAnnot2:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.RenamedAnnot3:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.RenamedAnnot4:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.RenamedAnnot5:
+    java.lang.String value() -> renamedValue
 com.android.jack.shrob.test016.jack.KeepClass -> com.android.jack.shrob.test016.jack.KeepClass:
-    java.lang.String value() -> a
-    java.lang.String value2() -> b
-    java.lang.String value3() -> c
-    java.lang.String value4() -> d
-    java.lang.String value5() -> e
-    java.lang.String value6() -> f
-    java.lang.String value7() -> g
-    java.lang.String value8() -> h
-    java.lang.String value9() -> i
\ No newline at end of file
+    java.lang.String value() -> renamedValue
+    java.lang.String value2() -> renamedValue2
+    java.lang.String value3() -> renamedValue3
+    java.lang.String value4() -> renamedValue4
+    java.lang.String value5() -> renamedValue5
+    java.lang.String value6() -> renamedValue6
+    java.lang.String value7() -> renamedValue7
+    java.lang.String value8() -> renamedValue8
+    java.lang.String value9() -> renamedValue9
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-001.txt
index 3eb5acf..bc4aa5c 100644
--- a/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-001.txt
@@ -1,23 +1,23 @@
-com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.b:
-    java.lang.String value() -> value
+com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.RenamedAnnot:
+    java.lang.String value() -> renamedValue
 com.android.jack.shrob.test016.jack.KeepClass -> com.android.jack.shrob.test016.jack.KeepClass:
     void <init>() -> <init>
-    java.lang.String value() -> value
-    java.lang.String value2() -> value2
-    java.lang.String value3() -> value3
-    java.lang.String value4() -> value4
-    java.lang.String value5() -> value5
-    java.lang.String value6() -> value6
-    java.lang.String value7() -> value7
-    java.lang.String value8() -> value8
-    java.lang.String value9() -> value9
-com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.e:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.f:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.a:
+    java.lang.String value() -> renamedValue
+    java.lang.String value2() -> renamedValue2
+    java.lang.String value3() -> renamedValue3
+    java.lang.String value4() -> renamedValue4
+    java.lang.String value5() -> renamedValue5
+    java.lang.String value6() -> renamedValue6
+    java.lang.String value7() -> renamedValue7
+    java.lang.String value8() -> renamedValue8
+    java.lang.String value9() -> renamedValue9
+com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.RenamedAnnot4:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.RenamedAnnot5:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.c:
-    java.lang.String value() -> value
-com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.d:
-    java.lang.String value() -> value
+com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.RenamedAnnot2:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.RenamedAnnot3:
+    java.lang.String value() -> renamedValue
diff --git a/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-002.txt b/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-002.txt
index cb9d1db..bc4aa5c 100644
--- a/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-002.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test016/refsObfuscationWithMapping/expected-002.txt
@@ -1,23 +1,23 @@
-com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.b:
-    java.lang.String value() -> a
+com.android.jack.shrob.test016.jack.Annot -> com.android.jack.shrob.test016.jack.RenamedAnnot:
+    java.lang.String value() -> renamedValue
 com.android.jack.shrob.test016.jack.KeepClass -> com.android.jack.shrob.test016.jack.KeepClass:
     void <init>() -> <init>
-    java.lang.String value() -> a
-    java.lang.String value2() -> b
-    java.lang.String value3() -> c
-    java.lang.String value4() -> d
-    java.lang.String value5() -> e
-    java.lang.String value6() -> f
-    java.lang.String value7() -> g
-    java.lang.String value8() -> h
-    java.lang.String value9() -> i
-com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.e:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.f:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.a:
+    java.lang.String value() -> renamedValue
+    java.lang.String value2() -> renamedValue2
+    java.lang.String value3() -> renamedValue3
+    java.lang.String value4() -> renamedValue4
+    java.lang.String value5() -> renamedValue5
+    java.lang.String value6() -> renamedValue6
+    java.lang.String value7() -> renamedValue7
+    java.lang.String value8() -> renamedValue8
+    java.lang.String value9() -> renamedValue9
+com.android.jack.shrob.test016.jack.Annot4 -> com.android.jack.shrob.test016.jack.RenamedAnnot4:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot5 -> com.android.jack.shrob.test016.jack.RenamedAnnot5:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.A -> com.android.jack.shrob.test016.jack.RenamedA:
     void <init>() -> <init>
-com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.c:
-    java.lang.String value() -> a
-com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.d:
-    java.lang.String value() -> a
+com.android.jack.shrob.test016.jack.Annot2 -> com.android.jack.shrob.test016.jack.RenamedAnnot2:
+    java.lang.String value() -> renamedValue
+com.android.jack.shrob.test016.jack.Annot3 -> com.android.jack.shrob.test016.jack.RenamedAnnot3:
+    java.lang.String value() -> renamedValue
diff --git a/jack-tests/tests/com/android/jack/shrob/test017/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test017/proguard.flags001.mapping
index 602f21a..135648c 100644
--- a/jack-tests/tests/com/android/jack/shrob/test017/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test017/proguard.flags001.mapping
@@ -1,10 +1,10 @@
-com.android.jack.shrob.test017.jack.Reflect2 -> com.android.jack.shrob.test017.jack.a:
-com.android.jack.shrob.test017.jack.Reflect2$A -> com.android.jack.shrob.test017.jack.b:
-com.android.jack.shrob.test017.jack.Reflect2$B -> com.android.jack.shrob.test017.jack.c:
-com.android.jack.shrob.test017.jack.Reflect3 -> com.android.jack.shrob.test017.jack.d:
-    int fieldPublic -> a
-    long fieldLong -> b
-    long fieldLong3 -> c
-    long fieldLong4 -> d
-    com.android.jack.shrob.test017.jack.Reflect2$A a -> e
-    47:47:void m(com.android.jack.shrob.test017.jack.Reflect2$A) -> a
\ No newline at end of file
+com.android.jack.shrob.test017.jack.Reflect2 -> com.android.jack.shrob.test017.jack.RenamedReflect2:
+com.android.jack.shrob.test017.jack.Reflect2$A -> com.android.jack.shrob.test017.jack.RenamedReflect2$A:
+com.android.jack.shrob.test017.jack.Reflect2$B -> com.android.jack.shrob.test017.jack.RenamedReflect2$B:
+com.android.jack.shrob.test017.jack.Reflect3 -> com.android.jack.shrob.test017.jack.RenamedReflect3:
+    int fieldPublic -> renamedFieldPublic
+    long fieldLong -> renamedFieldLong
+    long fieldLong3 -> renamedFieldLong3
+    long fieldLong4 -> renamedFieldLong4
+    com.android.jack.shrob.test017.jack.Reflect2$A a -> renamedA
+    47:47:void m(com.android.jack.shrob.test017.jack.Reflect2$A) -> renamedM
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test017/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test017/refsObfuscationWithMapping/expected-001.txt
index b393f13..8e97b63 100644
--- a/jack-tests/tests/com/android/jack/shrob/test017/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test017/refsObfuscationWithMapping/expected-001.txt
@@ -4,11 +4,11 @@
     void keep3() -> keep3
     void keep4() -> keep4
     void keep5() -> keep5
-com.android.jack.shrob.test017.jack.Reflect3 -> com.android.jack.shrob.test017.jack.d:
-    int fieldPublic -> a
+com.android.jack.shrob.test017.jack.Reflect3 -> com.android.jack.shrob.test017.jack.RenamedReflect3:
+    int fieldPublic -> renamedFieldPublic
     void <init>() -> <init>
-    void m(com.android.jack.shrob.test017.jack.Reflect2$A) -> a
-com.android.jack.shrob.test017.jack.Reflect2 -> com.android.jack.shrob.test017.jack.a:
+    void m(com.android.jack.shrob.test017.jack.Reflect2$A) -> renamedM
+com.android.jack.shrob.test017.jack.Reflect2 -> com.android.jack.shrob.test017.jack.RenamedReflect2:
     void <init>() -> <init>
-com.android.jack.shrob.test017.jack.Reflect2$A -> com.android.jack.shrob.test017.jack.b:
-com.android.jack.shrob.test017.jack.Reflect2$B -> com.android.jack.shrob.test017.jack.c:
+com.android.jack.shrob.test017.jack.Reflect2$A -> com.android.jack.shrob.test017.jack.RenamedReflect2$A:
+com.android.jack.shrob.test017.jack.Reflect2$B -> com.android.jack.shrob.test017.jack.RenamedReflect2$B:
diff --git a/jack-tests/tests/com/android/jack/shrob/test019/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test019/refsObfuscationWithMapping/expected-001.txt
index b108b6f..3d3e14e 100644
--- a/jack-tests/tests/com/android/jack/shrob/test019/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test019/refsObfuscationWithMapping/expected-001.txt
@@ -4,7 +4,7 @@
     void <init>() -> <init>
 com.android.jack.shrob.test019.jack.B$C$Inner4 -> com.android.jack.shrob.test019.jack.B$C$Inner4:
     void <init>() -> <init>
-com.android.jack.shrob.test019.jack.B$E -> com.android.jack.shrob.test019.jack.a:
+com.android.jack.shrob.test019.jack.B$E -> com.android.jack.shrob.test019.jack.RenamedB$E:
     void <init>() -> <init>
 com.android.jack.shrob.test019.jack.B$E$1 -> com.android.jack.shrob.test019.jack.B$E$1:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test021/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test021/proguard.flags001.mapping
new file mode 100644
index 0000000..14597dc
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test021/proguard.flags001.mapping
@@ -0,0 +1,2 @@
+com.android.jack.shrob.test021.jack.Shrob021$KeptInterface -> com.android.jack.shrob.test021.jack.RenamedShrob021$KeptInterface:
+    void interfaceMethod() -> renamedInterfaceMethod
diff --git a/jack-tests/tests/com/android/jack/shrob/test021/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test021/refsObfuscationWithMapping/expected-001.txt
index 9e8e7d8..a923f0f 100644
--- a/jack-tests/tests/com/android/jack/shrob/test021/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test021/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test021.jack.Shrob021 -> com.android.jack.shrob.test021.jack.Shrob021:
     void <init>() -> <init>
     int toKeep() -> toKeep
-com.android.jack.shrob.test021.jack.Shrob021$KeptInterface -> com.android.jack.shrob.test021.jack.a:
-    void interfaceMethod() -> a
+com.android.jack.shrob.test021.jack.Shrob021$KeptInterface -> com.android.jack.shrob.test021.jack.RenamedShrob021$KeptInterface:
+    void interfaceMethod() -> renamedInterfaceMethod
diff --git a/jack-tests/tests/com/android/jack/shrob/test022/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test022/proguard.flags001.mapping
new file mode 100644
index 0000000..7ce5a1d
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test022/proguard.flags001.mapping
@@ -0,0 +1 @@
+com.android.jack.shrob.test022.jack.AbstractClass -> com.android.jack.shrob.test022.jack.RenamedAbstractClass:
diff --git a/jack-tests/tests/com/android/jack/shrob/test022/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test022/refsObfuscationWithMapping/expected-001.txt
index c0c3b70..21d2582 100644
--- a/jack-tests/tests/com/android/jack/shrob/test022/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test022/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test022.jack.Shrob022 -> com.android.jack.shrob.test022.jack.Shrob022:
     void <init>() -> <init>
     void method() -> method
-com.android.jack.shrob.test022.jack.AbstractClass -> com.android.jack.shrob.test022.jack.a:
+com.android.jack.shrob.test022.jack.AbstractClass -> com.android.jack.shrob.test022.jack.RenamedAbstractClass:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test023/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test023/proguard.flags001.mapping
new file mode 100644
index 0000000..b5eb082
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test023/proguard.flags001.mapping
@@ -0,0 +1,3 @@
+com.android.jack.shrob.test023.jack.Outer$Inner -> com.android.jack.shrob.test023.jack.Outer$Inner:
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test023/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test023/refsObfuscationWithMapping/expected-001.txt
index c3debfc..ae96dbb 100644
--- a/jack-tests/tests/com/android/jack/shrob/test023/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test023/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test023.jack.Outer$Inner -> com.android.jack.shrob.test023.jack.Outer$Inner:
     void <init>() -> <init>
     void <init>(int) -> <init>
-    void m() -> a
-    void m2() -> b
+    void m() -> renamedM
+    void m2() -> renamedM2
diff --git a/jack-tests/tests/com/android/jack/shrob/test025/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test025/refsObfuscationWithMapping/expected-001.txt
index c297699..0072c41 100644
--- a/jack-tests/tests/com/android/jack/shrob/test025/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test025/refsObfuscationWithMapping/expected-001.txt
@@ -1,7 +1,7 @@
 com.android.jack.shrob.test025.jack.Keep -> com.android.jack.shrob.test025.jack.Keep:
     void <init>() -> <init>
-    java.lang.String m(java.lang.String) -> m
     java.lang.String keep() -> keep
+    java.lang.String m(java.lang.String) -> m
 com.android.jack.shrob.test025.jack.A$I -> com.android.jack.shrob.test025.jack.A$I:
 com.android.jack.shrob.test025.jack.A$I2 -> com.android.jack.shrob.test025.jack.A$I2:
     java.lang.String s -> s
diff --git a/jack-tests/tests/com/android/jack/shrob/test026/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test026/proguard.flags001.mapping
new file mode 100644
index 0000000..5a7008f
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test026/proguard.flags001.mapping
@@ -0,0 +1,2 @@
+com.android.jack.shrob.test026.jack.Enum -> com.android.jack.shrob.test026.jack.Enum:
+    com.android.jack.shrob.test026.jack.Enum[] $VALUES -> renamed$VALUES
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test026/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test026/refsObfuscationWithMapping/expected-001.txt
index c64557f..f41d8e6 100644
--- a/jack-tests/tests/com/android/jack/shrob/test026/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test026/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test026.jack.Enum -> com.android.jack.shrob.test026.jack.Enum:
-    com.android.jack.shrob.test026.jack.Enum[] $VALUES -> a
-    void <clinit>() -> <clinit>
+    com.android.jack.shrob.test026.jack.Enum[] $VALUES -> renamed$VALUES
     com.android.jack.shrob.test026.jack.Enum valueOf(java.lang.String) -> valueOf
     com.android.jack.shrob.test026.jack.Enum[] values() -> values
+    void <clinit>() -> <clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.class b/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.class
deleted file mode 100644
index be729ee..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.class
+++ /dev/null
Binary files differ
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.java b/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.java
deleted file mode 100644
index 2b797c9..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test027/lib/ForName.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.jack.shrob.test027.lib;
-
-public class ForName {
-  public static Class<?> keptMethod() throws ClassNotFoundException {
-    return Class.forName("com.android.jack.shrob.test027.jack.A");
-  }
-}
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/proguard.flags001 b/jack-tests/tests/com/android/jack/shrob/test027/proguard.flags001
deleted file mode 100644
index 0be8a6a..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test027/proguard.flags001
+++ /dev/null
@@ -1,3 +0,0 @@
--keep class **.ForName {
-  *;
-}
\ No newline at end of file
diff --git a/jack-tests/tests/com/android/jack/shrob/test027/refsShrinking/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test027/refsShrinking/expected-001.txt
deleted file mode 100644
index 8525ee8..0000000
--- a/jack-tests/tests/com/android/jack/shrob/test027/refsShrinking/expected-001.txt
+++ /dev/null
@@ -1,5 +0,0 @@
-Lcom/android/jack/shrob/test027/jack/A;:
-<init>()V
-Lcom/android/jack/shrob/test027/lib/ForName;:
-<init>()V
-keptMethod()Ljava/lang/Class;
diff --git a/jack-tests/tests/com/android/jack/shrob/test029/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test029/proguard.flags001.mapping
index 11178a1..4d69ede 100644
--- a/jack-tests/tests/com/android/jack/shrob/test029/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test029/proguard.flags001.mapping
@@ -1,5 +1,5 @@
-com.android.jack.shrob.test029.jack.I -> com.android.jack.shrob.test029.jack.a:
-com.android.jack.shrob.test029.jack.B -> com.android.jack.shrob.test029.jack.b:
-    com.android.jack.shrob.test029.jack.B get(com.android.jack.shrob.test029.jack.I) -> a
-com.android.jack.shrob.test029.jack.C -> com.android.jack.shrob.test029.jack.c:
-com.android.jack.shrob.test029.jack.A -> com.android.jack.shrob.test029.jack.d:
+com.android.jack.shrob.test029.jack.I -> com.android.jack.shrob.test029.jack.RenamedI:
+com.android.jack.shrob.test029.jack.B -> com.android.jack.shrob.test029.jack.RenamedB:
+    com.android.jack.shrob.test029.jack.B get(com.android.jack.shrob.test029.jack.I) -> renamedGet
+com.android.jack.shrob.test029.jack.C -> com.android.jack.shrob.test029.jack.RenamedC:
+com.android.jack.shrob.test029.jack.A -> com.android.jack.shrob.test029.jack.RenamedA:
diff --git a/jack-tests/tests/com/android/jack/shrob/test029/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test029/refsObfuscationWithMapping/expected-001.txt
index b3feff8..2b074ac 100644
--- a/jack-tests/tests/com/android/jack/shrob/test029/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test029/refsObfuscationWithMapping/expected-001.txt
@@ -1,12 +1,12 @@
 com.android.jack.shrob.test029.jack.Kept -> com.android.jack.shrob.test029.jack.Kept:
     void <init>() -> <init>
     void kept() -> kept
-com.android.jack.shrob.test029.jack.I -> com.android.jack.shrob.test029.jack.a:
+com.android.jack.shrob.test029.jack.I -> com.android.jack.shrob.test029.jack.RenamedI:
     void <init>() -> <init>
-com.android.jack.shrob.test029.jack.B -> com.android.jack.shrob.test029.jack.b:
+com.android.jack.shrob.test029.jack.B -> com.android.jack.shrob.test029.jack.RenamedB:
     void <init>() -> <init>
-    com.android.jack.shrob.test029.jack.B get(com.android.jack.shrob.test029.jack.I) -> a
-com.android.jack.shrob.test029.jack.C -> com.android.jack.shrob.test029.jack.c:
+    com.android.jack.shrob.test029.jack.B get(com.android.jack.shrob.test029.jack.I) -> renamedGet
+com.android.jack.shrob.test029.jack.C -> com.android.jack.shrob.test029.jack.RenamedC:
     void <init>() -> <init>
-com.android.jack.shrob.test029.jack.A -> com.android.jack.shrob.test029.jack.d:
+com.android.jack.shrob.test029.jack.A -> com.android.jack.shrob.test029.jack.RenamedA:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test030/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test030/proguard.flags001.mapping
index a8740da..7f9b50c 100644
--- a/jack-tests/tests/com/android/jack/shrob/test030/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test030/proguard.flags001.mapping
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test030.jack.I -> com.android.jack.shrob.test030.jack.a:
-	int m() -> a
-com.android.jack.shrob.test030.jack.A -> com.android.jack.shrob.test030.jack.b:
-	int m() -> a
+com.android.jack.shrob.test030.jack.Kept -> com.android.jack.shrob.test030.jack.Kept:
+com.android.jack.shrob.test030.jack.I -> com.android.jack.shrob.test030.jack.RenamedI:
+com.android.jack.shrob.test030.jack.A -> com.android.jack.shrob.test030.jack.RenamedA:
+    int m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test030/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test030/refsObfuscationWithMapping/expected-001.txt
index 5ba496e..2419711 100644
--- a/jack-tests/tests/com/android/jack/shrob/test030/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test030/refsObfuscationWithMapping/expected-001.txt
@@ -1,10 +1,10 @@
 com.android.jack.shrob.test030.jack.Kept -> com.android.jack.shrob.test030.jack.Kept:
     void <init>() -> <init>
     int kept(com.android.jack.shrob.test030.jack.I) -> kept
-com.android.jack.shrob.test030.jack.I -> com.android.jack.shrob.test030.jack.a:
-    int m() -> a
+com.android.jack.shrob.test030.jack.I -> com.android.jack.shrob.test030.jack.RenamedI:
+    int m() -> renamedM
 com.android.jack.shrob.test030.jack.B -> com.android.jack.shrob.test030.jack.B:
     void <init>() -> <init>
-com.android.jack.shrob.test030.jack.A -> com.android.jack.shrob.test030.jack.b:
+com.android.jack.shrob.test030.jack.A -> com.android.jack.shrob.test030.jack.RenamedA:
     void <init>() -> <init>
-    int m() -> a
+    int m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test031/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test031/proguard.flags001.mapping
index 6a76a4c..09aa9cc 100644
--- a/jack-tests/tests/com/android/jack/shrob/test031/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test031/proguard.flags001.mapping
@@ -1,16 +1,4 @@
-com.android.jack.shrob.test031.jack.E -> com.android.jack.shrob.test031.jack.E:
-	void <init>() -> <init>
-com.android.jack.shrob.test031.jack.Kept -> com.android.jack.shrob.test031.jack.Kept:
-	void <init>() -> <init>
-	int kept(com.android.jack.shrob.test031.jack.I) -> kept
-com.android.jack.shrob.test031.jack.I -> com.android.jack.shrob.test031.jack.a:
-	int m() -> a
-com.android.jack.shrob.test031.jack.F -> com.android.jack.shrob.test031.jack.b:
-	void <init>() -> <init>
-com.android.jack.shrob.test031.jack.B -> com.android.jack.shrob.test031.jack.B:
-	void <init>() -> <init>
-com.android.jack.shrob.test031.jack.D -> com.android.jack.shrob.test031.jack.D:
-	void <init>() -> <init>
-com.android.jack.shrob.test031.jack.A -> com.android.jack.shrob.test031.jack.c:
-	void <init>() -> <init>
-	int m() -> a
+com.android.jack.shrob.test031.jack.I -> com.android.jack.shrob.test031.jack.RenamedI:
+	int m() -> renamedM
+com.android.jack.shrob.test031.jack.F -> com.android.jack.shrob.test031.jack.RenamedF:
+com.android.jack.shrob.test031.jack.A -> com.android.jack.shrob.test031.jack.RenamedA:
diff --git a/jack-tests/tests/com/android/jack/shrob/test031/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test031/refsObfuscationWithMapping/expected-001.txt
index d5d1daf..89eb0ed 100644
--- a/jack-tests/tests/com/android/jack/shrob/test031/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test031/refsObfuscationWithMapping/expected-001.txt
@@ -3,14 +3,14 @@
 com.android.jack.shrob.test031.jack.Kept -> com.android.jack.shrob.test031.jack.Kept:
     void <init>() -> <init>
     int kept(com.android.jack.shrob.test031.jack.I) -> kept
-com.android.jack.shrob.test031.jack.I -> com.android.jack.shrob.test031.jack.a:
-    int m() -> a
-com.android.jack.shrob.test031.jack.F -> com.android.jack.shrob.test031.jack.b:
+com.android.jack.shrob.test031.jack.I -> com.android.jack.shrob.test031.jack.RenamedI:
+    int m() -> renamedM
+com.android.jack.shrob.test031.jack.F -> com.android.jack.shrob.test031.jack.RenamedF:
     void <init>() -> <init>
 com.android.jack.shrob.test031.jack.B -> com.android.jack.shrob.test031.jack.B:
     void <init>() -> <init>
 com.android.jack.shrob.test031.jack.D -> com.android.jack.shrob.test031.jack.D:
     void <init>() -> <init>
-com.android.jack.shrob.test031.jack.A -> com.android.jack.shrob.test031.jack.c:
+com.android.jack.shrob.test031.jack.A -> com.android.jack.shrob.test031.jack.RenamedA:
     void <init>() -> <init>
-    int m() -> a
+    int m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test032/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test032/proguard.flags001.mapping
index ac19db9..80c9322 100644
--- a/jack-tests/tests/com/android/jack/shrob/test032/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test032/proguard.flags001.mapping
@@ -1,4 +1,4 @@
-com.android.jack.shrob.test032.jack.I -> com.android.jack.shrob.test032.jack.a:
-com.android.jack.shrob.test032.jack.B -> com.android.jack.shrob.test032.jack.b:
-com.android.jack.shrob.test032.jack.A -> com.android.jack.shrob.test032.jack.c:
-  int m() -> a
+com.android.jack.shrob.test032.jack.I -> com.android.jack.shrob.test032.jack.RenamedI:
+com.android.jack.shrob.test032.jack.B -> com.android.jack.shrob.test032.jack.RenamedB:
+com.android.jack.shrob.test032.jack.A -> com.android.jack.shrob.test032.jack.RenamedA:
+  int m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test032/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test032/refsObfuscationWithMapping/expected-001.txt
index c9a8f93..1f831ef 100644
--- a/jack-tests/tests/com/android/jack/shrob/test032/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test032/refsObfuscationWithMapping/expected-001.txt
@@ -1,13 +1,13 @@
 com.android.jack.shrob.test032.jack.Kept -> com.android.jack.shrob.test032.jack.Kept:
     void <init>() -> <init>
     int kept(com.android.jack.shrob.test032.jack.I) -> kept
-com.android.jack.shrob.test032.jack.I -> com.android.jack.shrob.test032.jack.a:
-    int m() -> a
-com.android.jack.shrob.test032.jack.B -> com.android.jack.shrob.test032.jack.b:
+com.android.jack.shrob.test032.jack.I -> com.android.jack.shrob.test032.jack.RenamedI:
+    int m() -> renamedM
+com.android.jack.shrob.test032.jack.B -> com.android.jack.shrob.test032.jack.RenamedB:
     void <init>() -> <init>
 com.android.jack.shrob.test032.jack.C -> com.android.jack.shrob.test032.jack.C:
     void <init>() -> <init>
-    int m() -> a
-com.android.jack.shrob.test032.jack.A -> com.android.jack.shrob.test032.jack.c:
+    int m() -> renamedM
+com.android.jack.shrob.test032.jack.A -> com.android.jack.shrob.test032.jack.RenamedA:
     void <init>() -> <init>
-    int m() -> a
+    int m() -> renamedM
diff --git a/jack-tests/tests/com/android/jack/shrob/test036/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test036/proguard.flags001.mapping
new file mode 100644
index 0000000..8b692a9
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test036/proguard.flags001.mapping
@@ -0,0 +1,8 @@
+com.android.jack.shrob.test036.jack.E -> com.android.jack.shrob.test036.jack.RenamedE:
+    com.android.jack.shrob.test036.jack.E A -> renamedA
+    com.android.jack.shrob.test036.jack.E B -> renamedB
+    com.android.jack.shrob.test036.jack.E C -> renamedC
+    com.android.jack.shrob.test036.jack.E[] $VALUES -> renamed$VALUES
+    void <init>(java.lang.String,int) -> renamed<init>
+    com.android.jack.shrob.test036.jack.E[] values() -> renamedValues
+    void <clinit>() -> renamed<clinit>
diff --git a/jack-tests/tests/com/android/jack/shrob/test036/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test036/refsObfuscationWithMapping/expected-001.txt
index b024d02..1d7594a 100644
--- a/jack-tests/tests/com/android/jack/shrob/test036/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test036/refsObfuscationWithMapping/expected-001.txt
@@ -1,10 +1,10 @@
-com.android.jack.shrob.test036.jack.E -> com.android.jack.shrob.test036.jack.a:
-    com.android.jack.shrob.test036.jack.E A -> a
-    com.android.jack.shrob.test036.jack.E B -> b
-    com.android.jack.shrob.test036.jack.E C -> c
-    com.android.jack.shrob.test036.jack.E[] $VALUES -> d
+com.android.jack.shrob.test036.jack.E -> com.android.jack.shrob.test036.jack.RenamedE:
+    com.android.jack.shrob.test036.jack.E A -> renamedA
+    com.android.jack.shrob.test036.jack.E B -> renamedB
+    com.android.jack.shrob.test036.jack.E C -> renamedC
+    com.android.jack.shrob.test036.jack.E[] $VALUES -> renamed$VALUES
     void <init>(java.lang.String,int) -> <init>
-    com.android.jack.shrob.test036.jack.E[] values() -> a
+    com.android.jack.shrob.test036.jack.E[] values() -> renamedValues
     void <clinit>() -> <clinit>
 com.android.jack.shrob.test036.jack.Kept -> com.android.jack.shrob.test036.jack.Kept:
     int[] -ESwitchesValues -> -ESwitchesValues
diff --git a/jack-tests/tests/com/android/jack/shrob/test037/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test037/proguard.flags001.mapping
index c6b7a14..34627fe 100644
--- a/jack-tests/tests/com/android/jack/shrob/test037/proguard.flags001.mapping
+++ b/jack-tests/tests/com/android/jack/shrob/test037/proguard.flags001.mapping
@@ -1,3 +1,3 @@
-com.android.jack.shrob.test037.jack.B -> com.android.jack.shrob.test037.jack.a:
-    void m() -> a
-com.android.jack.shrob.test037.jack.A -> com.android.jack.shrob.test037.jack.b:
+com.android.jack.shrob.test037.jack.B -> com.android.jack.shrob.test037.jack.RenamedB:
+    void m() -> renamedM
+com.android.jack.shrob.test037.jack.A -> com.android.jack.shrob.test037.jack.RenamedA:
diff --git a/jack-tests/tests/com/android/jack/shrob/test037/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test037/refsObfuscationWithMapping/expected-001.txt
index b4e8d03..e060833 100644
--- a/jack-tests/tests/com/android/jack/shrob/test037/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test037/refsObfuscationWithMapping/expected-001.txt
@@ -1,8 +1,8 @@
 com.android.jack.shrob.test037.jack.Kept -> com.android.jack.shrob.test037.jack.Kept:
     void <init>() -> <init>
     void kept() -> kept
-com.android.jack.shrob.test037.jack.B -> com.android.jack.shrob.test037.jack.a:
+com.android.jack.shrob.test037.jack.B -> com.android.jack.shrob.test037.jack.RenamedB:
     void <init>() -> <init>
-    void m() -> a
-com.android.jack.shrob.test037.jack.A -> com.android.jack.shrob.test037.jack.b:
+    void m() -> renamedM
+com.android.jack.shrob.test037.jack.A -> com.android.jack.shrob.test037.jack.RenamedA:
     void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test038/proguard.flags001.mapping b/jack-tests/tests/com/android/jack/shrob/test038/proguard.flags001.mapping
new file mode 100644
index 0000000..820fbe8
--- /dev/null
+++ b/jack-tests/tests/com/android/jack/shrob/test038/proguard.flags001.mapping
@@ -0,0 +1,5 @@
+com.android.jack.shrob.test038.jack.Kept -> com.android.jack.shrob.test038.jack.Kept:
+    void <init>() -> <init>
+    void kept() -> kept
+com.android.jack.shrob.test038.jack.Element -> com.android.jack.shrob.test038.jack.RenamedElement:
+    void <init>() -> <init>
diff --git a/jack-tests/tests/com/android/jack/shrob/test038/refsObfuscationWithMapping/expected-001.txt b/jack-tests/tests/com/android/jack/shrob/test038/refsObfuscationWithMapping/expected-001.txt
index db5c11e..820fbe8 100644
--- a/jack-tests/tests/com/android/jack/shrob/test038/refsObfuscationWithMapping/expected-001.txt
+++ b/jack-tests/tests/com/android/jack/shrob/test038/refsObfuscationWithMapping/expected-001.txt
@@ -1,5 +1,5 @@
 com.android.jack.shrob.test038.jack.Kept -> com.android.jack.shrob.test038.jack.Kept:
     void <init>() -> <init>
     void kept() -> kept
-com.android.jack.shrob.test038.jack.Element -> com.android.jack.shrob.test038.jack.a:
+com.android.jack.shrob.test038.jack.Element -> com.android.jack.shrob.test038.jack.RenamedElement:
     void <init>() -> <init>
diff --git a/jack/.settings/org.eclipse.jdt.core.prefs b/jack/.settings/org.eclipse.jdt.core.prefs
index b474ac4..58cab3f 100644
--- a/jack/.settings/org.eclipse.jdt.core.prefs
+++ b/jack/.settings/org.eclipse.jdt.core.prefs
@@ -185,7 +185,7 @@
 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false
 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false
 org.eclipse.jdt.core.formatter.comment.format_block_comments=true
-org.eclipse.jdt.core.formatter.comment.format_header=true
+org.eclipse.jdt.core.formatter.comment.format_header=false
 org.eclipse.jdt.core.formatter.comment.format_html=true
 org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true
 org.eclipse.jdt.core.formatter.comment.format_line_comments=true
diff --git a/jack/src/com/android/jack/CommandLine.java b/jack/src/com/android/jack/CommandLine.java
index 38abde4..8cead0f 100644
--- a/jack/src/com/android/jack/CommandLine.java
+++ b/jack/src/com/android/jack/CommandLine.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.frontend.FrontendCompilationException;
 import com.android.sched.util.TextUtils;
+import com.android.sched.util.UnrecoverableException;
 import com.android.sched.util.config.ChainedException;
 import com.android.sched.util.config.ConfigurationException;
 import com.android.sched.util.config.GatherConfigBuilder;
@@ -77,10 +78,17 @@
       } else if (e instanceof StackOverflowError) {
         System.err.println("Try increasing stack size with java option '-Xss<size>'");
       }
+      System.err.println("Warning: This may have produced partial or corrupted output.");
       logger.log(Level.CONFIG, "Virtual machine error:", e);
       System.exit(ExitStatus.FAILURE_VM);
+    } catch (UnrecoverableException e) {
+      System.err.println("Unrecoverable error: " + e.getMessage());
+      System.err.println("Warning: This may have produced partial or corrupted output.");
+      logger.log(Level.FINE, "Unrecoverable exception:", e);
+      System.exit(ExitStatus.FAILURE_UNRECOVERABLE);
     } catch (Throwable e) {
       System.err.println("Internal compiler error (see log)");
+      System.err.println("Warning: This may have produced partial or corrupted output.");
       logger.log(Level.SEVERE, "Internal compiler error:", e);
 
       System.exit(ExitStatus.FAILURE_INTERNAL);
diff --git a/jack/src/com/android/jack/ExitStatus.java b/jack/src/com/android/jack/ExitStatus.java
index 8293ed4..3fb67a0 100644
--- a/jack/src/com/android/jack/ExitStatus.java
+++ b/jack/src/com/android/jack/ExitStatus.java
@@ -44,4 +44,8 @@
    * Virtual machine error.
    */
   public static final int FAILURE_VM = 5;
+  /**
+   * Unrecoverable exception.
+   */
+  public static final int FAILURE_UNRECOVERABLE = 6;
 }
diff --git a/jack/src/com/android/jack/Jack.java b/jack/src/com/android/jack/Jack.java
index 8cf25f5..ca07644 100644
--- a/jack/src/com/android/jack/Jack.java
+++ b/jack/src/com/android/jack/Jack.java
@@ -60,7 +60,7 @@
 import com.android.jack.ir.ast.JField;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.formatter.InternalFormatter;
@@ -185,9 +185,6 @@
 import com.android.jack.transformations.uselessif.UselessIfChecker;
 import com.android.jack.transformations.uselessif.UselessIfRemover;
 import com.android.jack.util.collect.UnmodifiableCollections;
-import com.android.jack.vfs.VDir;
-import com.android.jack.vfs.direct.DirectDir;
-import com.android.jack.vfs.zip.ZipArchive;
 import com.android.sched.scheduler.FeatureSet;
 import com.android.sched.scheduler.IllegalRequestException;
 import com.android.sched.scheduler.Plan;
@@ -204,6 +201,7 @@
 import com.android.sched.util.config.ConfigPrinterFactory;
 import com.android.sched.util.config.ConfigurationException;
 import com.android.sched.util.config.HasKeyId;
+import com.android.sched.util.config.ReflectFactory;
 import com.android.sched.util.config.ThreadConfig;
 import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.ReflectFactoryPropertyId;
@@ -211,12 +209,16 @@
 import com.android.sched.util.log.LoggerFactory;
 import com.android.sched.util.log.Tracer;
 import com.android.sched.util.log.TracerFactory;
+import com.android.sched.vfs.InputVDir;
+import com.android.sched.vfs.direct.InputDirectDir;
+import com.android.sched.vfs.zip.InputZipArchive;
 
 import org.antlr.runtime.RecognitionException;
 
 import java.io.File;
 import java.io.IOException;
 import java.io.InputStream;
+import java.util.ArrayList;
 import java.util.List;
 import java.util.Properties;
 import java.util.logging.Level;
@@ -243,8 +245,8 @@
       UserFriendlyFormatter.getFormatter();
 
   @Nonnull
-  public static final ObjectId<JProgram> PROGRAM =
-      new ObjectId<JProgram>("jack.program", JProgram.class);
+  public static final ObjectId<JSession> SESSION =
+      new ObjectId<JSession>("jack.session", JSession.class);
 
 
   // Compilation configuration kept in a static field to avoid ThreadConfig overhead
@@ -258,7 +260,7 @@
           "jack.internal.jayce.loader.classpath.policy",
           "Hint on default load policy for classpath entries",
           JaycePackageLoader.class)
-          .addArgType(VDir.class).addArgType(JPhantomLookup.class).bypassAccessibility()
+          .addArgType(InputVDir.class).addArgType(JPhantomLookup.class).bypassAccessibility()
           .addDefaultValue("structure");
 
   @Nonnull
@@ -267,12 +269,12 @@
           "jack.internal.jayce.loader.import.policy",
           "Hint on default load policy for import entries",
           JaycePackageLoader.class)
-          .addArgType(VDir.class).addArgType(JPhantomLookup.class).bypassAccessibility()
+          .addArgType(InputVDir.class).addArgType(JPhantomLookup.class).bypassAccessibility()
           .addDefaultValue("full");
 
   @Nonnull
-  public static JProgram getProgram() {
-    return ThreadConfig.get(Jack.PROGRAM);
+  public static JSession getSession() {
+    return ThreadConfig.get(Jack.SESSION);
   }
 
   @Nonnull
@@ -334,7 +336,7 @@
         logger.log(Level.INFO, "Jack sanity checks {0}",
             (options.hasSanityChecks() ? "enabled" : "disabled"));
 
-        JProgram program = buildProgram(options, hooks);
+        JSession session = buildSession(options, hooks);
         Request request = createInitialRequest();
 
         JavaVersion sourceVersion = config.get(Options.JAVA_SOURCE_VERSION);
@@ -405,9 +407,9 @@
 
         ProductionSet targetProduction = request.getTargetProductions();
         FeatureSet features = request.getFeatures();
-        PlanBuilder<JProgram> planBuilder;
+        PlanBuilder<JSession> planBuilder;
         try {
-          planBuilder = request.getPlanBuilder(JProgram.class);
+          planBuilder = request.getPlanBuilder(JSession.class);
         } catch (IllegalRequestException e) {
           throw new AssertionError(e);
         }
@@ -444,11 +446,11 @@
           }
         }
 
-        Plan<JProgram> plan;
+        Plan<JSession> plan;
         try {
           // Try to build an automatic plan ...
           try {
-            plan = request.buildPlan(JProgram.class);
+            plan = request.buildPlan(JSession.class);
           } catch (PlanNotFoundException e) {
             throw new AssertionError(e);
           } catch (IllegalRequestException e) {
@@ -466,7 +468,7 @@
 
         PlanPrinterFactory.getPlanPrinter().printPlan(plan);
         try {
-          plan.getScheduleInstance().process(program);
+          plan.getScheduleInstance().process(session);
         } catch (Exception e) {
           throw new AssertionError(e);
         }
@@ -507,26 +509,22 @@
   }
 
   @Nonnull
-  static JProgram buildProgram(@Nonnull Options options, @Nonnull RunnableHooks hooks)
+  static JSession buildSession(@Nonnull Options options, @Nonnull RunnableHooks hooks)
       throws JackIOException {
 
     Tracer tracer = TracerFactory.getTracer();
 
     List<String> ecjArguments = options.ecjArguments;
 
-    JProgram program =  getProgram();
+    JSession session =  getSession();
 
-    ComposedPackageLoader rootPackageLoader = program.getTopLevelLoader();
+    ComposedPackageLoader rootPackageLoader = session.getTopLevelLoader();
 
-    JPhantomLookup phantomLookup = program.getPhantomLookup();
-    putInJackClasspath(options.jayceImport, rootPackageLoader, phantomLookup, hooks,
-        IMPORT_POLICY);
-    putInJackClasspath(options.getBootclasspath(), rootPackageLoader, phantomLookup, hooks,
-        CLASSPATH_POLICY);
-    putInJackClasspath(options.getClasspath(), rootPackageLoader, phantomLookup, hooks,
-        CLASSPATH_POLICY);
-
-    JayceFileImporter jayceImporter = new JayceFileImporter(options.jayceImport);
+    JPhantomLookup phantomLookup = session.getPhantomLookup();
+    JayceFileImporter jayceImporter =
+        getJayceFileImporter(options.jayceImport, rootPackageLoader, phantomLookup, hooks);
+    putInJackClasspath(options.getBootclasspath(), rootPackageLoader, phantomLookup, hooks);
+    putInJackClasspath(options.getClasspath(), rootPackageLoader, phantomLookup, hooks);
 
     if (ecjArguments != null) {
       String bootclasspathOption = "-bootclasspath";
@@ -543,7 +541,7 @@
         ecjArguments.add(JackBatchCompiler.JACK_LOGICAL_PATH_ENTRY);
       }
 
-      JackBatchCompiler jbc = new JackBatchCompiler(program, jayceImporter);
+      JackBatchCompiler jbc = new JackBatchCompiler(session, jayceImporter);
 
       Event event = tracer.start(JackEventType.ECJ_COMPILATION);
 
@@ -556,18 +554,18 @@
       }
     }
 
-    jayceImporter.doImport(program);
+    jayceImporter.doImport(session);
 
     Event eventIdMerger = tracer.start(JackEventType.METHOD_ID_MERGER);
 
     try {
       JClass javaLangObject = phantomLookup.getClass(CommonTypes.JAVA_LANG_OBJECT);
       MethodIdMerger merger = new MethodIdMerger(javaLangObject);
-      for (JType type : program.getTypesToEmit()) {
+      for (JType type : session.getTypesToEmit()) {
         merger.accept(type);
       }
       JVisitor remover = new VirtualMethodsMarker.Remover(javaLangObject);
-      for (JType type : program.getTypesToEmit()) {
+      for (JType type : session.getTypesToEmit()) {
         remover.accept(type);
       }
     } finally {
@@ -575,106 +573,135 @@
     }
 
     MethodIdDuplicateRemover methodIdDupRemover = new MethodIdDuplicateRemover();
-    methodIdDupRemover.accept(program);
+    methodIdDupRemover.accept(session);
 
-    return program;
+    return session;
+  }
+
+  @Nonnull
+  private static JayceFileImporter getJayceFileImporter(@Nonnull List<File> jayceImport,
+      @Nonnull ComposedPackageLoader rootPackageLoader, @Nonnull JPhantomLookup phantomLookup,
+      @Nonnull RunnableHooks hooks) {
+    List<InputVDir> jackFilesToImport = new ArrayList<InputVDir>(jayceImport.size());
+    ReflectFactory<JaycePackageLoader> factory = ThreadConfig.get(IMPORT_POLICY);
+    for (final File jackFile : jayceImport) {
+      try {
+        InputVDir vDir = wrapAsVDir(jackFile, hooks);
+        jackFilesToImport.add(vDir);
+        // add to classpath
+        JaycePackageLoader rootPLoader = factory.create(vDir, phantomLookup);
+        rootPackageLoader.appendLoader(rootPLoader);
+      } catch (IOException ioException) {
+        throw new JackFileException("Error importing jack container: " + jackFile.getAbsolutePath(),
+            ioException);
+      }
+    }
+    return new JayceFileImporter(jackFilesToImport);
   }
 
   private static void putInJackClasspath(@Nonnull List<File> jackFiles,
       @Nonnull ComposedPackageLoader rootPackageLoader,
       @Nonnull JPhantomLookup phantomJNodeLookup,
-      @Nonnull RunnableHooks hooks,
-      @Nonnull ReflectFactoryPropertyId<JaycePackageLoader> loadPolicy)
-      throws JackIOException {
+      @Nonnull RunnableHooks hooks) {
+    ReflectFactory<JaycePackageLoader> factory = ThreadConfig.get(CLASSPATH_POLICY);
     for (final File jackFile : jackFiles) {
       try {
-        VDir dir;
-        if (jackFile.isDirectory()) {
-          dir = new DirectDir(jackFile);
-        } else { // zip
-          final ZipArchive zipArchive = new ZipArchive(jackFile);
-          dir = zipArchive;
-          hooks.addHook(new Runnable() {
-            @Override
-            public void run() {
-              try {
-                zipArchive.close();
-              } catch (IOException e) {
-                logger.log(Level.FINE, "Failed to close zip for '" + jackFile + "'.", e);
-              }
-            }
-          });
-        }
-        JaycePackageLoader rootPLoader =
-            ThreadConfig.get(loadPolicy).create(dir, phantomJNodeLookup);
+        InputVDir vDir = wrapAsVDir(jackFile, hooks);
+        JaycePackageLoader rootPLoader = factory.create(vDir, phantomJNodeLookup);
         rootPackageLoader.appendLoader(rootPLoader);
       } catch (IOException ioException) {
         // Ignore bad entry
-        logger.log(Level.WARNING, "Ignore bad entry into classpath: {0}",
+        logger.log(Level.WARNING, "Bad classpath entry ignored: {0}",
             jackFile.getAbsolutePath());
       }
     }
   }
 
+  @Nonnull
+  private static InputVDir wrapAsVDir(@Nonnull final File dirOrZip,
+      @Nonnull RunnableHooks hooks) throws IOException {
+    InputVDir dir;
+    if (dirOrZip.isDirectory()) {
+      dir = new InputDirectDir(dirOrZip);
+    } else { // zip
+      final InputZipArchive zipArchive = new InputZipArchive(dirOrZip);
+      dir = zipArchive;
+      hooks.addHook(new Runnable() {
+        @Override
+        public void run() {
+          try {
+            zipArchive.close();
+          } catch (IOException e) {
+            logger.log(Level.FINE, "Failed to close zip for '" + dirOrZip + "'.", e);
+          }
+        }
+      });
+    }
+    return dir;
+  }
+
   private static void fillJayceToJaycePlan(
-      @Nonnull Options options, @Nonnull PlanBuilder<JProgram> programPlan) {
+      @Nonnull Options options, @Nonnull PlanBuilder<JSession> planBuilder) {
     // Add here transformations we want to apply before writing .jack file
-    FeatureSet features = programPlan.getRequest().getFeatures();
-    ProductionSet productions = programPlan.getRequest().getTargetProductions();
+    FeatureSet features = planBuilder.getRequest().getFeatures();
+    ProductionSet productions = planBuilder.getRequest().getTargetProductions();
 
     if (features.contains(SanityChecks.class)) {
-      programPlan.append(TypeDuplicateRemoverChecker.class);
+      planBuilder.append(TypeDuplicateRemoverChecker.class);
     }
 
     // JarJar
     if (features.contains(Jarjar.class)) {
-      programPlan.append(PackageRenamer.class);
+      planBuilder.append(PackageRenamer.class);
     }
 
     // Shrob
-    appendStringRefiningPlan(programPlan);
+    if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
+      appendStringRefiningPlan(planBuilder);
+    }
+
     if (productions.contains(SeedFile.class)) {
-      programPlan.append(SeedPrinter.class);
+      planBuilder.append(SeedPrinter.class);
     }
     if (features.contains(Shrinking.class)) {
-      appendShrinkingPlan(programPlan);
+      appendShrinkingPlan(planBuilder);
     }
     if (features.contains(Obfuscation.class)) {
-      appendObfuscationPlan(programPlan);
+      appendObfuscationPlan(planBuilder);
     }
     if (productions.contains(Mapping.class)) {
-      programPlan.append(MappingPrinter.class);
+      planBuilder.append(MappingPrinter.class);
     }
     if (productions.contains(TypeAndMemberListing.class)) {
-      programPlan.append(TypeAndMemberLister.class);
+      planBuilder.append(TypeAndMemberLister.class);
     }
     if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
-      appendShrobMarkerRemoverPlan(programPlan);
+      appendShrobMarkerRemoverPlan(planBuilder);
     }
   }
 
-  static void fillDexPlan(@Nonnull Options options, @Nonnull PlanBuilder<JProgram> programPlan) {
-    FeatureSet features = programPlan.getRequest().getFeatures();
-    ProductionSet productions = programPlan.getRequest().getTargetProductions();
+  static void fillDexPlan(@Nonnull Options options, @Nonnull PlanBuilder<JSession> planBuilder) {
+    FeatureSet features = planBuilder.getRequest().getFeatures();
+    ProductionSet productions = planBuilder.getRequest().getTargetProductions();
     boolean hasSanityChecks = features.contains(SanityChecks.class);
 
     // Build the plan
     if (hasSanityChecks) {
-      programPlan.append(TypeDuplicateRemoverChecker.class);
+      planBuilder.append(TypeDuplicateRemoverChecker.class);
     }
 
     if (features.contains(Jarjar.class)) {
-      programPlan.append(PackageRenamer.class);
+      planBuilder.append(PackageRenamer.class);
     }
 
     if (hasSanityChecks) {
-      programPlan.append(ParentSetterChecker.class);
+      planBuilder.append(ParentSetterChecker.class);
     }
-    programPlan.append(DexFileBuilder.class);
+    planBuilder.append(DexFileBuilder.class);
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
         if (features.contains(LineDebugInfo.class)) {
@@ -690,21 +717,24 @@
       }
     }
 
-    appendStringRefiningPlan(programPlan);
+    if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
+      appendStringRefiningPlan(planBuilder);
+    }
+
     if (productions.contains(SeedFile.class)) {
-      programPlan.append(SeedPrinter.class);
+      planBuilder.append(SeedPrinter.class);
     }
     if (features.contains(Shrinking.class)) {
-      appendShrinkingPlan(programPlan);
+      appendShrinkingPlan(planBuilder);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(UsedEnumFieldCollector.class);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan2 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         if (features.contains(DxLegacy.class)) {
           typePlan2.append(VisibilityBridgeAdder.class);
@@ -715,10 +745,10 @@
         methodPlan.append(AssertionTransformer.class);
       }
     }
-    programPlan.append(AssertionTransformerSchedulingSeparator.class);
+    planBuilder.append(AssertionTransformerSchedulingSeparator.class);
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan3 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
 
       {
         {
@@ -746,18 +776,18 @@
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
       methodPlan.append(SwitchEnumSupport.class);
     }
 
-    programPlan.append(InnerAccessorSchedulingSeparator.class);
-    programPlan.append(TryStatementSchedulingSeparator.class);
-    programPlan.append(EnumMappingSchedulingSeparator.class);
+    planBuilder.append(InnerAccessorSchedulingSeparator.class);
+    planBuilder.append(TryStatementSchedulingSeparator.class);
+    planBuilder.append(EnumMappingSchedulingSeparator.class);
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan4 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan4.append(InnerAccessorAdder.class);
       typePlan4.append(UsedEnumFieldMarkerRemover.class);
       {
@@ -786,12 +816,12 @@
     }
 
     if (features.contains(JackFileZipOutput.class)) {
-      programPlan.append(JayceZipWriter.class);
+      planBuilder.append(JayceZipWriter.class);
     }
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan4 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
 
       {
         SubPlanBuilder<JMethod> methodPlan = typePlan4.appendSubPlan(JMethodAdaptor.class);
@@ -830,24 +860,24 @@
       }
     }
     if (features.contains(Obfuscation.class)) {
-      appendObfuscationPlan(programPlan);
+      appendObfuscationPlan(planBuilder);
     }
     if (productions.contains(Mapping.class)) {
-      programPlan.append(MappingPrinter.class);
+      planBuilder.append(MappingPrinter.class);
     }
     if (productions.contains(TypeAndMemberListing.class)) {
-      programPlan.append(TypeAndMemberLister.class);
+      planBuilder.append(TypeAndMemberLister.class);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(ClassDefItemBuilder.class);
       typePlan.append(ClassAnnotationBuilder.class);
     }
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan5 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         SubPlanBuilder<JMethod> methodPlan4 =
             typePlan5.appendSubPlan(JMethodAdaptor.class);
@@ -897,49 +927,52 @@
     }
 
     if (hasSanityChecks) {
-      programPlan.append(ParentSetterChecker.class);
+      planBuilder.append(ParentSetterChecker.class);
       {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(DeclaredTypePackageChecker.class);
       }
       {
-        SubPlanBuilder<JPackage> packagePlan = programPlan.appendSubPlan(JPackageAdapter.class);
+        SubPlanBuilder<JPackage> packagePlan = planBuilder.appendSubPlan(JPackageAdapter.class);
         packagePlan.append(PackageChecker.class);
       }
     }
   }
 
   private static void fillJavaToJaycePlan(
-      @Nonnull Options options, @Nonnull PlanBuilder<JProgram> programPlan) {
-    Request request = programPlan.getRequest();
+      @Nonnull Options options, @Nonnull PlanBuilder<JSession> planBuilder) {
+    Request request = planBuilder.getRequest();
     FeatureSet features = request.getFeatures();
     ProductionSet productions = request.getTargetProductions();
     boolean hasSanityChecks = features.contains(SanityChecks.class);
 
     // Build the plan
     if (hasSanityChecks) {
-      programPlan.append(TypeDuplicateRemoverChecker.class);
+      planBuilder.append(TypeDuplicateRemoverChecker.class);
     }
 
     if (features.contains(Jarjar.class)) {
-      programPlan.append(PackageRenamer.class);
+      planBuilder.append(PackageRenamer.class);
     }
 
-    appendStringRefiningPlan(programPlan);
+    if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
+      appendStringRefiningPlan(planBuilder);
+    }
+
     if (productions.contains(SeedFile.class)) {
-      programPlan.append(SeedPrinter.class);
+      planBuilder.append(SeedPrinter.class);
     }
     if (features.contains(Shrinking.class)) {
-      appendShrinkingPlan(programPlan);
+      appendShrinkingPlan(planBuilder);
     }
 
     if (hasSanityChecks) {
-      programPlan.append(ParentSetterChecker.class);
+      planBuilder.append(ParentSetterChecker.class);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan7 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan7.append(UsedEnumFieldCollector.class);
 
       {
@@ -957,7 +990,7 @@
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan2 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       if (features.contains(DxLegacy.class)) {
         typePlan2.append(VisibilityBridgeAdder.class);
       }
@@ -971,10 +1004,10 @@
         }
       }
     }
-    programPlan.append(AssertionTransformerSchedulingSeparator.class);
+    planBuilder.append(AssertionTransformerSchedulingSeparator.class);
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan3 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         {
           SubPlanBuilder<JField> fieldPlan =
@@ -999,17 +1032,17 @@
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
       methodPlan.append(SwitchEnumSupport.class);
     }
 
-    programPlan.append(InnerAccessorSchedulingSeparator.class);
-    programPlan.append(EnumMappingSchedulingSeparator.class);
+    planBuilder.append(InnerAccessorSchedulingSeparator.class);
+    planBuilder.append(EnumMappingSchedulingSeparator.class);
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan4 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan4.append(InnerAccessorAdder.class);
       typePlan4.append(UsedEnumFieldMarkerRemover.class);
       {
@@ -1027,29 +1060,29 @@
       }
       typePlan4.append(FieldInitMethodRemover.class);
     }
-    programPlan.append(TryStatementSchedulingSeparator.class);
+    planBuilder.append(TryStatementSchedulingSeparator.class);
 
     if (hasSanityChecks) {
-      programPlan.append(TypeDuplicateRemoverChecker.class);
+      planBuilder.append(TypeDuplicateRemoverChecker.class);
     }
     if (features.contains(Obfuscation.class)) {
-      appendObfuscationPlan(programPlan);
+      appendObfuscationPlan(planBuilder);
     }
     if (productions.contains(Mapping.class)) {
-      programPlan.append(MappingPrinter.class);
+      planBuilder.append(MappingPrinter.class);
     }
     if (productions.contains(TypeAndMemberListing.class)) {
-      programPlan.append(TypeAndMemberLister.class);
+      planBuilder.append(TypeAndMemberLister.class);
     }
     if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
-      appendShrobMarkerRemoverPlan(programPlan);
+      appendShrobMarkerRemoverPlan(planBuilder);
     }
   }
 
-  private static void appendStringRefiningPlan(@Nonnull PlanBuilder<JProgram> programPlan) {
+  private static void appendStringRefiningPlan(@Nonnull PlanBuilder<JSession> planBuilder) {
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(TypeGenericSignatureSplitter.class);
       typePlan.append(TypeStringLiteralRefiner.class);
       {
@@ -1068,10 +1101,10 @@
     }
   }
 
-  private static void appendShrobMarkerRemoverPlan(@Nonnull PlanBuilder<JProgram> programPlan) {
+  private static void appendShrobMarkerRemoverPlan(@Nonnull PlanBuilder<JSession> planBuilder) {
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan4 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan4.append(TypeShrinkMarkerRemover.class);
       typePlan4.append(TypeKeepNameMarkerRemover.class);
       typePlan4.append(TypeOriginalNameMarkerRemover.class);
@@ -1088,20 +1121,20 @@
     }
   }
 
-  private static void appendShrinkingPlan(@Nonnull PlanBuilder<JProgram> programPlan) {
+  private static void appendShrinkingPlan(@Nonnull PlanBuilder<JSession> planBuilder) {
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(ExtendingOrImplementingClassFinder.class);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(Keeper.class);
     }
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(TypeShrinker.class);
       {
         SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
@@ -1114,16 +1147,16 @@
     }
   }
 
-  private static void appendObfuscationPlan(@Nonnull PlanBuilder<JProgram> programPlan) {
+  private static void appendObfuscationPlan(@Nonnull PlanBuilder<JSession> planBuilder) {
     {
       SubPlanBuilder<JPackage> packagePlan =
-          programPlan.appendSubPlan(JPackageAdapter.class);
+          planBuilder.appendSubPlan(JPackageAdapter.class);
       packagePlan.append(NameKeeper.class);
     }
-    programPlan.append(Renamer.class);
+    planBuilder.append(Renamer.class);
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(TypeAnnotationRemover.class);
       {
         SubPlanBuilder<JField> fieldPlan = typePlan.appendSubPlan(JFieldAdaptor.class);
@@ -1138,43 +1171,46 @@
   }
 
   private static void fillJayceToDexPlan(
-      @Nonnull Options options, @Nonnull PlanBuilder<JProgram> programPlan) {
-    Request request = programPlan.getRequest();
+      @Nonnull Options options, @Nonnull PlanBuilder<JSession> planBuilder) {
+    Request request = planBuilder.getRequest();
     FeatureSet features = request.getFeatures();
     ProductionSet productions = request.getTargetProductions();
     boolean hasSanityChecks = features.contains(SanityChecks.class);
 
     // Build the plan
     if (hasSanityChecks) {
-      programPlan.append(TypeDuplicateRemoverChecker.class);
+      planBuilder.append(TypeDuplicateRemoverChecker.class);
     }
 
     if (features.contains(Jarjar.class)) {
-      programPlan.append(PackageRenamer.class);
+      planBuilder.append(PackageRenamer.class);
     }
 
-    appendStringRefiningPlan(programPlan);
+    if (features.contains(Shrinking.class) || features.contains(Obfuscation.class)) {
+      appendStringRefiningPlan(planBuilder);
+    }
+
     if (productions.contains(SeedFile.class)) {
-      programPlan.append(SeedPrinter.class);
+      planBuilder.append(SeedPrinter.class);
     }
     if (features.contains(Shrinking.class)) {
-      appendShrinkingPlan(programPlan);
+      appendShrinkingPlan(planBuilder);
     }
 
     if (hasSanityChecks) {
-      programPlan.append(ParentSetterChecker.class);
+      planBuilder.append(ParentSetterChecker.class);
     }
-    programPlan.append(DexFileBuilder.class);
+    planBuilder.append(DexFileBuilder.class);
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan.append(ReflectAnnotationsAdder.class);
     }
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan3 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         {
           SubPlanBuilder<JMethod> methodPlan2 =
@@ -1191,7 +1227,7 @@
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan4 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       typePlan4.append(ClassDefItemBuilder.class);
       typePlan4.append(ClassAnnotationBuilder.class);
       {
@@ -1231,18 +1267,18 @@
     }
 
     if (features.contains(Obfuscation.class)) {
-      appendObfuscationPlan(programPlan);
+      appendObfuscationPlan(planBuilder);
     }
     if (productions.contains(Mapping.class)) {
-      programPlan.append(MappingPrinter.class);
+      planBuilder.append(MappingPrinter.class);
     }
     if (productions.contains(TypeAndMemberListing.class)) {
-      programPlan.append(TypeAndMemberLister.class);
+      planBuilder.append(TypeAndMemberLister.class);
     }
 
     {
       SubPlanBuilder<JDefinedClassOrInterface> typePlan5 =
-          programPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+          planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
       {
         SubPlanBuilder<JMethod> methodPlan4 =
             typePlan5.appendSubPlan(JMethodAdaptor.class);
@@ -1292,7 +1328,7 @@
     }
 
     if (hasSanityChecks) {
-      programPlan.append(ParentSetterChecker.class);
+      planBuilder.append(ParentSetterChecker.class);
     }
   }
 
diff --git a/jack/src/com/android/jack/JackEventType.java b/jack/src/com/android/jack/JackEventType.java
index c447058..50227d5 100644
--- a/jack/src/com/android/jack/JackEventType.java
+++ b/jack/src/com/android/jack/JackEventType.java
@@ -25,37 +25,28 @@
  */
 public enum JackEventType implements EventType {
 
-  NNODE_READING_FOR_IMPORT("NNode reading for import", "Blue"),
-  NNODE_READING_FOR_CLASSPATH("NNode reading for classpath", "Teal"),
-  NNODE_TO_JNODE_CONVERSION_FOR_IMPORT("NNode to JNode conversion for import", "Purple"),
-  NNODE_TO_JNODE_CONVERSION_FOR_CLASSPATH("NNode to JNode conversion for classpath", "Green"),
-  JNODE_TO_NNODE_CONVERSION("JNode to NNode conversion", "Red"),
-  NNODE_WRITING("NNode writing", "Orange"),
-  LOOKUP_TRANSFER("Lookup transfer", "Yellow"),
-  METHOD_ID_MERGER("Method id merger", "Beige"),
-  PRELOOKUP("Pre-lookup", "Pink"),
-  ECJ_COMPILATION("ECJ compilation", "Black"),
-  GWT_AST_BUILDER("GwtAstBuilder", "LightSkyBlue"),
-  J_AST_BUILDER("JAstBuilder", "LightSeaGreen"),
-  DX_OPTIMIZATION("Dx optimizations on RopMethod", "Brown"),
-  REMOVE_DEAD_CODE("Remove dead code", "Chocolate"),
-  DOP_CREATION("Dop creation", "Cyan"),
-  JACK_RUN("Jack run", "BlueBerry");
+  NNODE_READING_FOR_IMPORT("NNode reading for import"),
+  NNODE_READING_FOR_CLASSPATH("NNode reading for classpath"),
+  NNODE_TO_JNODE_CONVERSION_FOR_IMPORT("NNode to JNode conversion for import"),
+  NNODE_TO_JNODE_CONVERSION_FOR_CLASSPATH("NNode to JNode conversion for classpath"),
+  JNODE_TO_NNODE_CONVERSION("JNode to NNode conversion"),
+  NNODE_WRITING("NNode writing"),
+  LOOKUP_TRANSFER("Lookup transfer"),
+  METHOD_ID_MERGER("Method id merger"),
+  PRELOOKUP("Pre-lookup"),
+  ECJ_COMPILATION("ECJ compilation"),
+  GWT_AST_BUILDER("GwtAstBuilder"),
+  J_AST_BUILDER("JAstBuilder"),
+  DX_OPTIMIZATION("Dx optimizations on RopMethod"),
+  REMOVE_DEAD_CODE("Remove dead code"),
+  DOP_CREATION("Dop creation"),
+  JACK_RUN("Jack run");
 
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
-  JackEventType(@Nonnull String name, @Nonnull String cssColor) {
+  JackEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/Options.java b/jack/src/com/android/jack/Options.java
index f974515..448656f 100644
--- a/jack/src/com/android/jack/Options.java
+++ b/jack/src/com/android/jack/Options.java
@@ -45,6 +45,7 @@
 import com.android.sched.util.config.StringLocation;
 import com.android.sched.util.config.id.BooleanPropertyId;
 import com.android.sched.util.config.id.EnumPropertyId;
+import com.android.sched.util.config.id.ImplementationPropertyId;
 import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.PropertyId;
 import com.android.sched.util.file.Directory;
@@ -99,11 +100,11 @@
 
   @Nonnull
   public static final BooleanPropertyId GENERATE_DEX_FILE = BooleanPropertyId.create(
-      "jack.dex.generate", "Generate dex file").addDefaultValue("false");
+      "jack.dex.generate", "Generate dex file").addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final BooleanPropertyId GENERATE_JACK_FILE = BooleanPropertyId.create(
-      "jack.jackfile.generate", "Generate jack files").addDefaultValue("false");
+      "jack.jackfile.generate", "Generate jack files").addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final EnumPropertyId<Container> DEX_OUTPUT_CONTAINER_TYPE = EnumPropertyId.create(
@@ -215,7 +216,7 @@
   @Nonnull
   public static final BooleanPropertyId SANITY_CHECKS = BooleanPropertyId.create(
       "jack.sanitychecks", "enable/disable compiler sanity checks")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Option(name = "--tracer-dir", usage = "enable tracer and output into this dir (.html)",
       metaVar = "DIRECTORY")
@@ -244,24 +245,24 @@
   @Nonnull
   public static final BooleanPropertyId EMIT_LOCAL_DEBUG_INFO = BooleanPropertyId.create(
       "jack.dex.debug.vars", "Emit local variable debug info into generated dex")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_JACK_FLAG = BooleanPropertyId.create(
       "jack.internal.jackflag", "Emit jack flag into generated dex")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   protected boolean emitSyntheticDebugInfo = false;
 
   @Nonnull
   public static final BooleanPropertyId EMIT_LINE_NUMBER_DEBUG_INFO = BooleanPropertyId.create(
       "jack.dex.debug.lines", "Emit line number debug info into generated dex")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_SOURCE_FILE_DEBUG_INFO = BooleanPropertyId.create(
       "jack.dex.debug.source", "Emit source file debug info into generated dex")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   protected boolean keepMethodBody = false;
 
@@ -275,7 +276,7 @@
   @Nonnull
   public static final BooleanPropertyId USE_MIXED_CASE_CLASSNAME = BooleanPropertyId.create(
       "jack.obfuscation.mixedcaseclassname",
-      "Use mixed case class name when obfuscating").addDefaultValue("false");
+      "Use mixed case class name when obfuscating").addDefaultValue(Boolean.FALSE);
 
   protected File typeAndMemberListing;
 
@@ -285,10 +286,12 @@
   @Nonnull
   protected Filter<JMethod> filter = new AllMethods();
 
-  @SuppressWarnings({"unchecked", "rawtypes"})
+  @SuppressWarnings("unchecked")
   @Nonnull
-  public static final ObjectId<Filter<JMethod>> METHOD_FILTER =
-      new ObjectId("jack.methodfilter", Filter.class);
+  public static final ImplementationPropertyId<Filter<JMethod>> METHOD_FILTER =
+      (ImplementationPropertyId<Filter<JMethod>>) (Object) ImplementationPropertyId.create(
+          "jack.internal.filter.method", "Define which filter will be used for methods",
+          Filter.class).addDefaultValue("all-methods");
 
   //
   // Getter
@@ -426,158 +429,158 @@
     }
 
     for (Entry<String, String> entry : properties.entrySet()) {
-      configBuilder.set(entry.getKey(), entry.getValue(), new StringLocation("-D option"));
+      configBuilder.setString(entry.getKey(), entry.getValue(), new StringLocation("-D option"));
     }
 
     configBuilder.pushDefaultLocation(new StringLocation("Options"));
 
     if (jarjarRulesFile != null) {
-      configBuilder.set(PackageRenamer.JARJAR_FILE, jarjarRulesFile.getAbsolutePath());
+      configBuilder.set(PackageRenamer.JARJAR_FILE, jarjarRulesFile);
     }
 
     configBuilder.pushDefaultLocation(new StringLocation("proguard flags"));
 
     if (flags != null) {
       configBuilder.set(ReflectAnnotationsAdder.EMIT_ANNOTATION_SIG,
-          Boolean.toString(flags.keepAttribute("Signatures")));
+          flags.keepAttribute("Signatures"));
       configBuilder.set(ReflectAnnotationsAdder.EMIT_ANNOTATION_THROWS,
-          Boolean.toString(flags.keepAttribute("Exceptions")));
+          flags.keepAttribute("Exceptions"));
       configBuilder.set(ReflectAnnotationsAdder.EMIT_ANNOTATION_MEMBER_CLASSES,
-          Boolean.toString(flags.keepAttribute("InnerClasses")));
+          flags.keepAttribute("InnerClasses"));
       configBuilder.set(ReflectAnnotationsAdder.EMIT_ANNOTATION_ENCLOSING_METHOD,
-          Boolean.toString(flags.keepAttribute("EnclosingMethod")));
+          flags.keepAttribute("EnclosingMethod"));
       configBuilder.set(DefaultValueAnnotationAdder.EMIT_ANNOTATION_DEFAULT,
-          Boolean.toString(flags.keepAttribute("AnnotationDefault")));
+          flags.keepAttribute("AnnotationDefault"));
       configBuilder.set(AnnotationRemover.EMIT_RUNTIME_INVISIBLE_ANNOTATION,
-          Boolean.toString(flags.keepAttribute("RuntimeInvisibleAnnotations")));
+          flags.keepAttribute("RuntimeInvisibleAnnotations"));
       configBuilder.set(AnnotationRemover.EMIT_RUNTIME_VISIBLE_ANNOTATION,
-          Boolean.toString(flags.keepAttribute("RuntimeVisibleAnnotations")));
+          flags.keepAttribute("RuntimeVisibleAnnotations"));
       configBuilder.set(ParameterAnnotationRemover.EMIT_RUNTIME_VISIBLE_PARAMETER_ANNOTATION,
-          Boolean.toString(flags.keepAttribute("RuntimeVisibleParameterAnnotations")));
+          flags.keepAttribute("RuntimeVisibleParameterAnnotations"));
       configBuilder.set(ParameterAnnotationRemover.EMIT_RUNTIME_INVISIBLE_PARAMETER_ANNOTATION,
-          Boolean.toString(flags.keepAttribute("RuntimeInvisibleParameterAnnotations")));
+          flags.keepAttribute("RuntimeInvisibleParameterAnnotations"));
       configBuilder.set(EMIT_LINE_NUMBER_DEBUG_INFO,
-          Boolean.toString(flags.keepAttribute("LineNumberTable")));
+          flags.keepAttribute("LineNumberTable"));
       configBuilder.set(Options.FLAGS, flags);
       configBuilder.set(
-          Options.USE_MIXED_CASE_CLASSNAME, String.valueOf(flags.getUseMixedCaseClassName()));
+          Options.USE_MIXED_CASE_CLASSNAME, flags.getUseMixedCaseClassName());
       configBuilder.set(Renamer.USE_UNIQUE_CLASSMEMBERNAMES,
-          String.valueOf(flags.getUseUniqueClassMemberNames()));
+          flags.getUseUniqueClassMemberNames());
 
       File mapping = flags.getObfuscationMapping();
       if (mapping != null) {
-        configBuilder.set(Renamer.USE_MAPPING, "true");
-        configBuilder.set(Renamer.MAPPING_FILE, mapping.getAbsolutePath());
+        configBuilder.set(Renamer.USE_MAPPING, true);
+        configBuilder.setString(Renamer.MAPPING_FILE, mapping.getAbsolutePath());
       } else {
-        configBuilder.set(Renamer.USE_MAPPING, "false");
+        configBuilder.set(Renamer.USE_MAPPING, false);
       }
 
       File seeds = flags.getSeedsFile();
       if (seeds != null) {
-        configBuilder.set(SeedPrinter.SEEDS_OUTPUT_FILE, seeds.getAbsolutePath());
+        configBuilder.setString(SeedPrinter.SEEDS_OUTPUT_FILE, seeds.getAbsolutePath());
       }
 
       File dictionary = flags.getObfuscationDictionary();
       if (dictionary != null) {
-        configBuilder.set(Renamer.USE_OBFUSCATION_DICTIONARY, "true");
-        configBuilder.set(Renamer.OBFUSCATION_DICTIONARY, dictionary.getAbsolutePath());
+        configBuilder.set(Renamer.USE_OBFUSCATION_DICTIONARY, true);
+        configBuilder.setString(Renamer.OBFUSCATION_DICTIONARY, dictionary.getAbsolutePath());
       } else {
-        configBuilder.set(Renamer.USE_OBFUSCATION_DICTIONARY, "false");
+        configBuilder.set(Renamer.USE_OBFUSCATION_DICTIONARY, false);
       }
 
       File classDictionary = flags.getClassObfuscationDictionary();
       if (classDictionary != null) {
-        configBuilder.set(Renamer.USE_CLASS_OBFUSCATION_DICTIONARY, "true");
-        configBuilder.set(Renamer.CLASS_OBFUSCATION_DICTIONARY, classDictionary.getAbsolutePath());
+        configBuilder.set(Renamer.USE_CLASS_OBFUSCATION_DICTIONARY, true);
+        configBuilder.setString(Renamer.CLASS_OBFUSCATION_DICTIONARY,
+            classDictionary.getAbsolutePath());
       } else {
-        configBuilder.set(Renamer.USE_CLASS_OBFUSCATION_DICTIONARY, "false");
+        configBuilder.set(Renamer.USE_CLASS_OBFUSCATION_DICTIONARY, false);
       }
 
       File packageDictionary = flags.getPackageObfuscationDictionary();
       if (packageDictionary != null) {
-        configBuilder.set(Renamer.USE_PACKAGE_OBFUSCATION_DICTIONARY, "true");
-        configBuilder.set(
+        configBuilder.set(Renamer.USE_PACKAGE_OBFUSCATION_DICTIONARY, true);
+        configBuilder.setString(
             Renamer.PACKAGE_OBFUSCATION_DICTIONARY, packageDictionary.getAbsolutePath());
       } else {
-        configBuilder.set(Renamer.USE_PACKAGE_OBFUSCATION_DICTIONARY, "false");
+        configBuilder.set(Renamer.USE_PACKAGE_OBFUSCATION_DICTIONARY, false);
       }
       File outputmapping = flags.getOutputMapping();
       if (outputmapping != null) {
-        configBuilder.set(MappingPrinter.MAPPING_OUTPUT_FILE, outputmapping.getAbsolutePath());
+        configBuilder.setString(MappingPrinter.MAPPING_OUTPUT_FILE,
+            outputmapping.getAbsolutePath());
       }
       if (nameProvider != null) {
-        configBuilder.set(NameProviderFactory.NAMEPROVIDER, nameProvider);
+        configBuilder.setString(NameProviderFactory.NAMEPROVIDER, nameProvider);
       } else {
         if (flags.getUseMixedCaseClassName()) {
-          configBuilder.set(NameProviderFactory.NAMEPROVIDER, "mixed-case");
+          configBuilder.setString(NameProviderFactory.NAMEPROVIDER, "mixed-case");
         }
       }
 
       String packageForRenamedClasses = flags.getPackageForRenamedClasses();
       if (packageForRenamedClasses != null) {
-        configBuilder.set(Renamer.REPACKAGE_CLASSES, "true");
+        configBuilder.set(Renamer.REPACKAGE_CLASSES, true);
         configBuilder.set(Renamer.PACKAGE_FOR_RENAMED_CLASSES, packageForRenamedClasses);
         if (flags.getPackageForFlatHierarchy() != null) {
           throw new IllegalOptionsException("Flatten package and repackage classes cannot be used"
               + " simultaneously");
         }
       } else {
-        configBuilder.set(Renamer.REPACKAGE_CLASSES, "false");
+        configBuilder.set(Renamer.REPACKAGE_CLASSES, false);
       }
 
       String packageForRenamedPackages = flags.getPackageForFlatHierarchy();
       if (packageForRenamedPackages != null) {
-        configBuilder.set(Renamer.FLATTEN_PACKAGE, "true");
+        configBuilder.set(Renamer.FLATTEN_PACKAGE, true);
         configBuilder.set(Renamer.PACKAGE_FOR_RENAMED_PACKAGES, packageForRenamedPackages);
       } else {
-        configBuilder.set(Renamer.FLATTEN_PACKAGE, "false");
+        configBuilder.set(Renamer.FLATTEN_PACKAGE, false);
       }
     }
 
     configBuilder.popDefaultLocation();
 
-    configBuilder.set(EMIT_LOCAL_DEBUG_INFO, Boolean.toString(emitLocalDebugInfo));
+    configBuilder.set(EMIT_LOCAL_DEBUG_INFO, emitLocalDebugInfo);
     configBuilder.set(
-        CodeItemBuilder.EMIT_SYNTHETIC_LOCAL_DEBUG_INFO, Boolean.toString(emitSyntheticDebugInfo));
+        CodeItemBuilder.EMIT_SYNTHETIC_LOCAL_DEBUG_INFO, emitSyntheticDebugInfo);
 
     if (typeAndMemberListing != null) {
-      configBuilder.set(TypeAndMemberLister.TYPE_AND_MEMBER_LISTING, "true");
-      configBuilder.set(
+      configBuilder.set(TypeAndMemberLister.TYPE_AND_MEMBER_LISTING, true);
+      configBuilder.setString(
           TypeAndMemberLister.TYPE_AND_MEMBER_LISTING_FILE, typeAndMemberListing.getAbsolutePath());
     }
 
     if (jayceOutZip != null) {
-      configBuilder.set(JACK_FILE_OUTPUT_ZIP, jayceOutZip.getAbsolutePath());
-      configBuilder.set(JACK_OUTPUT_CONTAINER_TYPE, Container.ZIP.toString());
-      configBuilder.set(GENERATE_JACK_FILE, "true");
+      configBuilder.setString(JACK_FILE_OUTPUT_ZIP, jayceOutZip.getAbsolutePath());
+      configBuilder.set(JACK_OUTPUT_CONTAINER_TYPE, Container.ZIP);
+      configBuilder.set(GENERATE_JACK_FILE, true);
     } else if (jayceOutDir != null) {
-      configBuilder.set(JACK_FILE_OUTPUT_DIR, jayceOutDir.getAbsolutePath());
-      configBuilder.set(JACK_OUTPUT_CONTAINER_TYPE, Container.DIR.toString());
-      configBuilder.set(GENERATE_JACK_FILE, "true");
+      configBuilder.setString(JACK_FILE_OUTPUT_DIR, jayceOutDir.getAbsolutePath());
+      configBuilder.set(JACK_OUTPUT_CONTAINER_TYPE, Container.DIR);
+      configBuilder.set(GENERATE_JACK_FILE, true);
     } else if (outZip != null) {
-      configBuilder.set(DEX_FILE_OUTPUT, outZip.getAbsolutePath());
-      configBuilder.set(DEX_OUTPUT_CONTAINER_TYPE, Container.ZIP.toString());
-      configBuilder.set(GENERATE_DEX_FILE, "true");
+      configBuilder.setString(DEX_FILE_OUTPUT, outZip.getAbsolutePath());
+      configBuilder.set(DEX_OUTPUT_CONTAINER_TYPE, Container.ZIP);
+      configBuilder.set(GENERATE_DEX_FILE, true);
     } else {
-      configBuilder.set(DEX_FILE_OUTPUT, out.getAbsolutePath());
-      configBuilder.set(DEX_OUTPUT_CONTAINER_TYPE, Container.FILE.toString());
-      configBuilder.set(GENERATE_DEX_FILE, "true");
+      configBuilder.setString(DEX_FILE_OUTPUT, out.getAbsolutePath());
+      configBuilder.set(DEX_OUTPUT_CONTAINER_TYPE, Container.FILE);
+      configBuilder.set(GENERATE_DEX_FILE, true);
     }
-    configBuilder.set(FieldInitializerRemover.CLASS_AS_INITIALVALUE, Boolean.toString(!dxLegacy));
+    configBuilder.set(FieldInitializerRemover.CLASS_AS_INITIALVALUE, !dxLegacy);
     configBuilder.set(
-        FieldInitializerRemover.STRING_AS_INITIALVALUE_OF_OBJECT, Boolean.toString(!runtimeLegacy));
-
-    configBuilder.set(METHOD_FILTER, filter);
+        FieldInitializerRemover.STRING_AS_INITIALVALUE_OF_OBJECT, !runtimeLegacy);
 
     if (tracerDir != null) {
-      configBuilder.set(TracerFactory.TRACER, "html");
-      configBuilder.set(StatsTracerFtl.TRACER_DIR, tracerDir.getAbsolutePath());
+      configBuilder.setString(TracerFactory.TRACER, "html");
+      configBuilder.setString(StatsTracerFtl.TRACER_DIR, tracerDir.getAbsolutePath());
     }
 
-    configBuilder.set(SANITY_CHECKS, Boolean.toString(sanityChecks));
+    configBuilder.set(SANITY_CHECKS, sanityChecks);
 
     if (dumpProperties) {
-      configBuilder.set(ConfigPrinterFactory.CONFIG_PRINTER, "properties-file");
+      configBuilder.setString(ConfigPrinterFactory.CONFIG_PRINTER, "properties-file");
     }
 
     configBuilder.popDefaultLocation();
@@ -702,10 +705,6 @@
     jayceImport.add(importFile);
   }
 
-  public void setFilter(@Nonnull Filter<JMethod> filter) {
-    this.filter = filter;
-  }
-
   public void addProperty(@Nonnull String propertyName, @Nonnull String propertyValue) {
     properties.put(propertyName, propertyValue);
   }
diff --git a/jack/src/com/android/jack/backend/dex/ClassDefItemBuilder.java b/jack/src/com/android/jack/backend/dex/ClassDefItemBuilder.java
index b6b43a6..eb873cc 100644
--- a/jack/src/com/android/jack/backend/dex/ClassDefItemBuilder.java
+++ b/jack/src/com/android/jack/backend/dex/ClassDefItemBuilder.java
@@ -95,7 +95,7 @@
       return;
     }
 
-    DexFileMarker dexFileMarker = declaredType.getJProgram().getMarker(DexFileMarker.class);
+    DexFileMarker dexFileMarker = declaredType.getSession().getMarker(DexFileMarker.class);
     assert dexFileMarker != null;
 
     DexFile dexFile = dexFileMarker.getDexFile();
@@ -127,10 +127,10 @@
     if (superClass == null) {
       if (type instanceof JDefinedInterface) {
         return RopHelper.getCstType(
-            Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT));
+            Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT));
       } else {
-        assert type == Jack.getProgram().getPhantomLookup().getType(CommonTypes.JAVA_LANG_OBJECT)
-            || type == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+        assert type == Jack.getSession().getPhantomLookup().getType(CommonTypes.JAVA_LANG_OBJECT)
+            || type == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
         return null;
       }
     }
diff --git a/jack/src/com/android/jack/backend/dex/DexFileBuilder.java b/jack/src/com/android/jack/backend/dex/DexFileBuilder.java
index b6b4100..910f6c0 100644
--- a/jack/src/com/android/jack/backend/dex/DexFileBuilder.java
+++ b/jack/src/com/android/jack/backend/dex/DexFileBuilder.java
@@ -18,7 +18,7 @@
 
 import com.android.jack.dx.dex.DexOptions;
 import com.android.jack.dx.dex.file.DexFile;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.marker.DexFileMarker;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
@@ -28,27 +28,27 @@
 import javax.annotation.Nonnull;
 
 /**
- * Builds a {@code DexFile} instance from a {@code JProgram}.
+ * Builds a {@code DexFile} instance from a {@code Session}.
  *
  * <p>This builder only creates an empty {@code DexFile} instance. This instance
  * is then filled with {@code ClassDefItem}s by the {@code ClassDefItemBuilder}.
  *
  * @see ClassDefItemBuilder
  */
-@Description("Builds a DexFile instance from a JProgram.")
+@Description("Builds a DexFile instance from a Session.")
 @Name("DexFileBuilder")
 @Transform(add = DexFileMarker.class)
-public class DexFileBuilder implements RunnableSchedulable<JProgram> {
+public class DexFileBuilder implements RunnableSchedulable<JSession> {
   private final DexFile dexFile = new DexFile(new DexOptions());
 
   /**
-   * Attaches the {@code DexFile} instance to build to the given {@code program}
+   * Attaches the {@code DexFile} instance to build to the given {@code session}
    * in a {@code DexFileMarker}. This {@code DexFile} instance is then accessible
    * in {@code ClassDefItemBuilder} schedulable.
    */
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     DexFileMarker dexFileMarker = new DexFileMarker(dexFile);
-    program.addMarker(dexFileMarker);
+    session.addMarker(dexFileMarker);
   }
 }
diff --git a/jack/src/com/android/jack/backend/dex/DexFileWriter.java b/jack/src/com/android/jack/backend/dex/DexFileWriter.java
index c92f27c..d158a34 100644
--- a/jack/src/com/android/jack/backend/dex/DexFileWriter.java
+++ b/jack/src/com/android/jack/backend/dex/DexFileWriter.java
@@ -19,7 +19,7 @@
 import com.android.jack.JackFileException;
 import com.android.jack.Options;
 import com.android.jack.dx.dex.file.DexFile;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.feature.DexNonZipOutput;
 import com.android.jack.scheduling.marker.DexFileMarker;
 import com.android.jack.scheduling.tags.DexFileProduct;
@@ -45,14 +45,14 @@
 @Constraint(need = {DexFileMarker.Complete.class})
 @Produce(DexFileProduct.class)
 @Support(DexNonZipOutput.class)
-public class DexFileWriter implements RunnableSchedulable<JProgram> {
+public class DexFileWriter implements RunnableSchedulable<JSession> {
 
   @Nonnull
   protected File outputFile = ThreadConfig.get(Options.DEX_FILE_OUTPUT);
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
-    DexFile dexFile = getDexFile(program);
+  public void run(@Nonnull JSession session) throws Exception {
+    DexFile dexFile = getDexFile(session);
 
     FileOutputStream fileOutputStream = new FileOutputStream(outputFile);
     try {
@@ -66,8 +66,8 @@
   }
 
   @Nonnull
-  protected DexFile getDexFile(@Nonnull JProgram program) {
-    DexFileMarker dexFileMarker = program.getMarker(DexFileMarker.class);
+  protected DexFile getDexFile(@Nonnull JSession session) {
+    DexFileMarker dexFileMarker = session.getMarker(DexFileMarker.class);
     assert dexFileMarker != null;
     DexFile dexFile = dexFileMarker.getDexFile();
     assert dexFile != null;
diff --git a/jack/src/com/android/jack/backend/dex/DexZipWriter.java b/jack/src/com/android/jack/backend/dex/DexZipWriter.java
index 2c14498..f966a5e 100644
--- a/jack/src/com/android/jack/backend/dex/DexZipWriter.java
+++ b/jack/src/com/android/jack/backend/dex/DexZipWriter.java
@@ -19,7 +19,7 @@
 import com.android.jack.JackFileException;
 import com.android.jack.backend.jayce.ResourceContainerMarker;
 import com.android.jack.dx.dex.file.DexFile;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.feature.DexZipOutput;
 import com.android.jack.scheduling.marker.DexFileMarker;
 import com.android.jack.scheduling.tags.DexFileProduct;
@@ -29,11 +29,13 @@
 import com.android.sched.schedulable.Constraint;
 import com.android.sched.schedulable.Produce;
 import com.android.sched.schedulable.Support;
+import com.android.sched.util.config.Location;
+import com.android.sched.util.config.ZipLocation;
+import com.android.sched.vfs.InputVFile;
 
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
 import java.util.zip.ZipOutputStream;
 
 import javax.annotation.Nonnull;
@@ -52,8 +54,8 @@
   private static final String DEX_NAME = "classes.dex";
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
-    DexFile dexFile = getDexFile(program);
+  public void run(@Nonnull JSession session) throws Exception {
+    DexFile dexFile = getDexFile(session);
 
     ZipOutputStream zos = null;
     try {
@@ -63,16 +65,22 @@
       dexFile.writeTo(zos, null, false);
       zos.closeEntry();
 
-      ResourceContainerMarker resourceContainer = program.getMarker(ResourceContainerMarker.class);
+      ResourceContainerMarker resourceContainer = session.getMarker(ResourceContainerMarker.class);
       if (resourceContainer != null) {
-        ZipFile zipFile = resourceContainer.getZipFile();
-        for (ZipEntry resourceEntry : resourceContainer.getZipEntries()) {
+        for (InputVFile resource : resourceContainer.getResources()) {
+          Location location = resource.getLocation();
+          String entryName;
+          if (location instanceof ZipLocation) {
+            ZipLocation zipLocation = (ZipLocation) location;
+            entryName = zipLocation.getEntryName();
+          } else {
+            entryName = resource.getName();
+          }
+          ZipEntry resourceEntry = new ZipEntry(entryName);
           zos.putNextEntry(resourceEntry);
-          BytesStreamSucker sucker =
-              new BytesStreamSucker(zipFile.getInputStream(resourceEntry), zos);
+          BytesStreamSucker sucker = new BytesStreamSucker(resource.openRead(), zos);
           sucker.run();
         }
-        zipFile.close();
       }
     } catch (IOException e) {
       throw new JackFileException(
diff --git a/jack/src/com/android/jack/backend/dex/FieldInitializerRemover.java b/jack/src/com/android/jack/backend/dex/FieldInitializerRemover.java
index 4485055..4739569 100644
--- a/jack/src/com/android/jack/backend/dex/FieldInitializerRemover.java
+++ b/jack/src/com/android/jack/backend/dex/FieldInitializerRemover.java
@@ -61,12 +61,12 @@
   @Nonnull
   public static final BooleanPropertyId CLASS_AS_INITIALVALUE = BooleanPropertyId.create(
       "jack.legacy.dx.initialvalue.class",
-      "Emit class literal as initial value of field").addDefaultValue("true");
+      "Emit class literal as initial value of field").addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId STRING_AS_INITIALVALUE_OF_OBJECT = BooleanPropertyId.create(
       "jack.legacy.runtime.initialvalue.string",
-      "Emit string literal as initial value of field").addDefaultValue("true");
+      "Emit string literal as initial value of field").addDefaultValue(Boolean.TRUE);
 
   private final boolean allowClassInInitialValue =
       ThreadConfig.get(CLASS_AS_INITIALVALUE).booleanValue();
@@ -84,7 +84,7 @@
           /* Object field initialized by a String literal: don't remove unless allowed */
           && (allowStringAsObjectInit
               || !((field.getType() !=
-                        Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING))
+                        Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING))
                   && (initialValue instanceof JAbstractStringLiteral)))
           /* Field initialized by a class literal: don't remove unless allowed */
           && (allowClassInInitialValue || !(initialValue instanceof JClassLiteral))
diff --git a/jack/src/com/android/jack/backend/dex/annotations/DefaultValueAnnotationAdder.java b/jack/src/com/android/jack/backend/dex/annotations/DefaultValueAnnotationAdder.java
index 35543ac..7275e6c 100644
--- a/jack/src/com/android/jack/backend/dex/annotations/DefaultValueAnnotationAdder.java
+++ b/jack/src/com/android/jack/backend/dex/annotations/DefaultValueAnnotationAdder.java
@@ -87,7 +87,7 @@
   @Nonnull
   public static final BooleanPropertyId EMIT_ANNOTATION_DEFAULT = BooleanPropertyId.create(
       "jack.annotation.annotationdefault", "Emit annotation default")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   private final Filter<JMethod> filter = ThreadConfig.get(Options.METHOD_FILTER);
@@ -150,7 +150,7 @@
   @Nonnull
   private JAnnotation getDefaultAnnotationType(@Nonnull JDefinedClassOrInterface type) {
     if (defaultAnnotation == null) {
-      defaultAnnotation = type.getJProgram()
+      defaultAnnotation = type.getSession()
           .getPhantomLookup().getAnnotation(DexAnnotations.ANNOTATION_ANNOTATION_DEFAULT);
     }
     assert defaultAnnotation != null;
diff --git a/jack/src/com/android/jack/backend/dex/annotations/ReflectAnnotationsAdder.java b/jack/src/com/android/jack/backend/dex/annotations/ReflectAnnotationsAdder.java
index 2fc3e60..540a343 100644
--- a/jack/src/com/android/jack/backend/dex/annotations/ReflectAnnotationsAdder.java
+++ b/jack/src/com/android/jack/backend/dex/annotations/ReflectAnnotationsAdder.java
@@ -129,6 +129,11 @@
     }
 
     @Override
+    public boolean visit(@Nonnull JMethod x) {
+      return false;
+    }
+
+    @Override
     public void endVisit(@Nonnull JDefinedClassOrInterface x) {
       JClassOrInterface enclosingType = x.getEnclosingType();
       if (enclosingType != null) {
@@ -380,21 +385,21 @@
   @Nonnull
   public static final BooleanPropertyId EMIT_ANNOTATION_SIG = BooleanPropertyId.create(
       "jack.annotation.signature", "Emit annotation signature")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_ANNOTATION_ENCLOSING_METHOD = BooleanPropertyId.create(
       "jack.annotation.enclosingmethod", "Emit annotation enclosing method")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_ANNOTATION_THROWS = BooleanPropertyId.create(
-      "jack.annotation.throws", "Emit annotation throws").addDefaultValue("true");
+      "jack.annotation.throws", "Emit annotation throws").addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_ANNOTATION_MEMBER_CLASSES = BooleanPropertyId.create(
       "jack.annotation.memberclasses", "Emit annotation member classes")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   private final boolean addAnnotationThrows =
       ThreadConfig.get(EMIT_ANNOTATION_THROWS).booleanValue();
@@ -411,7 +416,7 @@
   @Override
   public synchronized void run(@Nonnull JDefinedClassOrInterface declaredType) throws Exception {
     TransformationRequest tr = new TransformationRequest(declaredType);
-    Visitor visitor = new Visitor(tr, declaredType.getJProgram().getPhantomLookup());
+    Visitor visitor = new Visitor(tr, declaredType.getSession().getPhantomLookup());
     visitor.accept(declaredType);
     tr.commit();
   }
diff --git a/jack/src/com/android/jack/backend/dex/rop/CodeItemBuilder.java b/jack/src/com/android/jack/backend/dex/rop/CodeItemBuilder.java
index 66d7350b..97031e8 100644
--- a/jack/src/com/android/jack/backend/dex/rop/CodeItemBuilder.java
+++ b/jack/src/com/android/jack/backend/dex/rop/CodeItemBuilder.java
@@ -144,17 +144,17 @@
   @Nonnull
   public static final BooleanPropertyId EMIT_SYNTHETIC_LOCAL_DEBUG_INFO = BooleanPropertyId.create(
       "jack.dex.debug.vars.synthetic",
-      "Emit synthetic local variable debug info into generated dex").addDefaultValue("false");
+      "Emit synthetic local variable debug info into generated dex").addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final BooleanPropertyId DEX_OPTIMIZE = BooleanPropertyId.create(
       "jack.dex.optimize", "Define if Dex optimizations are activated")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId FORCE_JUMBO = BooleanPropertyId.create(
       "jack.dex.forcejumbo", "Force string opcodes to be emitted as jumbo in dex")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   private final Filter<JMethod> filter = ThreadConfig.get(Options.METHOD_FILTER);
@@ -487,7 +487,7 @@
   @Nonnull
   private DalvCode createCode(@Nonnull JMethod method, @Nonnull RopMethod ropMethod) {
     DexFileMarker dexFileMarker =
-        method.getEnclosingType().getJProgram().getMarker(DexFileMarker.class);
+        method.getEnclosingType().getSession().getMarker(DexFileMarker.class);
     assert dexFileMarker != null;
 
     DexOptions options = dexFileMarker.getDexFile().getDexOptions();
diff --git a/jack/src/com/android/jack/backend/jayce/JayceFileImporter.java b/jack/src/com/android/jack/backend/jayce/JayceFileImporter.java
index ec07c79..ed50bc5 100644
--- a/jack/src/com/android/jack/backend/jayce/JayceFileImporter.java
+++ b/jack/src/com/android/jack/backend/jayce/JayceFileImporter.java
@@ -20,30 +20,26 @@
 import com.android.jack.JackEventType;
 import com.android.jack.JackFileException;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JPackage;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.jayce.JayceFormatException;
 import com.android.jack.jayce.JayceVersionException;
-import com.android.jack.lookup.JLookup;
 import com.android.sched.util.codec.EnumCodec;
-import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.HasKeyId;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.config.ThreadConfig;
-import com.android.sched.util.config.ZipLocation;
 import com.android.sched.util.config.id.PropertyId;
 import com.android.sched.util.log.Event;
 import com.android.sched.util.log.LoggerFactory;
 import com.android.sched.util.log.Tracer;
 import com.android.sched.util.log.TracerFactory;
+import com.android.sched.vfs.InputVDir;
+import com.android.sched.vfs.InputVFile;
+import com.android.sched.vfs.VElement;
 
-import java.io.File;
 import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Enumeration;
 import java.util.List;
 import java.util.logging.Level;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
 
 import javax.annotation.Nonnull;
 
@@ -56,6 +52,8 @@
   @Nonnull
   public static final String JAYCE_FILE_EXTENSION = ".jack";
 
+  public static final int JACK_EXTENSION_LENGTH = JAYCE_FILE_EXTENSION.length();
+
   @Nonnull
   private final Tracer tracer = TracerFactory.getTracer();
 
@@ -63,7 +61,7 @@
   private final java.util.logging.Logger logger = LoggerFactory.getLogger();
 
   @Nonnull
-  private final List<File> jayceContainers;
+  private final List<InputVDir> jayceContainers;
 
   private enum CollisionPolicy {
     KEEP_FIRST,
@@ -75,100 +73,86 @@
       "jack.jackimport.policy",
       "Defines the policy to follow concerning type collision in imported jack files",
       new EnumCodec<CollisionPolicy>(CollisionPolicy.values()).ignoreCase())
-      .addDefaultValue("fail");
+      .addDefaultValue(CollisionPolicy.FAIL);
 
   @Nonnull
   private final CollisionPolicy collisionPolicy = ThreadConfig.get(COLLISION_POLICY);
 
-  public JayceFileImporter(@Nonnull List<File> jayceContainers) {
+  public JayceFileImporter(@Nonnull List<InputVDir> jayceContainers) {
     this.jayceContainers = jayceContainers;
   }
 
-  public void doImport(@Nonnull JProgram program)
-      throws JayceFormatException, JayceVersionException, JackFileException {
+  public void doImport(@Nonnull JSession session) throws JayceFormatException,
+      JayceVersionException, JackFileException {
 
-    JLookup lookup = program.getPhantomLookup();
-    for (File jayceContainer : jayceContainers) {
-      String rootDirPath = jayceContainer.getAbsolutePath();
+    ResourceContainerMarker resourceMarker = session.getMarker(ResourceContainerMarker.class);
+    if (resourceMarker == null) {
+      resourceMarker = new ResourceContainerMarker();
+      session.addMarker(resourceMarker);
+    }
+    for (InputVDir jayceContainer : jayceContainers) {
       try {
-        if (jayceContainer.isDirectory()) {
-          logger.log(Level.FINE, "Importing jack directory ''{0}''",
-              jayceContainer.getAbsolutePath());
-          for (File subFile : jayceContainer.listFiles()) {
-            importJayceFile(subFile, program, lookup, rootDirPath);
-          }
-        } else {
-          // try zip
-          ZipFile zipFile = new ZipFile(jayceContainer);
-          logger.log(Level.FINE, "Importing jack archive ''{0}''",
-              jayceContainer.getAbsolutePath());
-          List<ZipEntry> resources = new ArrayList<ZipEntry>();
-          Enumeration<? extends ZipEntry> zipFileEntries = zipFile.entries();
-          while (zipFileEntries.hasMoreElements()) {
-            ZipEntry zipEntry = zipFileEntries.nextElement();
-            if (zipEntry.getName().endsWith(JAYCE_FILE_EXTENSION)) {
-              addImportedTypesToProgram(
-                  program,
-                  lookup,
-                  zipEntry.getName(),
-                  rootDirPath,
-                  new ZipLocation(new FileLocation(jayceContainer), zipEntry));
-            } else {
-              resources.add(zipEntry);
-            }
-          }
-          program.addMarker(new ResourceContainerMarker(zipFile, resources));
+        logger.log(Level.FINE, "Importing {0}", jayceContainer.getLocation().getDescription());
+        JPackage topLevelPackage = session.getTopLevelPackage();
+        for (VElement subFile : jayceContainer.list()) {
+          importJayceFile(subFile, session, topLevelPackage, resourceMarker);
         }
       } catch (IOException e) {
-        throw new JackFileException("Error reading jack archive " + rootDirPath, e);
+        throw new JackFileException(
+            "Error importing " + jayceContainer.getLocation().getDescription(), e);
       }
     }
   }
 
-  private void importJayceFile(@Nonnull File file, @Nonnull JProgram program,
-      @Nonnull JLookup lookup,
-      @Nonnull String rootDirPath) throws IOException, JayceFormatException, JayceVersionException {
-    if (file.isDirectory()) {
-      for (File subFile : file.listFiles()) {
-        importJayceFile(subFile, program, lookup, rootDirPath);
+  private void importJayceFile(@Nonnull VElement element, @Nonnull JSession session,
+      @Nonnull JPackage pack, @Nonnull ResourceContainerMarker resourceMarker) throws IOException,
+      JayceFormatException, JayceVersionException {
+    if (element instanceof InputVDir) {
+      for (VElement subFile : ((InputVDir) element).list()) {
+        importJayceFile(subFile, session, pack.getSubPackage(element.getName()), resourceMarker);
+      }
+    } else if (element instanceof InputVFile) {
+      InputVFile file = (InputVFile) element;
+      if (isJackFileName(file.getName())) {
+        addImportedTypes(session, file.getName(), pack, file.getLocation());
+      } else {
+        resourceMarker.addResource(file);
       }
     } else {
-      if (file.getName().endsWith(JAYCE_FILE_EXTENSION)) {
-        String fullName = file.getAbsolutePath().substring(rootDirPath.length() + 1);
-        addImportedTypesToProgram(program, lookup, fullName, rootDirPath, new FileLocation(file));
-      }
+      throw new AssertionError();
     }
   }
 
-  private void addImportedTypesToProgram(
-      @Nonnull JProgram program,
-      @Nonnull JLookup lookup,
-      @Nonnull String path,
-      @Nonnull String rootDirPath,
-      @Nonnull Location expectedLoadSource) throws JayceFormatException, JayceVersionException {
-
+  private void addImportedTypes(@Nonnull JSession session, @Nonnull String path,
+      @Nonnull JPackage pack, @Nonnull Location expectedLoadSource) throws JayceFormatException,
+      JayceVersionException {
     Event readEvent = tracer.start(JackEventType.NNODE_READING_FOR_IMPORT);
     try {
-      logger.log(Level.FINEST, "Importing jack file ''{0}'' - from ''{1}''",
-          new Object[] {path, rootDirPath});
-      String typeBinaryName = path.substring(0, path.length() - JAYCE_FILE_EXTENSION.length());
-      JDefinedClassOrInterface declaredType =
-          (JDefinedClassOrInterface) lookup.getType('L' + typeBinaryName + ';');
+      logger.log(Level.FINEST, "Importing jack file ''{0}'' in package ''{1}''",
+          new Object[] {path, Jack.getUserFriendlyFormatter().getName(pack)});
+      String simpleName = path.substring(0, path.length() - JAYCE_FILE_EXTENSION.length());
+      JDefinedClassOrInterface declaredType = pack.getType(simpleName);
       Location existingSource = declaredType.getLocation();
       if (!expectedLoadSource.equals(existingSource)) {
         if (collisionPolicy == CollisionPolicy.FAIL) {
           throw new ImportConflictException(declaredType, expectedLoadSource);
         } else {
-          logger.log(Level.INFO, "Type '{0}' from '{1}' has already been imported from {2}: "
+          logger.log(Level.INFO,
+              "Type ''{0}'' has already been imported from {1}: "
               + "ignoring import", new Object[] {
-              Jack.getUserFriendlyFormatter().getName(declaredType), rootDirPath,
-              "'" + existingSource.getDescription() + "'"});
+              Jack.getUserFriendlyFormatter().getName(declaredType),
+              existingSource.getDescription()});
         }
       } else {
-        program.addTypeToEmit(declaredType);
+        session.addTypeToEmit(declaredType);
       }
     } finally {
       readEvent.end();
     }
   }
+
+  public static boolean isJackFileName(@Nonnull String name) {
+    return (name.length() > JACK_EXTENSION_LENGTH) && (name.substring(
+        name.length() - JACK_EXTENSION_LENGTH).equalsIgnoreCase(JAYCE_FILE_EXTENSION));
+  }
 }
diff --git a/jack/src/com/android/jack/backend/jayce/JayceSingleTypeWriter.java b/jack/src/com/android/jack/backend/jayce/JayceSingleTypeWriter.java
index de300c9..fef2d32 100644
--- a/jack/src/com/android/jack/backend/jayce/JayceSingleTypeWriter.java
+++ b/jack/src/com/android/jack/backend/jayce/JayceSingleTypeWriter.java
@@ -28,15 +28,19 @@
 import com.android.jack.scheduling.feature.JackFileNonZipOutput;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
+import com.android.sched.item.Synchronized;
 import com.android.sched.schedulable.Constraint;
 import com.android.sched.schedulable.Produce;
 import com.android.sched.schedulable.RunnableSchedulable;
 import com.android.sched.schedulable.Support;
 import com.android.sched.util.config.ThreadConfig;
+import com.android.sched.util.file.Directory;
+import com.android.sched.vfs.OutputVDir;
+import com.android.sched.vfs.OutputVFile;
+import com.android.sched.vfs.direct.OutputDirectDir;
 
 import java.io.BufferedOutputStream;
 import java.io.File;
-import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.OutputStream;
 
@@ -50,26 +54,22 @@
 @Constraint(need = {JackFormatIr.class}, no = {NonJackFormatIr.class})
 @Produce(JackFormatProduct.class)
 @Support(JackFileNonZipOutput.class)
+@Synchronized
 public class JayceSingleTypeWriter implements RunnableSchedulable<JDefinedClassOrInterface> {
 
   @Nonnull
   private static final TypeFormatter formatter = new FilePathFormatter();
 
   @Nonnull
-  private final File outputDir = ThreadConfig.get(Options.JACK_FILE_OUTPUT_DIR).getFile();
+  private final Directory outputDir = ThreadConfig.get(Options.JACK_FILE_OUTPUT_DIR);
 
   @Override
-  public void run(@Nonnull JDefinedClassOrInterface type) throws Exception {
-    String filePath = getFilePath(type);
-    File typeFile = new File(outputDir, filePath);
+  public synchronized void run(@Nonnull JDefinedClassOrInterface type) throws Exception {
+    OutputVDir vDir = new OutputDirectDir(outputDir);
+    OutputVFile vFile = vDir.createOutputVFile(getFilePath(type));
 
     try {
-      if (!typeFile.getParentFile().mkdirs() && !typeFile.getParentFile().isDirectory()) {
-        throw new IOException(
-            "Could not create directory: " + typeFile.getParentFile().getAbsolutePath());
-      }
-
-      OutputStream out = new BufferedOutputStream(new FileOutputStream(typeFile));
+      OutputStream out = new BufferedOutputStream(vFile.openWrite());
       try {
         // Write to file
         JayceWriter writer = new JayceWriter(out);
@@ -78,8 +78,7 @@
         out.close();
       }
     } catch (IOException e) {
-      throw new JackFileException(
-          "Could not write Jack file to output '" + typeFile.getAbsolutePath() + "'", e);
+      throw new JackFileException("Could not write Jack file to output '" + vFile + "'", e);
     }
   }
 
diff --git a/jack/src/com/android/jack/backend/jayce/JayceZipWriter.java b/jack/src/com/android/jack/backend/jayce/JayceZipWriter.java
index dec5124..221b38c 100644
--- a/jack/src/com/android/jack/backend/jayce/JayceZipWriter.java
+++ b/jack/src/com/android/jack/backend/jayce/JayceZipWriter.java
@@ -21,7 +21,7 @@
 import com.android.jack.ir.JackFormatIr;
 import com.android.jack.ir.NonJackFormatIr;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.jayce.JayceWriter;
 import com.android.jack.scheduling.feature.JackFileZipOutput;
 import com.android.jack.util.BytesStreamSucker;
@@ -31,14 +31,16 @@
 import com.android.sched.schedulable.Produce;
 import com.android.sched.schedulable.RunnableSchedulable;
 import com.android.sched.schedulable.Support;
+import com.android.sched.util.config.Location;
 import com.android.sched.util.config.ThreadConfig;
+import com.android.sched.util.config.ZipLocation;
+import com.android.sched.vfs.InputVFile;
 
 import java.io.BufferedOutputStream;
 import java.io.File;
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
 import java.util.zip.ZipOutputStream;
 
 import javax.annotation.Nonnull;
@@ -51,19 +53,19 @@
 @Constraint(need = {JackFormatIr.class}, no = {NonJackFormatIr.class})
 @Produce(JackFormatProduct.class)
 @Support(JackFileZipOutput.class)
-public class JayceZipWriter implements RunnableSchedulable<JProgram> {
+public class JayceZipWriter implements RunnableSchedulable<JSession> {
 
   @Nonnull
   private final File outputZip = ThreadConfig.get(Options.JACK_FILE_OUTPUT_ZIP);
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
 
     try {
       ZipOutputStream zos =
           new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(outputZip)));
       try {
-        for (JDefinedClassOrInterface type : program.getTypesToEmit()) {
+        for (JDefinedClassOrInterface type : session.getTypesToEmit()) {
           String filePath = JayceSingleTypeWriter.getFilePath(type);
           ZipEntry zipEntry = new ZipEntry(filePath);
           zos.putNextEntry(zipEntry);
@@ -72,16 +74,23 @@
         }
 
         ResourceContainerMarker resourceContainer =
-            program.getMarker(ResourceContainerMarker.class);
+            session.getMarker(ResourceContainerMarker.class);
         if (resourceContainer != null) {
-          ZipFile zipFile = resourceContainer.getZipFile();
-          for (ZipEntry resourceEntry : resourceContainer.getZipEntries()) {
+          for (InputVFile resource : resourceContainer.getResources()) {
+            Location location = resource.getLocation();
+            String entryName;
+            if (location instanceof ZipLocation) {
+              ZipLocation zipLocation = (ZipLocation) location;
+              entryName = zipLocation.getEntryName();
+            } else {
+              entryName = resource.getName();
+            }
+            ZipEntry resourceEntry = new ZipEntry(entryName);
             zos.putNextEntry(resourceEntry);
             BytesStreamSucker sucker =
-                new BytesStreamSucker(zipFile.getInputStream(resourceEntry), zos);
+                new BytesStreamSucker(resource.openRead(), zos);
             sucker.run();
           }
-          zipFile.close();
         }
       } finally {
         zos.close();
diff --git a/jack/src/com/android/jack/backend/jayce/ResourceContainerMarker.java b/jack/src/com/android/jack/backend/jayce/ResourceContainerMarker.java
index b4acc21..d128015 100644
--- a/jack/src/com/android/jack/backend/jayce/ResourceContainerMarker.java
+++ b/jack/src/com/android/jack/backend/jayce/ResourceContainerMarker.java
@@ -16,14 +16,14 @@
 
 package com.android.jack.backend.jayce;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.marker.Marker;
 import com.android.sched.marker.ValidOn;
+import com.android.sched.vfs.InputVFile;
 
+import java.util.ArrayList;
 import java.util.List;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
 
 import javax.annotation.Nonnull;
 
@@ -31,27 +31,18 @@
  * A marker that contains resources.
  */
 @Description("A marker that contains resources.")
-@ValidOn(JProgram.class)
+@ValidOn(JSession.class)
 public final class ResourceContainerMarker implements Marker {
 
   @Nonnull
-  private final ZipFile zipFile;
-  @Nonnull
-  private final List<ZipEntry> zipEntries;
+  private final List<InputVFile> resourceFiles = new ArrayList<InputVFile>();
 
-  public ResourceContainerMarker(@Nonnull ZipFile zipFile, @Nonnull List<ZipEntry> zipEntries) {
-    this.zipFile = zipFile;
-    this.zipEntries = zipEntries;
+  public ResourceContainerMarker() {
   }
 
   @Nonnull
-  public List<ZipEntry> getZipEntries() {
-    return zipEntries;
-  }
-
-  @Nonnull
-  public ZipFile getZipFile() {
-    return zipFile;
+  public List<InputVFile> getResources() {
+    return resourceFiles;
   }
 
   @Override
@@ -60,4 +51,11 @@
     return this;
   }
 
+  public void addResource(@Nonnull InputVFile file) {
+    boolean res = resourceFiles.add(file);
+    if (!res) {
+      throw new AssertionError();
+    }
+  }
+
 }
diff --git a/jack/src/com/android/jack/cfg/CfgMarkerRemover.java b/jack/src/com/android/jack/cfg/CfgMarkerRemover.java
index 7e5bab2..cf1f6a4 100644
--- a/jack/src/com/android/jack/cfg/CfgMarkerRemover.java
+++ b/jack/src/com/android/jack/cfg/CfgMarkerRemover.java
@@ -16,14 +16,17 @@
 
 package com.android.jack.cfg;
 
+import com.android.jack.Options;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JVisitor;
+import com.android.jack.util.filter.Filter;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
 import com.android.sched.schedulable.Constraint;
 import com.android.sched.schedulable.RunnableSchedulable;
 import com.android.sched.schedulable.Transform;
+import com.android.sched.util.config.ThreadConfig;
 
 import javax.annotation.Nonnull;
 
@@ -36,6 +39,9 @@
 @Transform(remove = {ControlFlowGraph.class, BasicBlockMarker.class})
 public class CfgMarkerRemover implements RunnableSchedulable<JMethod> {
 
+  @Nonnull
+  private final Filter<JMethod> filter = ThreadConfig.get(Options.METHOD_FILTER);
+
   private static class Visitor extends JVisitor {
     @Override
     public boolean visit(@Nonnull JStatement stmt) {
@@ -46,6 +52,11 @@
 
   @Override
   public void run(@Nonnull JMethod method) throws Exception {
+    if (method.getEnclosingType().isExternal() || method.isNative() || method.isAbstract()
+        || !filter.accept(this.getClass(), method)) {
+      return;
+    }
+
     method.removeMarker(ControlFlowGraph.class);
     Visitor v = new Visitor();
     v.accept(method);
diff --git a/jack/src/com/android/jack/config/id/JavaVersionPropertyId.java b/jack/src/com/android/jack/config/id/JavaVersionPropertyId.java
index fe62ff9..e35e0a2 100644
--- a/jack/src/com/android/jack/config/id/JavaVersionPropertyId.java
+++ b/jack/src/com/android/jack/config/id/JavaVersionPropertyId.java
@@ -100,6 +100,14 @@
 
   @Override
   @Nonnull
+  public JavaVersionPropertyId addDefaultValue (@Nonnull JavaVersion defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public JavaVersionPropertyId requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
diff --git a/jack/src/com/android/jack/frontend/TypeDuplicateRemoverChecker.java b/jack/src/com/android/jack/frontend/TypeDuplicateRemoverChecker.java
index c320770..eb3eb9f 100644
--- a/jack/src/com/android/jack/frontend/TypeDuplicateRemoverChecker.java
+++ b/jack/src/com/android/jack/frontend/TypeDuplicateRemoverChecker.java
@@ -26,7 +26,7 @@
 import com.android.jack.ir.ast.JFieldId;
 import com.android.jack.ir.ast.JInterface;
 import com.android.jack.ir.ast.JNode;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.lookup.JLookup;
@@ -49,37 +49,37 @@
     "counterparts in IR.")
 @Name("TypeDuplicatesRemoverChecker")
 @Support(SanityChecks.class)
-public class TypeDuplicateRemoverChecker implements RunnableSchedulable<JProgram> {
+public class TypeDuplicateRemoverChecker implements RunnableSchedulable<JSession> {
 
   private static class Visitor extends JVisitor {
 
     @Nonnull
-    private final JProgram program;
+    private final JSession session;
 
-    public Visitor(@Nonnull JProgram  program) {
-      this.program = program;
+    public Visitor(@Nonnull JSession session) {
+      this.session = session;
     }
 
     @Override
     public void endVisit(@Nonnull JNode x) {
-      checkFieldsOf(x.getClass(), x, program);
+      checkFieldsOf(x.getClass(), x, session);
     }
   }
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
-    TypeDuplicateRemoverChecker.checkFieldsOf(Jack.getProgram().getPhantomLookup().getClass(),
-        Jack.getProgram().getPhantomLookup(), program);
+  public void run(@Nonnull JSession session) throws Exception {
+    TypeDuplicateRemoverChecker.checkFieldsOf(Jack.getSession().getPhantomLookup().getClass(),
+        Jack.getSession().getPhantomLookup(), session);
 
-    Visitor visitor = new Visitor(program);
-    for (JDefinedClassOrInterface declaredType : program.getTypesToEmit()) {
+    Visitor visitor = new Visitor(session);
+    for (JDefinedClassOrInterface declaredType : session.getTypesToEmit()) {
       visitor.accept(declaredType);
     }
   }
 
   @SuppressWarnings("rawtypes")
-  public static void checkFieldsOf(@Nonnull Class<?> type, @Nonnull Object node, JProgram program) {
-      JLookup lookup = program.getPhantomLookup();
+  public static void checkFieldsOf(@Nonnull Class<?> type, @Nonnull Object node, JSession session) {
+      JLookup lookup = session.getPhantomLookup();
       for (Field f : type.getDeclaredFields()) {
         boolean fieldAccess = f.isAccessible();
         try {
@@ -93,7 +93,7 @@
               if (typeField instanceof JArrayType) {
                 // break the stack overflow (JArrayType.array <=> JArrayType.elementType)
                 if (((JArrayType) typeField).getElementType() != node) {
-                  checkFieldsOf(typeField.getClass(), typeField, program);
+                  checkFieldsOf(typeField.getClass(), typeField, session);
                 }
               }
             }
@@ -113,7 +113,7 @@
                checkType(node, lookup, f, t);
              }
             } else if (fieldObject instanceof JFieldId) {
-              checkFieldsOf(fieldObject.getClass(), fieldObject, program);
+              checkFieldsOf(fieldObject.getClass(), fieldObject, session);
             }
         } catch (IllegalArgumentException e) {
           throw new AssertionError("Error during duplicate types checking.");
@@ -126,10 +126,10 @@
         }
       }
       if (type.getSuperclass() != null && type.getSuperclass() != JNode.class) {
-        checkFieldsOf(type.getSuperclass(), node, program);
+        checkFieldsOf(type.getSuperclass(), node, session);
       }
       for (Class<?> interf : type.getInterfaces()) {
-        checkFieldsOf(interf, node, program);
+        checkFieldsOf(interf, node, session);
       }
   }
 
diff --git a/jack/src/com/android/jack/frontend/java/JAstBuilder.java b/jack/src/com/android/jack/frontend/java/JAstBuilder.java
index 72a8b2e..c3f3ed9 100644
--- a/jack/src/com/android/jack/frontend/java/JAstBuilder.java
+++ b/jack/src/com/android/jack/frontend/java/JAstBuilder.java
@@ -21,10 +21,11 @@
 import com.android.jack.backend.jayce.JayceFileImporter;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.impl.EcjSourceTypeLoader;
 import com.android.jack.ir.impl.GwtAstBuilder;
 import com.android.jack.ir.impl.ReferenceMapper;
+import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.log.Event;
 import com.android.sched.util.log.Tracer;
 import com.android.sched.util.log.TracerFactory;
@@ -40,6 +41,7 @@
 import org.eclipse.jdt.internal.compiler.impl.CompilerOptions;
 import org.eclipse.jdt.internal.compiler.lookup.LocalTypeBinding;
 
+import java.io.File;
 import java.io.PrintWriter;
 import java.util.List;
 
@@ -55,7 +57,7 @@
   private static final Tracer tracer = TracerFactory.getTracer();
 
   @Nonnull
-  private final JProgram jprogram;
+  private final JSession session;
 
   @Nonnull
   private final GwtAstBuilder astBuilder;
@@ -78,7 +80,7 @@
       @CheckForNull PrintWriter out,
       @CheckForNull CompilationProgress progress,
       @Nonnull JayceFileImporter jayceImporter,
-      @Nonnull JProgram program) {
+      @Nonnull JSession session) {
     super(environment,
         policy,
         options,
@@ -86,15 +88,15 @@
         problemFactory,
         out,
         progress);
-    jprogram = program;
-    astBuilder = new GwtAstBuilder(lookupEnvironment, program);
+    this.session = session;
+    astBuilder = new GwtAstBuilder(lookupEnvironment, session);
     this.jayceImporter = jayceImporter;
   }
 
   @Nonnull
   private JPackage getOrCreatePackage(@Nonnull char[][] compoundName, int compoundNameLength) {
     assert compoundNameLength <= compoundName.length && compoundNameLength >= 0;
-    JPackage currentPackage = jprogram.getTopLevelPackage();
+    JPackage currentPackage = session.getTopLevelPackage();
     for (int i = 0; i < compoundNameLength; i++) {
       String name = String.valueOf(compoundName[i]);
       currentPackage = currentPackage.getOrCreateSubPackage(name);
@@ -133,7 +135,7 @@
       }
 
       for (JDefinedClassOrInterface type : types) {
-        jprogram.addTypeToEmit(type);
+        session.addTypeToEmit(type);
       }
     } finally {
       jastEvent.end();
@@ -154,7 +156,7 @@
         char[][] packageNames = parsedUnit.currentPackage.tokens;
         enclosingPackage = getOrCreatePackage(packageNames, packageNames.length);
       } else {
-        enclosingPackage = jprogram.getTopLevelPackage();
+        enclosingPackage = session.getTopLevelPackage();
       }
       ReferenceMapper refMap = astBuilder.getTypeMap();
 
@@ -171,14 +173,15 @@
         char[][] packageNames = unit.currentPackage.tokens;
         enclosingPackage = getOrCreatePackage(packageNames, packageNames.length);
       } else {
-        enclosingPackage = jprogram.getTopLevelPackage();
+        enclosingPackage = session.getTopLevelPackage();
       }
       ReferenceMapper refMap = astBuilder.getTypeMap();
       for (LocalTypeBinding binding : unit.localTypes) {
         /* binding.constantPoolName() == null means that ecj detected the local type to be dead
          * code and didn't completed processing */
         if (binding != null && binding.constantPoolName() != null) {
-          EcjSourceTypeLoader.createType(refMap, enclosingPackage, binding, null);
+          EcjSourceTypeLoader.createType(refMap, enclosingPackage, binding, null,
+              new FileLocation(new File(new String(unit.getFileName()))));
         }
       }
     }
@@ -187,7 +190,8 @@
   private void createTypes(@Nonnull JPackage enclosingPackage, @Nonnull ReferenceMapper refMap,
       @Nonnull TypeDeclaration typeDeclaration) {
     EcjSourceTypeLoader.createType(refMap, enclosingPackage, typeDeclaration.binding,
-        typeDeclaration);
+        typeDeclaration,
+        new FileLocation(new File(new String(typeDeclaration.compilationResult.fileName))));
     if (typeDeclaration.memberTypes != null) {
       for (TypeDeclaration memberType : typeDeclaration.memberTypes) {
         createTypes(enclosingPackage, refMap, memberType);
diff --git a/jack/src/com/android/jack/frontend/java/JackBatchCompiler.java b/jack/src/com/android/jack/frontend/java/JackBatchCompiler.java
index d7d9810..c2657b5 100644
--- a/jack/src/com/android/jack/frontend/java/JackBatchCompiler.java
+++ b/jack/src/com/android/jack/frontend/java/JackBatchCompiler.java
@@ -18,7 +18,7 @@
 
 import com.android.jack.backend.jayce.JayceFileImporter;
 import com.android.jack.ecj.loader.jast.JAstClasspath;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.util.log.LoggerFactory;
 
 import org.eclipse.jdt.internal.compiler.batch.ClasspathDirectory;
@@ -55,12 +55,12 @@
     LoggerFactory.getLogger();
 
   @Nonnull
-  private final JProgram program;
+  private final JSession session;
 
-  public JackBatchCompiler(@Nonnull JProgram program,
+  public JackBatchCompiler(@Nonnull JSession session,
       @Nonnull JayceFileImporter jayceFileImporter) {
     super(new PrintWriter(System.out), new PrintWriter(System.err), true, null, null);
-    this.program = program;
+    this.session = session;
     jayceImporter = jayceFileImporter;
   }
 
@@ -84,7 +84,7 @@
           isSourceOnly,
           rejectDestinationPathOnJars);
     } else if (JACK_LOGICAL_PATH_ENTRY.equals(currentClasspathName)) {
-      paths.add(new JAstClasspath(currentClasspathName, program.getLookup(), null));
+      paths.add(new JAstClasspath(currentClasspathName, session.getLookup(), null));
     } else {
 
       /* Call super so that it make the required checks and prepare ClasspathDex
@@ -151,7 +151,7 @@
         out,
         progress,
         jayceImporter,
-        program);
+        session);
     batchCompiler.remainingIterations = maxRepetition - currentRepetition;
     batchCompiler.useSingleThread = Boolean.getBoolean(USE_SINGLE_THREAD_SYSPROP);
 
diff --git a/jack/src/com/android/jack/ir/JackFormatIr.java b/jack/src/com/android/jack/ir/JackFormatIr.java
index 548e861..f925c2a 100644
--- a/jack/src/com/android/jack/ir/JackFormatIr.java
+++ b/jack/src/com/android/jack/ir/JackFormatIr.java
@@ -96,8 +96,8 @@
 import com.android.jack.ir.ast.JPrimitiveType.JLongType;
 import com.android.jack.ir.ast.JPrimitiveType.JShortType;
 import com.android.jack.ir.ast.JPrimitiveType.JVoidType;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReturnStatement;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShlOperation;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JShrOperation;
@@ -216,7 +216,7 @@
     JPrefixNegOperation.class,
     JPrefixNotOperation.class,
     JPrimitiveClassLiteral.class,
-    JProgram.class,
+    JSession.class,
     JReturnStatement.class,
     JShlOperation.class,
     JShortLiteral.class,
diff --git a/jack/src/com/android/jack/ir/JavaSourceIr.java b/jack/src/com/android/jack/ir/JavaSourceIr.java
index 27b67b3..33bd98c 100644
--- a/jack/src/com/android/jack/ir/JavaSourceIr.java
+++ b/jack/src/com/android/jack/ir/JavaSourceIr.java
@@ -117,8 +117,8 @@
 import com.android.jack.ir.ast.JPrimitiveType.JLongType;
 import com.android.jack.ir.ast.JPrimitiveType.JShortType;
 import com.android.jack.ir.ast.JPrimitiveType.JVoidType;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReturnStatement;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShlOperation;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JShrOperation;
@@ -261,7 +261,7 @@
     JPrefixNegOperation.class,
     JPrefixNotOperation.class,
     JPrimitiveClassLiteral.class,
-    JProgram.class,
+    JSession.class,
     JReturnStatement.class,
     JShlOperation.class,
     JShortLiteral.class,
diff --git a/jack/src/com/android/jack/ir/ast/Annotable.java b/jack/src/com/android/jack/ir/ast/Annotable.java
index 3d3ac71..c6c68c5 100644
--- a/jack/src/com/android/jack/ir/ast/Annotable.java
+++ b/jack/src/com/android/jack/ir/ast/Annotable.java
@@ -33,6 +33,4 @@
 
   @Nonnull
   Collection<JAnnotationLiteral> getAnnotations();
-
-  void updateAnnotations();
 }
diff --git a/jack/src/com/android/jack/ir/ast/AnnotationSet.java b/jack/src/com/android/jack/ir/ast/AnnotationSet.java
index 4384786..af611df 100644
--- a/jack/src/com/android/jack/ir/ast/AnnotationSet.java
+++ b/jack/src/com/android/jack/ir/ast/AnnotationSet.java
@@ -24,9 +24,7 @@
 import java.io.Serializable;
 import java.util.Collection;
 import java.util.HashMap;
-import java.util.Iterator;
 import java.util.Map;
-import java.util.Map.Entry;
 
 import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
@@ -103,21 +101,4 @@
       annotation.traverse(schedule);
     }
   }
-
-  void updateAnnotationSet() {
-    Map<JAnnotation, JAnnotationLiteral> updatedAnnotations =
-        new HashMap<JAnnotation, JAnnotationLiteral>();
-
-    Iterator<Entry<JAnnotation, JAnnotationLiteral>> it = annotations.entrySet().iterator();
-    while (it.hasNext()) {
-      Entry<JAnnotation, JAnnotationLiteral> entry = it.next();
-      JAnnotation valueType = entry.getValue().getType();
-      if (entry.getKey() != valueType) {
-        updatedAnnotations.put(valueType, entry.getValue());
-        it.remove();
-      }
-    }
-
-    annotations.putAll(updatedAnnotations);
-  }
 }
diff --git a/jack/src/com/android/jack/ir/ast/JAbstractStringLiteral.java b/jack/src/com/android/jack/ir/ast/JAbstractStringLiteral.java
index e741075..ccf8737 100644
--- a/jack/src/com/android/jack/ir/ast/JAbstractStringLiteral.java
+++ b/jack/src/com/android/jack/ir/ast/JAbstractStringLiteral.java
@@ -37,7 +37,7 @@
   @Override
   @Nonnull
   public JClass getType() {
-    return Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
+    return Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
   }
 
   @Nonnull
diff --git a/jack/src/com/android/jack/ir/ast/JArrayType.java b/jack/src/com/android/jack/ir/ast/JArrayType.java
index 97f6d9b..3ca3812 100644
--- a/jack/src/com/android/jack/ir/ast/JArrayType.java
+++ b/jack/src/com/android/jack/ir/ast/JArrayType.java
@@ -126,7 +126,7 @@
   public List<JInterface> getImplements() {
     // TODO(mikaelpeltier): Move init of superInterfaces into constructor (Bug:9652410)
     if (superInterfaces.isEmpty()) {
-      JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+      JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
       superInterfaces.add(lookup.getInterface(CommonTypes.JAVA_IO_SERIALIZABLE));
       superInterfaces.add(lookup.getInterface(CommonTypes.JAVA_LANG_CLONEABLE));
     }
diff --git a/jack/src/com/android/jack/ir/ast/JCastOperation.java b/jack/src/com/android/jack/ir/ast/JCastOperation.java
index d4dc73b..65bcb8d 100644
--- a/jack/src/com/android/jack/ir/ast/JCastOperation.java
+++ b/jack/src/com/android/jack/ir/ast/JCastOperation.java
@@ -62,13 +62,6 @@
     this.castType = type;
   }
 
-  /**
-   * Resolve an external reference during AST stitching.
-   */
-  public void resolve(@Nonnull JType newType) {
-    castType = newType;
-  }
-
   @Override
   protected void replaceImpl(@Nonnull JNode existingNode, @Nonnull JNode newNode)
       throws UnsupportedOperationException {
diff --git a/jack/src/com/android/jack/ir/ast/JClassLiteral.java b/jack/src/com/android/jack/ir/ast/JClassLiteral.java
index f2f409b..a4edff2 100644
--- a/jack/src/com/android/jack/ir/ast/JClassLiteral.java
+++ b/jack/src/com/android/jack/ir/ast/JClassLiteral.java
@@ -37,7 +37,7 @@
 
   private JClass javaLangClass;
 
-  private JType refType;
+  private final JType refType;
 
   public JClassLiteral(SourceInfo sourceInfo, JType type, JClass javaLangClass) {
     super(sourceInfo);
@@ -63,13 +63,6 @@
     return true;
   }
 
-  /**
-   * Resolve an external reference during AST stitching.
-   */
-  public void resolve(JType newType) {
-    refType = newType;
-  }
-
   @Override
   public void traverse(@Nonnull JVisitor visitor) {
     if (visitor.visit(this)) {
diff --git a/jack/src/com/android/jack/ir/ast/JConditionalExpression.java b/jack/src/com/android/jack/ir/ast/JConditionalExpression.java
index 037a509..0d8441b 100644
--- a/jack/src/com/android/jack/ir/ast/JConditionalExpression.java
+++ b/jack/src/com/android/jack/ir/ast/JConditionalExpression.java
@@ -104,7 +104,7 @@
     }
 
     // JLS-7 15.25 fourth bullet
-    JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+    JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
     if (isNumber(thenType) && isNumber(elseType)) {
       // first sub-bullet
       if ((JPrimitiveTypeEnum.BYTE.getType().isEquivalent(thenType)
diff --git a/jack/src/com/android/jack/ir/ast/JConstructor.java b/jack/src/com/android/jack/ir/ast/JConstructor.java
index c8a915f..392f3c4 100644
--- a/jack/src/com/android/jack/ir/ast/JConstructor.java
+++ b/jack/src/com/android/jack/ir/ast/JConstructor.java
@@ -18,6 +18,7 @@
 import com.android.jack.ir.SourceInfo;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
 import com.android.jack.load.MethodLoader;
+import com.android.jack.util.NamingTools;
 import com.android.sched.item.Component;
 import com.android.sched.item.Description;
 import com.android.sched.scheduler.ScheduleInstance;
@@ -35,7 +36,7 @@
 
   public JConstructor(@Nonnull SourceInfo info, @Nonnull JDefinedClass enclosingType,
       int modifier) {
-    super(info, new JMethodId(JProgram.INIT_NAME, MethodKind.INSTANCE_NON_VIRTUAL),
+    super(info, new JMethodId(NamingTools.INIT_NAME, MethodKind.INSTANCE_NON_VIRTUAL),
         enclosingType, JPrimitiveTypeEnum.VOID.getType(), modifier);
     assert JModifier.isMethodModifier(modifier);
     assert JModifier.isValidMethodModifier(modifier);
@@ -49,7 +50,7 @@
 
   public JConstructor(@Nonnull SourceInfo info, @Nonnull JDefinedClass enclosingType, int modifier,
       @Nonnull MethodLoader loader) {
-    super(info, new JMethodId(JProgram.INIT_NAME, MethodKind.INSTANCE_NON_VIRTUAL),
+    super(info, new JMethodId(NamingTools.INIT_NAME, MethodKind.INSTANCE_NON_VIRTUAL),
         enclosingType, JPrimitiveTypeEnum.VOID.getType(), modifier, loader);
     assert JModifier.isMethodModifier(modifier);
     assert JModifier.isValidMethodModifier(modifier);
diff --git a/jack/src/com/android/jack/ir/ast/JDefinedClassOrInterface.java b/jack/src/com/android/jack/ir/ast/JDefinedClassOrInterface.java
index 9a76555..2ab63d1 100644
--- a/jack/src/com/android/jack/ir/ast/JDefinedClassOrInterface.java
+++ b/jack/src/com/android/jack/ir/ast/JDefinedClassOrInterface.java
@@ -87,6 +87,9 @@
   @Nonnull
   protected final ClassOrInterfaceLoader loader;
 
+  @Nonnull
+  private final Location location;
+
   public JDefinedClassOrInterface(@Nonnull SourceInfo info, @Nonnull String name, int modifier,
       @Nonnull JPackage enclosingPackage) {
     this(info, name, modifier, enclosingPackage, NopClassOrInterfaceLoader.INSTANCE);
@@ -104,6 +107,7 @@
     this.enclosingPackage = enclosingPackage;
     this.enclosingPackage.addType(this);
     this.loader = loader;
+    location = loader.getLocation(this);
   }
 
   public void setModifier(int modifier) {
@@ -193,8 +197,8 @@
     return enclosingType;
   }
 
-  public JProgram getJProgram() {
-    return enclosingPackage.getProgram();
+  public JSession getSession() {
+    return enclosingPackage.getSession();
   }
 
   /**
@@ -404,11 +408,6 @@
     }
   }
 
-  @Override
-  public void updateAnnotations() {
-    annotations.updateAnnotationSet();
-  }
-
   @Nonnull
   @Override
   public JMethodId getMethodId(@Nonnull String name, @Nonnull List<? extends JType> argsType,
@@ -550,7 +549,7 @@
 
   @Nonnull
   public Location getLocation() {
-    return loader.getLocation(this);
+    return location;
   }
 
 }
diff --git a/jack/src/com/android/jack/ir/ast/JEnumLiteral.java b/jack/src/com/android/jack/ir/ast/JEnumLiteral.java
index 12d593f..cd075bc 100644
--- a/jack/src/com/android/jack/ir/ast/JEnumLiteral.java
+++ b/jack/src/com/android/jack/ir/ast/JEnumLiteral.java
@@ -33,7 +33,7 @@
   private static final long serialVersionUID = 1L;
 
   @Nonnull
-  private JFieldId value;
+  private final JFieldId value;
 
   public JEnumLiteral(@Nonnull SourceInfo sourceInfo, @Nonnull JFieldId value) {
     super(sourceInfo);
@@ -69,13 +69,6 @@
     return value;
   }
 
-  /**
-   * Resolve an external reference during AST stitching.
-   */
-  public void resolve(@Nonnull JFieldId newField) {
-    value = newField;
-  }
-
   @Override
   public void visit(@Nonnull JVisitor visitor, @Nonnull TransformRequest transformRequest)
       throws Exception {
diff --git a/jack/src/com/android/jack/ir/ast/JField.java b/jack/src/com/android/jack/ir/ast/JField.java
index 9d95317..31bd627 100644
--- a/jack/src/com/android/jack/ir/ast/JField.java
+++ b/jack/src/com/android/jack/ir/ast/JField.java
@@ -258,10 +258,4 @@
       super.transform(existingNode, newNode, transformation);
     }
   }
-
-  @Override
-  public void updateAnnotations() {
-    annotations.updateAnnotationSet();
-  }
-
 }
diff --git a/jack/src/com/android/jack/ir/ast/JFieldRef.java b/jack/src/com/android/jack/ir/ast/JFieldRef.java
index 0c43e05..c0396e6 100644
--- a/jack/src/com/android/jack/ir/ast/JFieldRef.java
+++ b/jack/src/com/android/jack/ir/ast/JFieldRef.java
@@ -39,7 +39,7 @@
   private JClassOrInterface receiverType;
 
   @Nonnull
-  private JFieldId fieldId;
+  private final JFieldId fieldId;
 
   /**
    * This can only be null if the referenced field is static.
@@ -86,13 +86,6 @@
     return true;
   }
 
-  /**
-   * Resolve an external reference during AST stitching.
-   */
-  public void resolve(@Nonnull JFieldId fieldId) {
-    this.fieldId = fieldId;
-  }
-
   @Override
   public void traverse(@Nonnull JVisitor visitor) {
     if (visitor.visit(this)) {
diff --git a/jack/src/com/android/jack/ir/ast/JInstanceOf.java b/jack/src/com/android/jack/ir/ast/JInstanceOf.java
index a4682ee..6ec1931 100644
--- a/jack/src/com/android/jack/ir/ast/JInstanceOf.java
+++ b/jack/src/com/android/jack/ir/ast/JInstanceOf.java
@@ -33,7 +33,7 @@
   private static final long serialVersionUID = 1L;
 
   private JExpression expr;
-  private JReferenceType testType;
+  private final JReferenceType testType;
 
   public JInstanceOf(SourceInfo info, JReferenceType testType, JExpression expression) {
     super(info);
@@ -59,13 +59,6 @@
     return true;
   }
 
-  /**
-   * Resolve an external reference during AST stitching.
-   */
-  public void resolve(JReferenceType newType) {
-    testType = newType;
-  }
-
   @Override
   public void traverse(@Nonnull JVisitor visitor) {
     if (visitor.visit(this)) {
diff --git a/jack/src/com/android/jack/ir/ast/JMethod.java b/jack/src/com/android/jack/ir/ast/JMethod.java
index f29a99a..42185f8 100644
--- a/jack/src/com/android/jack/ir/ast/JMethod.java
+++ b/jack/src/com/android/jack/ir/ast/JMethod.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.ir.SourceInfo;
 import com.android.jack.load.MethodLoader;
+import com.android.jack.util.NamingTools;
 import com.android.sched.item.Component;
 import com.android.sched.item.Description;
 import com.android.sched.marker.Marker;
@@ -391,11 +392,6 @@
     visitor.visit(this, transformRequest);
   }
 
-  @Override
-  public void updateAnnotations() {
-    annotations.updateAnnotationSet();
-  }
-
   @Nonnull
   public JMethodId getMethodId() {
     return methodId;
@@ -423,4 +419,8 @@
   public JThis getThis() {
     return jThis;
   }
+
+  public static boolean isClinit(@Nonnull JMethod method) {
+    return method.getName().equals(NamingTools.STATIC_INIT_NAME);
+  }
 }
diff --git a/jack/src/com/android/jack/ir/ast/JMethodCall.java b/jack/src/com/android/jack/ir/ast/JMethodCall.java
index 99e2692..7c92419 100644
--- a/jack/src/com/android/jack/ir/ast/JMethodCall.java
+++ b/jack/src/com/android/jack/ir/ast/JMethodCall.java
@@ -56,7 +56,7 @@
   @Nonnull
   private JMethodId methodId;
   @Nonnull
-  private JType returnType;
+  private final JType returnType;
   @Nonnull
   private final DispatchKind dispatchKind;
 
@@ -189,10 +189,6 @@
     return returnType;
   }
 
-  public void resolveType(@Nonnull JType returnType) {
-    this.returnType = returnType;
-  }
-
   public void resolveMethodId(@Nonnull JMethodId methodId) {
     this.methodId = methodId;
   }
@@ -239,11 +235,6 @@
     return methodId.getName();
   }
 
-  public void resolve(@Nonnull JClassOrInterface receiverType, @Nonnull JType returnType) {
-    setReceiverType(receiverType);
-    this.returnType = returnType;
-  }
-
   @Nonnull
   public DispatchKind getDispatchKind() {
     return dispatchKind;
diff --git a/jack/src/com/android/jack/ir/ast/JMethodId.java b/jack/src/com/android/jack/ir/ast/JMethodId.java
index a379cc4..3bead39 100644
--- a/jack/src/com/android/jack/ir/ast/JMethodId.java
+++ b/jack/src/com/android/jack/ir/ast/JMethodId.java
@@ -17,6 +17,7 @@
 package com.android.jack.ir.ast;
 
 import com.android.jack.Jack;
+import com.android.jack.util.NamingTools;
 import com.android.sched.marker.LocalMarkerManager;
 
 import java.io.Serializable;
@@ -48,16 +49,16 @@
   @Nonnull
   private String name;
   @Nonnull
-  private List<JType> paramTypes = new ArrayList<JType>();
+  private final List<JType> paramTypes = new ArrayList<JType>();
   @Nonnull
-  private List<JMethod> methods = new ArrayList<JMethod>();
+  private final List<JMethod> methods = new ArrayList<JMethod>();
 
   @Nonnull
   private final MethodKind methodKind;
 
   public JMethodId(@Nonnull String name, @Nonnull MethodKind kind) {
     assert !(name.contains("(") || name.contains(")"));
-    assert (!("<init>".equals(name) || "<clinit>".equals(name)))
+    assert (!(NamingTools.INIT_NAME.equals(name) || NamingTools.STATIC_INIT_NAME.equals(name)))
         || (kind != MethodKind.INSTANCE_VIRTUAL);
     this.name = name;
     this.methodKind = kind;
@@ -144,14 +145,6 @@
     return paramTypes;
   }
 
-  public void resolve(@Nonnull List<JType> paramTypes, @Nonnull Collection<JMethod> methods) {
-    this.paramTypes = paramTypes;
-    this.methods = new ArrayList<JMethod>();
-    for (JMethod jMethod : methods) {
-      addMethod(jMethod);
-    }
-  }
-
   @Override
   public void setName(@Nonnull String newName) {
     assert !(name.contains("(") || name.contains(")"));
diff --git a/jack/src/com/android/jack/ir/ast/JPackage.java b/jack/src/com/android/jack/ir/ast/JPackage.java
index 5af0b69..a09b06f 100644
--- a/jack/src/com/android/jack/ir/ast/JPackage.java
+++ b/jack/src/com/android/jack/ir/ast/JPackage.java
@@ -23,6 +23,9 @@
 import com.android.sched.item.Description;
 import com.android.sched.scheduler.ScheduleInstance;
 import com.android.sched.transform.TransformRequest;
+import com.android.sched.util.log.stats.Counter;
+import com.android.sched.util.log.stats.CounterImpl;
+import com.android.sched.util.log.stats.StatisticId;
 
 import java.util.ArrayList;
 import java.util.Collection;
@@ -39,6 +42,16 @@
 
   private static final long serialVersionUID = 1L;
 
+  @Nonnull
+  public static final StatisticId<Counter> PACKAGE_CREATION = new StatisticId<Counter>(
+      "jack.package.create", "Created JPackage",
+      CounterImpl.class, Counter.class);
+
+  @Nonnull
+  public static final StatisticId<Counter> PHANTOM_CREATION = new StatisticId<Counter>(
+      "jack.phantom.create", "Created phantom class or interface",
+      CounterImpl.class, Counter.class);
+
   @CheckForNull
   private JPackage enclosingPackage;
 
@@ -69,7 +82,7 @@
   private String name;
 
   @Nonnull
-  private final JProgram program;
+  private final JSession session;
 
   @Nonnull
   private final transient ComposedPackageLoader loader;
@@ -77,14 +90,14 @@
   private boolean isOnPath;
 
   public JPackage(
-      @Nonnull String name, @Nonnull JProgram program, @CheckForNull JPackage enclosingPackage) {
-    this(name, program, enclosingPackage, new ComposedPackageLoader());
+      @Nonnull String name, @Nonnull JSession session, @CheckForNull JPackage enclosingPackage) {
+    this(name, session, enclosingPackage, new ComposedPackageLoader());
   }
 
-  public JPackage(@Nonnull String name, @Nonnull JProgram program,
+  public JPackage(@Nonnull String name, @Nonnull JSession session,
       @CheckForNull JPackage enclosingPackage, @Nonnull ComposedPackageLoader loader) {
     super(SourceOrigin.UNKNOWN);
-    this.program = program;
+    this.session = session;
     this.name = name;
     this.loader = loader;
     if (enclosingPackage != null) {
@@ -93,7 +106,8 @@
       this.enclosingPackage.addPackage(this);
     }
     isOnPath = loader.isOnPath(this);
-   }
+    session.getTracer().getStatistic(PACKAGE_CREATION).incValue();
+  }
 
   public void addType(@Nonnull JDefinedClassOrInterface type) {
     declaredTypes.add(type);
@@ -158,7 +172,7 @@
       return getSubPackage(packageName);
     } catch (JPackageLookupException e) {
       assert !packageName.isEmpty();
-      JPackage newPackage = new JPackage(packageName, program, this);
+      JPackage newPackage = new JPackage(packageName, session, this);
       newPackage.updateParents(this);
       return newPackage;
     }
@@ -198,6 +212,7 @@
       }
       JPhantomClassOrInterface phantom = new JPhantomClassOrInterface(typeName, this);
       phantomTypes.add(phantom);
+      session.getTracer().getStatistic(PHANTOM_CREATION).incValue();
       return phantom;
     }
   }
@@ -219,6 +234,7 @@
     }
     JPhantomClass phantom = new JPhantomClass(typeName, this);
     phantomClasses.add(phantom);
+    session.getTracer().getStatistic(PHANTOM_CREATION).incValue();
     return phantom;
   }
 
@@ -239,6 +255,7 @@
     }
     JPhantomEnum phantom = new JPhantomEnum(typeName, this);
     phantomEnums.add(phantom);
+    session.getTracer().getStatistic(PHANTOM_CREATION).incValue();
     return phantom;
   }
 
@@ -259,6 +276,7 @@
     }
     JPhantomInterface phantom = new JPhantomInterface(typeName, this);
     phantomInterfaces.add(phantom);
+    session.getTracer().getStatistic(PHANTOM_CREATION).incValue();
     return phantom;
   }
 
@@ -279,6 +297,7 @@
     }
     JPhantomAnnotation phantom = new JPhantomAnnotation(typeName, this);
     phantomAnnotations.add(phantom);
+    session.getTracer().getStatistic(PHANTOM_CREATION).incValue();
     return phantom;
   }
 
@@ -292,8 +311,8 @@
   }
 
   @Nonnull
-  public JProgram getProgram() {
-    return program;
+  public JSession getSession() {
+    return session;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/ir/ast/JPrimitiveType.java b/jack/src/com/android/jack/ir/ast/JPrimitiveType.java
index 69fec7e..93a522e 100644
--- a/jack/src/com/android/jack/ir/ast/JPrimitiveType.java
+++ b/jack/src/com/android/jack/ir/ast/JPrimitiveType.java
@@ -30,7 +30,6 @@
 import com.android.sched.scheduler.ScheduleInstance;
 import com.android.sched.transform.TransformRequest;
 
-import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
@@ -71,9 +70,6 @@
   @Nonnull
   protected final String name;
 
-  @CheckForNull
-  private JArrayType array;
-
   private JPrimitiveType(@Nonnull String name, @Nonnull String signatureName) {
     super(SourceOrigin.UNKNOWN);
     this.name = name;
@@ -156,11 +152,11 @@
 
   @Nonnull
   public final JClass getWrapperType() {
-    return Jack.getProgram().getPhantomLookup().getClass(getWrapperCommonType());
+    return Jack.getSession().getPhantomLookup().getClass(getWrapperCommonType());
   }
 
   public boolean isWrapperType(@Nonnull JType candidate) {
-    JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+    JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
     return lookup.getClass(getWrapperCommonType()) == candidate
         || lookup.getType(getWrapperCommonType()) == candidate;
   }
@@ -187,11 +183,7 @@
   @Override
   @Nonnull
   public JArrayType getArray() {
-    if (array == null) {
-      array = new JArrayType(this);
-    }
-    assert array != null;
-    return array;
+    return Jack.getSession().getArrayOf(getPrimitiveTypeEnum());
   }
 
   @Nonnull
@@ -540,11 +532,12 @@
     CommonType getWrapperCommonType() {
       return CommonTypes.JAVA_LANG_VOID;
     }
-  }
 
-  static void reset() {
-    for (JPrimitiveTypeEnum typeEnum : JPrimitiveTypeEnum.values()) {
-      typeEnum.type.array = null;
+    @Override
+    @Nonnull
+    public JArrayType getArray() {
+      // Array of void does not exist.
+      throw new AssertionError();
     }
   }
 }
diff --git a/jack/src/com/android/jack/ir/ast/JReferenceTypeCommon.java b/jack/src/com/android/jack/ir/ast/JReferenceTypeCommon.java
index 3b7890d..0eaf0b7 100644
--- a/jack/src/com/android/jack/ir/ast/JReferenceTypeCommon.java
+++ b/jack/src/com/android/jack/ir/ast/JReferenceTypeCommon.java
@@ -68,8 +68,8 @@
 
   protected boolean isTrivialCast(@Nonnull JReferenceType castTo) {
     if (this == castTo
-        || castTo == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT)
-        || castTo == Jack.getProgram().getPhantomLookup().getType(CommonTypes.JAVA_LANG_OBJECT)) {
+        || castTo == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT)
+        || castTo == Jack.getSession().getPhantomLookup().getType(CommonTypes.JAVA_LANG_OBJECT)) {
       return true;
     }
 
diff --git a/jack/src/com/android/jack/ir/ast/JProgram.java b/jack/src/com/android/jack/ir/ast/JSession.java
similarity index 75%
rename from jack/src/com/android/jack/ir/ast/JProgram.java
rename to jack/src/com/android/jack/ir/ast/JSession.java
index 83f455e..61801ed 100644
--- a/jack/src/com/android/jack/ir/ast/JProgram.java
+++ b/jack/src/com/android/jack/ir/ast/JSession.java
@@ -16,17 +16,17 @@
 package com.android.jack.ir.ast;
 
 
-import com.android.jack.Jack;
-import com.android.jack.ir.SourceInfo;
 import com.android.jack.ir.SourceOrigin;
+import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
 import com.android.jack.load.ComposedPackageLoader;
-import com.android.jack.lookup.CommonTypes;
 import com.android.jack.lookup.JNodeLookup;
 import com.android.jack.lookup.JPhantomLookup;
 import com.android.sched.item.Component;
 import com.android.sched.item.Description;
 import com.android.sched.scheduler.ScheduleInstance;
 import com.android.sched.transform.TransformRequest;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -35,23 +35,13 @@
 import javax.annotation.Nonnull;
 
 /**
- * Root for the AST representing an entire Java program.
+ * Storage for information concerning one compilation.
  */
-@Description("Representing an entire Java program")
-public class JProgram extends JNode {
+@Description("Representing a compilation")
+public class JSession extends JNode {
 
   private static final long serialVersionUID = 1L;
 
-  public static final String STATIC_INIT_NAME = "<clinit>";
-
-  public static final String INIT_NAME = "<init>";
-
-  public static boolean isClinit(JMethod method) {
-    return method.getName().equals(STATIC_INIT_NAME);
-  }
-
-  public final List<JDefinedClass> codeGenTypes = new ArrayList<JDefinedClass>();
-
   @Nonnull
   private final List<JDefinedClassOrInterface> typesToEmit =
       new ArrayList<JDefinedClassOrInterface>();
@@ -65,9 +55,14 @@
   @Nonnull
   private final transient JPhantomLookup phantomLookup;
 
-  public JProgram() {
-    super(SourceOrigin.create(0, 0, JProgram.class.getName()));
-    JPrimitiveType.reset();
+  @Nonnull
+  private final JArrayType[] primitiveArrays = new JArrayType[JPrimitiveTypeEnum.values().length];
+
+  @Nonnull
+  private final transient Tracer tracer = TracerFactory.getTracer();
+
+  public JSession() {
+    super(SourceOrigin.create(0, 0, JSession.class.getName()));
     topLevelPackage = new JPackage("", this, null);
     topLevelPackage.updateParents(this);
     lookup = new JNodeLookup(topLevelPackage);
@@ -87,6 +82,11 @@
     return lookup;
   }
 
+  @Nonnull
+  public Tracer getTracer() {
+    return tracer;
+  }
+
   /**
    * @return the phantom lookup
    */
@@ -111,19 +111,6 @@
     return topLevelPackage;
   }
 
-  public JStringLiteral getLiteralString(SourceInfo sourceInfo, char[] s) {
-    return getLiteralString(sourceInfo, String.valueOf(s));
-  }
-
-  public JStringLiteral getLiteralString(SourceInfo sourceInfo, String s) {
-    return new JStringLiteral(sourceInfo, s);
-  }
-
-  public boolean isJavaLangString(JType type) {
-    JClass jls = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
-    return type == jls;
-  }
-
   @Override
   public void traverse(@Nonnull JVisitor visitor) {
     if (visitor.visit(this)) {
@@ -156,4 +143,13 @@
       throws Exception {
     visitor.visit(this, transformRequest);
   }
+
+  @Nonnull
+  synchronized JArrayType getArrayOf(JPrimitiveTypeEnum primitive) {
+    assert primitive != JPrimitiveTypeEnum.VOID;
+    if (primitiveArrays[primitive.ordinal()] == null) {
+      primitiveArrays[primitive.ordinal()] = new JArrayType(primitive.getType());
+    }
+    return primitiveArrays[primitive.ordinal()];
+  }
 }
diff --git a/jack/src/com/android/jack/ir/ast/JVariable.java b/jack/src/com/android/jack/ir/ast/JVariable.java
index caa78ba..572a977 100644
--- a/jack/src/com/android/jack/ir/ast/JVariable.java
+++ b/jack/src/com/android/jack/ir/ast/JVariable.java
@@ -121,9 +121,4 @@
       super.transform(existingNode, newNode, transformation);
     }
   }
-
-  @Override
-  public void updateAnnotations() {
-    annotations.updateAnnotationSet();
-  }
 }
diff --git a/jack/src/com/android/jack/ir/ast/JVisitor.java b/jack/src/com/android/jack/ir/ast/JVisitor.java
index 5514b91..8534e21 100644
--- a/jack/src/com/android/jack/ir/ast/JVisitor.java
+++ b/jack/src/com/android/jack/ir/ast/JVisitor.java
@@ -374,7 +374,7 @@
     endVisit((JType) x);
   }
 
-  public void endVisit(@Nonnull JProgram x) {
+  public void endVisit(@Nonnull JSession x) {
     endVisit((JNode) x);
   }
 
@@ -750,7 +750,7 @@
     return visit((JType) x);
   }
 
-  public boolean visit(@Nonnull JProgram x) {
+  public boolean visit(@Nonnull JSession x) {
     return visit((JNode) x);
   }
 
@@ -1194,7 +1194,7 @@
     visit((JType) x, transformRequest);
   }
 
-  public void visit(@Nonnull JProgram x, @Nonnull TransformRequest transformRequest)
+  public void visit(@Nonnull JSession x, @Nonnull TransformRequest transformRequest)
       throws Exception {
     visit((JNode) x, transformRequest);
   }
diff --git a/jack/src/com/android/jack/ir/impl/EcjSourceTypeLoader.java b/jack/src/com/android/jack/ir/impl/EcjSourceTypeLoader.java
index 172e9b6..b944f6c 100644
--- a/jack/src/com/android/jack/ir/impl/EcjSourceTypeLoader.java
+++ b/jack/src/com/android/jack/ir/impl/EcjSourceTypeLoader.java
@@ -34,7 +34,6 @@
 import com.android.jack.lookup.JLookup;
 import com.android.jack.util.NamingTools;
 import com.android.sched.marker.Marker;
-import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.Location;
 
 import org.eclipse.jdt.core.compiler.CharOperation;
@@ -46,7 +45,6 @@
 import org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding;
 import org.eclipse.jdt.internal.compiler.lookup.SourceTypeBinding;
 
-import java.io.File;
 import java.lang.ref.WeakReference;
 import java.util.List;
 
@@ -82,7 +80,7 @@
   @Nonnull
   private final WeakReference<SourceTypeBinding> bindingRef;
 
-  @Nonnull
+  @CheckForNull
   private final WeakReference<TypeDeclaration> declarationRef;
 
   @Nonnull
@@ -91,10 +89,14 @@
   private int loadStatus = 0;
 
   @Nonnull
+  private final Location location;
+
+  @Nonnull
   public static JDefinedClassOrInterface createType(@Nonnull ReferenceMapper refMap,
       @Nonnull JPackage enclosingPackage, @Nonnull SourceTypeBinding binding,
-      @CheckForNull TypeDeclaration typeDeclaration) {
-    EcjSourceTypeLoader loader = new EcjSourceTypeLoader(refMap, binding, typeDeclaration);
+      @CheckForNull TypeDeclaration typeDeclaration, Location location) {
+    EcjSourceTypeLoader loader = new EcjSourceTypeLoader(refMap, binding, typeDeclaration,
+        location);
     CudInfo cuInfo = new CudInfo(binding.scope.referenceCompilationUnit());
     SourceInfo info = ReferenceMapper.makeSourceInfo(cuInfo, binding.scope.referenceContext);
     String name;
@@ -134,24 +136,27 @@
     } else {
       throw new AssertionError("ReferenceBinding is not a class, interface, or enum.");
     }
-    type.updateParents(enclosingPackage.getProgram());
+    type.updateParents(enclosingPackage.getSession());
     return type;
   }
 
 
   EcjSourceTypeLoader(@Nonnull ReferenceMapper refMap, @Nonnull SourceTypeBinding binding,
-      @CheckForNull TypeDeclaration typeDeclaration) {
+      @CheckForNull TypeDeclaration typeDeclaration, @Nonnull Location location) {
     this.refMap = new WeakReference<ReferenceMapper>(refMap);
     this.bindingRef = new WeakReference<SourceTypeBinding>(binding);
-    this.declarationRef = new WeakReference<TypeDeclaration>(typeDeclaration);
+    if (typeDeclaration != null) {
+      this.declarationRef = new WeakReference<TypeDeclaration>(typeDeclaration);
+    } else {
+      this.declarationRef = null;
+    }
+    this.location = location;
   }
 
   @Override
   @Nonnull
   public Location getLocation(@Nonnull JDefinedClassOrInterface loaded) {
-    TypeDeclaration decl = declarationRef.get();
-    assert decl != null;
-    return new FileLocation(new File(new String(decl.compilationResult.fileName)));
+    return location;
   }
 
 
@@ -196,7 +201,7 @@
         return;
       }
       SourceTypeBinding binding = getBinding(loaded);
-      JLookup lookup = loaded.getEnclosingPackage().getProgram().getPhantomLookup();
+      JLookup lookup = loaded.getEnclosingPackage().getSession().getPhantomLookup();
       if (loaded instanceof JDefinedClass) {
         ReferenceBinding superclass = binding.superclass();
         if (superclass != null) {
@@ -278,11 +283,14 @@
       if (isLoaded(Scope.INNERS)) {
         return;
       }
-      TypeDeclaration declaration = declarationRef.get();
-      if (declaration != null && declaration.memberTypes != null) {
-        ReferenceMapper referenceMapper = refMap.get();
-        for (TypeDeclaration memberType : declaration.memberTypes) {
-          ((JDefinedClassOrInterface) referenceMapper.get(memberType.binding)).getEnclosingType();
+      if (declarationRef != null) {
+        TypeDeclaration declaration = declarationRef.get();
+        assert declaration != null;
+        if (declaration.memberTypes != null) {
+          ReferenceMapper referenceMapper = refMap.get();
+          for (TypeDeclaration memberType : declaration.memberTypes) {
+            ((JDefinedClassOrInterface) referenceMapper.get(memberType.binding)).getEnclosingType();
+          }
         }
       }
       markLoaded(Scope.INNERS);
@@ -310,7 +318,7 @@
         return;
       }
       SourceTypeBinding binding = getBinding(loaded);
-      JLookup lookup = loaded.getEnclosingPackage().getProgram().getPhantomLookup();
+      JLookup lookup = loaded.getEnclosingPackage().getSession().getPhantomLookup();
       for (MethodBinding methodBinding : binding.methods()) {
         load(lookup, loaded, methodBinding);
       }
@@ -331,7 +339,7 @@
         return;
       }
       SourceTypeBinding binding = getBinding(loaded);
-      JLookup lookup = loaded.getEnclosingPackage().getProgram().getPhantomLookup();
+      JLookup lookup = loaded.getEnclosingPackage().getSession().getPhantomLookup();
       for (FieldBinding fieldBinding : binding.fields()) {
         load(lookup, loaded, fieldBinding);
       }
diff --git a/jack/src/com/android/jack/ir/impl/GwtAstBuilder.java b/jack/src/com/android/jack/ir/impl/GwtAstBuilder.java
index 351b7c8..a54416c 100644
--- a/jack/src/com/android/jack/ir/impl/GwtAstBuilder.java
+++ b/jack/src/com/android/jack/ir/impl/GwtAstBuilder.java
@@ -98,9 +98,9 @@
 import com.android.jack.ir.ast.JPrefixOperation;
 import com.android.jack.ir.ast.JPrimitiveType;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReferenceType;
 import com.android.jack.ir.ast.JReturnStatement;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JStringLiteral;
@@ -119,6 +119,7 @@
 import com.android.jack.ir.ast.marker.OriginalTypeInfo;
 import com.android.jack.ir.ast.marker.ThisRefTypeInfo;
 import com.android.jack.lookup.CommonTypes;
+import com.android.jack.util.NamingTools;
 
 import org.eclipse.jdt.core.compiler.CharOperation;
 import org.eclipse.jdt.internal.compiler.ASTVisitor;
@@ -239,7 +240,7 @@
 
 /**
  * Constructs a GWT Java AST from a single isolated compilation unit. The AST is
- * not associated with any {@link com.android.jack.ir.ast.JProgram} and will
+ * not associated with any {@link com.android.jack.ir.ast.JSession} and will
  * contain unresolved references.
  */
 public class GwtAstBuilder {
@@ -2248,7 +2249,8 @@
       JNewArray newExpr = JNewArray.createWithInits(info, enumArrayType, initializers);
       JFieldRef valuesRef = new JFieldRef(info, null, valuesField.getId(), type);
       JAsgOperation assignValues = new JAsgOperation(info, valuesRef, newExpr);
-      JMethod clinit = type.getMethod(JProgram.STATIC_INIT_NAME, JPrimitiveTypeEnum.VOID.getType());
+      JMethod clinit = type.getMethod(NamingTools.STATIC_INIT_NAME,
+          JPrimitiveTypeEnum.VOID.getType());
       JAbstractMethodBody body = clinit.getBody();
       assert body instanceof JMethodBody;
       JBlock clinitBlock = ((JMethodBody) body).getBlock();
@@ -2585,7 +2587,8 @@
       JMethod initMeth;
       if (x.isStatic()) {
         initMeth =
-            curClass.type.getMethod(JProgram.STATIC_INIT_NAME, JPrimitiveTypeEnum.VOID.getType());
+            curClass.type.getMethod(NamingTools.STATIC_INIT_NAME,
+                JPrimitiveTypeEnum.VOID.getType());
       } else {
         initMeth = curClass.type.getMethod(INIT_METHOD_NAME, JPrimitiveTypeEnum.VOID.getType());
       }
@@ -3185,9 +3188,9 @@
   private final LookupEnvironment lookupEnvironment;
 
   public GwtAstBuilder(@Nonnull LookupEnvironment lookupEnvironment,
-      @Nonnull JProgram program) {
+      @Nonnull JSession session) {
     this.lookupEnvironment = lookupEnvironment;
-    typeMap = new ReferenceMapper(program.getLookup(), lookupEnvironment);
+    typeMap = new ReferenceMapper(session.getLookup(), lookupEnvironment);
   }
 
   /**
@@ -3457,7 +3460,7 @@
     int modifier = JModifier.STATIC | JModifier.STATIC_INIT;
     JMethod method =
         new JMethod(info,
-            new JMethodId(JProgram.STATIC_INIT_NAME, MethodKind.STATIC),
+            new JMethodId(NamingTools.STATIC_INIT_NAME, MethodKind.STATIC),
             enclosingType,
             JPrimitiveTypeEnum.VOID.getType(),
             modifier);
diff --git a/jack/src/com/android/jack/ir/impl/SourceGenerationVisitor.java b/jack/src/com/android/jack/ir/impl/SourceGenerationVisitor.java
index 4e19899..e9c4cf5 100644
--- a/jack/src/com/android/jack/ir/impl/SourceGenerationVisitor.java
+++ b/jack/src/com/android/jack/ir/impl/SourceGenerationVisitor.java
@@ -22,7 +22,7 @@
 import com.android.jack.ir.ast.JField;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.util.TextOutput;
 
 import javax.annotation.Nonnull;
@@ -61,7 +61,7 @@
       newline();
     }
     for (JMethod it : x.getMethods()) {
-      if (JProgram.isClinit(it)) {
+      if (JMethod.isClinit(it)) {
         // Suppress empty clinit.
         JMethodBody body = (JMethodBody) it.getBody();
         assert body != null;
@@ -100,7 +100,7 @@
   }
 
   @Override
-  public boolean visit(@Nonnull JProgram x) {
+  public boolean visit(@Nonnull JSession x) {
     for (int i = 0; i < x.getTypesToEmit().size(); ++i) {
       JDefinedClassOrInterface type = x.getTypesToEmit().get(i);
       if (!type.isExternal()) {
diff --git a/jack/src/com/android/jack/ir/impl/ToStringGenerationVisitor.java b/jack/src/com/android/jack/ir/impl/ToStringGenerationVisitor.java
index 8c23276..307c81b 100644
--- a/jack/src/com/android/jack/ir/impl/ToStringGenerationVisitor.java
+++ b/jack/src/com/android/jack/ir/impl/ToStringGenerationVisitor.java
@@ -92,10 +92,10 @@
 import com.android.jack.ir.ast.JPostfixOperation;
 import com.android.jack.ir.ast.JPrefixOperation;
 import com.android.jack.ir.ast.JPrimitiveType;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReferenceType;
 import com.android.jack.ir.ast.JReinterpretCastOperation;
 import com.android.jack.ir.ast.JReturnStatement;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JSwitchStatement;
@@ -305,7 +305,7 @@
   @Override
   public boolean visit(@Nonnull JCatchBlock x) {
     JLocal catchVar = x.getCatchVar();
-    if (catchVar.getType() == Jack.getProgram().getPhantomLookup()
+    if (catchVar.getType() == Jack.getSession().getPhantomLookup()
         .getClass(CommonTypes.JAVA_LANG_OBJECT)) {
       print(CHARS_FINALLY);
     } else {
@@ -954,8 +954,8 @@
   }
 
   @Override
-  public boolean visit(@Nonnull JProgram x) {
-    print("<JProgram>");
+  public boolean visit(@Nonnull JSession x) {
+    print("<JSession>");
     return false;
   }
 
diff --git a/jack/src/com/android/jack/jayce/FullPackageLoader.java b/jack/src/com/android/jack/jayce/FullPackageLoader.java
index 0e121f2..00ffec0 100644
--- a/jack/src/com/android/jack/jayce/FullPackageLoader.java
+++ b/jack/src/com/android/jack/jayce/FullPackageLoader.java
@@ -17,15 +17,15 @@
 package com.android.jack.jayce;
 
 import com.android.jack.lookup.JPhantomLookup;
-import com.android.jack.vfs.VDir;
 import com.android.sched.util.codec.ImplementationName;
+import com.android.sched.vfs.InputVDir;
 
 import javax.annotation.Nonnull;
 
 @ImplementationName(iface = JaycePackageLoader.class, name = "full")
 class FullPackageLoader extends JaycePackageLoader {
 
-  public FullPackageLoader(@Nonnull VDir dir, @Nonnull JPhantomLookup lookup) {
+  public FullPackageLoader(@Nonnull InputVDir dir, @Nonnull JPhantomLookup lookup) {
     super(dir, lookup, NodeLevel.FULL);
   }
 }
diff --git a/jack/src/com/android/jack/jayce/JayceClassOrInterfaceLoader.java b/jack/src/com/android/jack/jayce/JayceClassOrInterfaceLoader.java
index abb21bf..af6d6d6 100644
--- a/jack/src/com/android/jack/jayce/JayceClassOrInterfaceLoader.java
+++ b/jack/src/com/android/jack/jayce/JayceClassOrInterfaceLoader.java
@@ -22,20 +22,30 @@
 import com.android.jack.ir.ast.JDefinedAnnotation;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.load.AbtractClassOrInterfaceLoader;
 import com.android.jack.lookup.JPhantomLookup;
 import com.android.jack.util.NamingTools;
-import com.android.jack.vfs.VFile;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.log.LoggerFactory;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
+import com.android.sched.util.log.stats.Counter;
+import com.android.sched.util.log.stats.CounterImpl;
+import com.android.sched.util.log.stats.Percent;
+import com.android.sched.util.log.stats.PercentImpl;
+import com.android.sched.util.log.stats.StatisticId;
+import com.android.sched.vfs.InputVFile;
 
+import java.io.BufferedInputStream;
 import java.io.IOException;
 import java.io.InputStream;
+import java.lang.ref.Reference;
 import java.lang.ref.SoftReference;
 import java.util.logging.Level;
 import java.util.logging.Logger;
 
+import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
 
 /**
@@ -43,13 +53,22 @@
  */
 public class JayceClassOrInterfaceLoader extends AbtractClassOrInterfaceLoader {
   @Nonnull
+  private static final StatisticId<Percent> NNODE_RELOAD = new StatisticId<
+      Percent>("jayce.reload", "Jayce file reload versus total jayce file load",
+          PercentImpl.class, Percent.class);
+  @Nonnull
+  private static final StatisticId<Counter> STRUCTURE_LOAD = new StatisticId<Counter>(
+      "jayce.structure.load", "NDeclaredType structure loaded in a JNode",
+          CounterImpl.class, Counter.class);
+
+  @Nonnull
   private final Logger logger = LoggerFactory.getLogger();
 
   @Nonnull
-  private final VFile source;
+  private final InputVFile source;
 
   @Nonnull
-  private SoftReference<DeclaredTypeNode> nnode;
+  private Reference<DeclaredTypeNode> nnode;
 
   private boolean structureLoaded = false;
 
@@ -59,15 +78,21 @@
   @Nonnull
   private final NodeLevel defaultLoadLevel;
 
+  @Nonnegative
+  private int loadCount = 0;
+
   @Nonnull
-  public static JDefinedClassOrInterface load(@Nonnull VFile source, @Nonnull JProgram program,
+  final Tracer tracer = TracerFactory.getTracer();
+
+  @Nonnull
+  public static JDefinedClassOrInterface load(@Nonnull InputVFile source, @Nonnull JSession session,
       @Nonnull NodeLevel maxLevel)
       throws JayceFormatException, IOException {
-    return new JayceClassOrInterfaceLoader(source, program.getPhantomLookup(),
-        maxLevel).create(program);
+    return new JayceClassOrInterfaceLoader(source, session.getPhantomLookup(),
+        maxLevel).create(session);
   }
 
-  JayceClassOrInterfaceLoader(@Nonnull VFile source, @Nonnull JPhantomLookup lookup,
+  JayceClassOrInterfaceLoader(@Nonnull InputVFile source, @Nonnull JPhantomLookup lookup,
       @Nonnull NodeLevel defaultLoadLevel) {
     this.source = source;
     this.lookup = lookup;
@@ -113,20 +138,20 @@
           + type.getSignature() + "' while expecting '" + expectedSignature + "'");
     }
     JDefinedClassOrInterface jType = type.create(enclosingPackage, this);
-    jType.updateParents(enclosingPackage.getProgram());
+    jType.updateParents(enclosingPackage.getSession());
     return jType;
   }
 
   @Nonnull
-  private JDefinedClassOrInterface create(@Nonnull JProgram program)
+  private JDefinedClassOrInterface create(@Nonnull JSession session)
       throws JayceFormatException, IOException {
 
     DeclaredTypeNode type = getNNode(NodeLevel.TYPES);
     String packageQualifiedName = NamingTools.getPackageNameFromBinaryName(
         NamingTools.getClassBinaryNameFromDescriptor(type.getSignature()));
-    JPackage pack = program.getLookup().getOrCreatePackage(packageQualifiedName);
+    JPackage pack = session.getLookup().getOrCreatePackage(packageQualifiedName);
     JDefinedClassOrInterface jType = type.create(pack, this);
-    jType.updateParents(program);
+    jType.updateParents(session);
     return jType;
   }
 
@@ -134,7 +159,7 @@
   DeclaredTypeNode getNNode(@Nonnull NodeLevel minimumLevel) throws IOException {
     DeclaredTypeNode type = nnode.get();
     if (type == null || !type.getLevel().keep(minimumLevel)) {
-      InputStream in = source.openRead();
+      InputStream in = new BufferedInputStream(source.openRead());
       try {
         JayceReader reader = new JayceReader(in);
         NodeLevel loadLevel = defaultLoadLevel;
@@ -150,6 +175,8 @@
           logger.log(Level.WARNING, "Failed to close input stream on '" + source + "'", e);
         }
       }
+      tracer.getStatistic(NNODE_RELOAD).add(loadCount > 0);
+      loadCount++;
     }
     return type;
   }
@@ -169,7 +196,7 @@
         type.updateToStructure(loaded, this);
         ParentSetter parentSetter = new ParentSetter();
         parentSetter.accept(loaded);
-        structureLoaded = true;
+        tracer.getStatistic(STRUCTURE_LOAD).incValue();
       }
     }
   }
diff --git a/jack/src/com/android/jack/jayce/JayceMethodLoader.java b/jack/src/com/android/jack/jayce/JayceMethodLoader.java
index 0cb7119..8c617a8 100644
--- a/jack/src/com/android/jack/jayce/JayceMethodLoader.java
+++ b/jack/src/com/android/jack/jayce/JayceMethodLoader.java
@@ -22,6 +22,9 @@
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.load.AbstractMethodLoader;
 import com.android.sched.util.config.Location;
+import com.android.sched.util.log.stats.Counter;
+import com.android.sched.util.log.stats.CounterImpl;
+import com.android.sched.util.log.stats.StatisticId;
 
 import java.io.IOException;
 import java.lang.ref.SoftReference;
@@ -32,6 +35,10 @@
  * A loader for method loaded from a jack file.
  */
 public class JayceMethodLoader extends AbstractMethodLoader {
+  @Nonnull
+  private static final StatisticId<Counter> BODY_LOAD_COUNT = new StatisticId<Counter>(
+      "jayce.body.load", "Body loaded from a NNode in a JNode",
+          CounterImpl.class, Counter.class);
 
   @Nonnull
   private final JayceClassOrInterfaceLoader enclosingClassLoader;
@@ -59,6 +66,7 @@
         body.updateParents(loaded);
       }
       isLoaded = true;
+      enclosingClassLoader.tracer.getStatistic(BODY_LOAD_COUNT).incValue();
     }
   }
 
diff --git a/jack/src/com/android/jack/jayce/JaycePackageLoader.java b/jack/src/com/android/jack/jayce/JaycePackageLoader.java
index 6b7e00b..8d88afd 100644
--- a/jack/src/com/android/jack/jayce/JaycePackageLoader.java
+++ b/jack/src/com/android/jack/jayce/JaycePackageLoader.java
@@ -26,10 +26,10 @@
 import com.android.jack.load.ComposablePackageLoader;
 import com.android.jack.lookup.JLookupException;
 import com.android.jack.lookup.JPhantomLookup;
-import com.android.jack.vfs.VDir;
-import com.android.jack.vfs.VElement;
-import com.android.jack.vfs.VFile;
 import com.android.sched.util.config.Location;
+import com.android.sched.vfs.InputVDir;
+import com.android.sched.vfs.InputVFile;
+import com.android.sched.vfs.VElement;
 
 import java.io.IOException;
 import java.util.ArrayList;
@@ -43,16 +43,14 @@
  */
 public class JaycePackageLoader implements ComposablePackageLoader {
 
-  private static final int JACK_EXTENSION_LENGTH = JayceFileImporter.JAYCE_FILE_EXTENSION.length();
-
   @Nonnull
-  private final VDir dir;
+  private final InputVDir dir;
   private final JPhantomLookup lookup;
 
   @Nonnull
   private final NodeLevel defaultLoadLevel;
 
-  JaycePackageLoader(@Nonnull VDir dir, @Nonnull JPhantomLookup lookup,
+  JaycePackageLoader(@Nonnull InputVDir dir, @Nonnull JPhantomLookup lookup,
       @Nonnull NodeLevel defaultLoadLevel) {
     this.dir = dir;
     this.lookup = lookup;
@@ -64,9 +62,9 @@
   public JDefinedClassOrInterface loadClassOrInterface(
       @Nonnull JPackage loading, @Nonnull String simpleName) throws JLookupException {
     for (VElement sub : dir.list()) {
-      if (sub instanceof VFile && isJackFileNameOf(sub.getName(), simpleName)) {
+      if (sub instanceof InputVFile && isJackFileNameOf(sub.getName(), simpleName)) {
         try {
-          return new JayceClassOrInterfaceLoader((VFile) sub, lookup, defaultLoadLevel)
+          return new JayceClassOrInterfaceLoader((InputVFile) sub, lookup, defaultLoadLevel)
             .loadClassOrInterface(loading, simpleName);
         } catch (IOException e) {
           throw new JackIOException("Failed to load class '" + simpleName + "' in package '"
@@ -83,7 +81,7 @@
     List<String> subs = new ArrayList<String>();
     for (VElement sub : dir.list()) {
       String fileName = sub.getName();
-      if (sub instanceof VFile && isJackFileName(fileName)) {
+      if (sub instanceof InputVFile && JayceFileImporter.isJackFileName(fileName)) {
         subs.add(fileName.substring(0, fileName.length() - 5));
       }
     }
@@ -94,11 +92,11 @@
   @Override
   public ComposablePackageLoader getLoaderForSubPackage(@Nonnull JPackage loading,
       @Nonnull String simpleName) {
-    for (VElement sub : dir.list()) {
-      if (sub instanceof VDir && sub.getName().equals(simpleName)) {
-        return new JaycePackageLoader((VDir) sub, lookup, defaultLoadLevel);
+      for (VElement sub : dir.list()) {
+        if (sub instanceof InputVDir && sub.getName().equals(simpleName)) {
+          return new JaycePackageLoader((InputVDir) sub, lookup, defaultLoadLevel);
+        }
       }
-    }
     throw new JPackageLookupException(simpleName, loading);
   }
 
@@ -107,7 +105,7 @@
   public Collection<String> getSubPackageNames(@Nonnull JPackage loading) {
     List<String> subs = new ArrayList<String>();
     for (VElement sub : dir.list()) {
-      if (sub instanceof VDir) {
+      if (sub instanceof InputVDir) {
         subs.add(sub.getName());
       }
     }
@@ -121,21 +119,14 @@
   }
 
   private boolean isJackFileNameOf(@Nonnull String fileName, @Nonnull String typeName) {
-    return (fileName.length() >  JACK_EXTENSION_LENGTH)
-        && (fileName.substring(0, fileName.length() - JACK_EXTENSION_LENGTH).equals(typeName))
-        && (fileName.substring(fileName.length() - JACK_EXTENSION_LENGTH).equalsIgnoreCase(
-            JayceFileImporter.JAYCE_FILE_EXTENSION));
-  }
-
-  private boolean isJackFileName(@Nonnull String name) {
-    return (name.length() >  JACK_EXTENSION_LENGTH)
-        && (name.substring(name.length() - JACK_EXTENSION_LENGTH).equalsIgnoreCase(
-            JayceFileImporter.JAYCE_FILE_EXTENSION));
+    return (fileName.length() > JayceFileImporter.JACK_EXTENSION_LENGTH) && (fileName.substring(0,
+        fileName.length() - JayceFileImporter.JACK_EXTENSION_LENGTH).equals(typeName)) && (fileName
+        .substring(fileName.length() - JayceFileImporter.JACK_EXTENSION_LENGTH).equalsIgnoreCase(
+        JayceFileImporter.JAYCE_FILE_EXTENSION));
   }
 
   @Override
   public boolean isOnPath(@Nonnull JPackage loaded) {
     return true;
   }
-
 }
diff --git a/jack/src/com/android/jack/jayce/LoadIOException.java b/jack/src/com/android/jack/jayce/LoadIOException.java
index 4e1acee..53ac61a 100644
--- a/jack/src/com/android/jack/jayce/LoadIOException.java
+++ b/jack/src/com/android/jack/jayce/LoadIOException.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.jayce;
 
 import com.android.jack.Jack;
diff --git a/jack/src/com/android/jack/jayce/StructurePackageLoader.java b/jack/src/com/android/jack/jayce/StructurePackageLoader.java
index ecb7fb0..83a2b87 100644
--- a/jack/src/com/android/jack/jayce/StructurePackageLoader.java
+++ b/jack/src/com/android/jack/jayce/StructurePackageLoader.java
@@ -17,15 +17,15 @@
 package com.android.jack.jayce;
 
 import com.android.jack.lookup.JPhantomLookup;
-import com.android.jack.vfs.VDir;
 import com.android.sched.util.codec.ImplementationName;
+import com.android.sched.vfs.InputVDir;
 
 import javax.annotation.Nonnull;
 
 @ImplementationName(iface = JaycePackageLoader.class, name = "structure")
 class StructurePackageLoader extends JaycePackageLoader {
 
-  public StructurePackageLoader(@Nonnull VDir dir, @Nonnull JPhantomLookup lookup) {
+  public StructurePackageLoader(@Nonnull InputVDir dir, @Nonnull JPhantomLookup lookup) {
     super(dir, lookup, NodeLevel.STRUCTURE);
   }
 }
diff --git a/jack/src/com/android/jack/jayce/v0002/NodeFactory.java b/jack/src/com/android/jack/jayce/v0002/NodeFactory.java
index 6740092..d340c54 100644
--- a/jack/src/com/android/jack/jayce/v0002/NodeFactory.java
+++ b/jack/src/com/android/jack/jayce/v0002/NodeFactory.java
@@ -112,9 +112,9 @@
 import com.android.jack.ir.ast.JPrefixIncOperation;
 import com.android.jack.ir.ast.JPrefixNegOperation;
 import com.android.jack.ir.ast.JPrefixNotOperation;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReinterpretCastOperation;
 import com.android.jack.ir.ast.JReturnStatement;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShlOperation;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JShrOperation;
@@ -671,7 +671,7 @@
     }
 
     @Override
-    public boolean visit(@Nonnull JProgram x) {
+    public boolean visit(@Nonnull JSession x) {
       newNode = new NProgram();
       return false;
     }
diff --git a/jack/src/com/android/jack/jayce/v0002/io/ExportSession.java b/jack/src/com/android/jack/jayce/v0002/io/ExportSession.java
index 93ae5ca..b37bfda 100644
--- a/jack/src/com/android/jack/jayce/v0002/io/ExportSession.java
+++ b/jack/src/com/android/jack/jayce/v0002/io/ExportSession.java
@@ -31,7 +31,7 @@
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JParameter;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.MethodKind;
 import com.android.jack.ir.formatter.TypeFormatter;
@@ -93,11 +93,11 @@
   private JMethod currentMethod;
 
   @Nonnull
-  private final JProgram program;
+  private final JSession session;
 
   public ExportSession(
-       @Nonnull JLookup lookup, @Nonnull JProgram program, @Nonnull NodeLevel nodeLevel) {
-    this.program = program;
+       @Nonnull JLookup lookup, @Nonnull JSession session, @Nonnull NodeLevel nodeLevel) {
+    this.session = session;
     this.lookup = lookup;
     this.nodeLevel = nodeLevel;
   }
@@ -133,8 +133,8 @@
   }
 
   @Nonnull
-  public JProgram getProgram() {
-    return program;
+  public JSession getSession() {
+    return session;
   }
 
   @Nonnull
diff --git a/jack/src/com/android/jack/jayce/v0002/io/JayceInternalReaderImpl.java b/jack/src/com/android/jack/jayce/v0002/io/JayceInternalReaderImpl.java
index 3132bf9..3bc42aa 100644
--- a/jack/src/com/android/jack/jayce/v0002/io/JayceInternalReaderImpl.java
+++ b/jack/src/com/android/jack/jayce/v0002/io/JayceInternalReaderImpl.java
@@ -31,6 +31,11 @@
 import com.android.jack.jayce.v0002.util.MethodKindIdHelper;
 import com.android.jack.jayce.v0002.util.ReceiverKindIdHelper;
 import com.android.jack.jayce.v0002.util.RetentionPolicyIdHelper;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
+import com.android.sched.util.log.stats.Percent;
+import com.android.sched.util.log.stats.PercentImpl;
+import com.android.sched.util.log.stats.StatisticId;
 
 import java.io.IOException;
 import java.io.InputStream;
@@ -46,6 +51,14 @@
  * Jayce internal reader implementation.
  */
 public class JayceInternalReaderImpl implements JayceInternalReader {
+  @Nonnull
+  public static final StatisticId<Percent> SKIPED_NDECLARED_TYPE = new StatisticId<Percent>(
+      "jayce.ndeclaredtype.skiped", "NDeclaredType loading that skiped by the reader",
+      PercentImpl.class, Percent.class);
+  @Nonnull
+  public static final StatisticId<Percent> SKIPED_BODY = new StatisticId<Percent>(
+      "jayce.body.skiped", "Body loading skiped by the reader",
+      PercentImpl.class, Percent.class);
 
   @Nonnull
   private final Tokenizer tokenizer;
@@ -65,6 +78,9 @@
   @Nonnull
   private final List<String> currentCatchBlockList = new ArrayList<String>();
 
+  @Nonnull
+  private final Tracer tracer = TracerFactory.getTracer();
+
   public JayceInternalReaderImpl(@Nonnull InputStream in, @Nonnull Charset encoding) {
     this.tokenizer = new Tokenizer(in);
   }
@@ -179,6 +195,8 @@
       return null;
     }
 
+
+
     tokenizer.readOpen();
     NNode node;
     try {
@@ -186,6 +204,12 @@
     } catch (InvalidTokenException e) {
       throw new ParseException("Unexpected token " + token + " while expecting node.", e);
     }
+    Percent statistic = null;
+    if (token == Token.METHOD_BODY) {
+      statistic = tracer.getStatistic(SKIPED_BODY);
+    } else if (node instanceof NDeclaredType) {
+      statistic = tracer.getStatistic(SKIPED_NDECLARED_TYPE);
+    }
 
     assert nodeClass.isAssignableFrom(node.getClass());
 
@@ -204,8 +228,14 @@
     tokenizer.readClose();
 
     if (nodeLevel.keep(token.getNodeLevel())) {
+      if (statistic != null) {
+        statistic.addFalse();
+      }
       return (T) node;
     } else {
+      if (statistic != null) {
+        statistic.addTrue();
+      }
       return null;
     }
   }
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NAnnotationType.java b/jack/src/com/android/jack/jayce/v0002/nodes/NAnnotationType.java
index 5a8462b..0f611b2 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NAnnotationType.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NAnnotationType.java
@@ -82,7 +82,7 @@
     String binaryName = NamingTools.getClassBinaryNameFromDescriptor(signature);
     String simpleName = NamingTools.getSimpleClassNameFromBinaryName(binaryName);
     SourceInfo jSourceInfo = sourceInfo.exportAsJast(
-        new ExportSession(loader.getLookup(), enclosingPackage.getProgram(), NodeLevel.TYPES));
+        new ExportSession(loader.getLookup(), enclosingPackage.getSession(), NodeLevel.TYPES));
     JDefinedAnnotation jInterfaceType =
         new JDefinedAnnotation(jSourceInfo, simpleName, modifiers, enclosingPackage, loader);
     jInterfaceType.setRetentionPolicy(retentionPolicy);
@@ -95,7 +95,7 @@
     assert sourceInfo != null;
     assert signature != null;
     JDefinedAnnotation jInterfaceType = (JDefinedAnnotation) loading;
-    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getJProgram(),
+    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getSession(),
         NodeLevel.STRUCTURE);
     exportSession.setCurrentType(jInterfaceType);
     exportSession.setCurrentType(jInterfaceType);
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NClassType.java b/jack/src/com/android/jack/jayce/v0002/nodes/NClassType.java
index 8193817..6744a25 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NClassType.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NClassType.java
@@ -117,7 +117,7 @@
     String binaryName = NamingTools.getClassBinaryNameFromDescriptor(signature);
     String simpleName = NamingTools.getSimpleClassNameFromBinaryName(binaryName);
     SourceInfo jSourceInfo = sourceInfo.exportAsJast(
-        new ExportSession(loader.getLookup(), enclosingPackage.getProgram(), NodeLevel.TYPES));
+        new ExportSession(loader.getLookup(), enclosingPackage.getSession(), NodeLevel.TYPES));
     JDefinedClass jClassType =
         new JDefinedClass(jSourceInfo, simpleName, modifiers, enclosingPackage, loader);
     return jClassType;
@@ -129,7 +129,7 @@
     assert sourceInfo != null;
     assert signature != null;
     JDefinedClass jClassType = (JDefinedClass) loading;
-    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getJProgram(),
+    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getSession(),
         NodeLevel.STRUCTURE);
     exportSession.setCurrentType(jClassType);
     if (superClass != null) {
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NEnumType.java b/jack/src/com/android/jack/jayce/v0002/nodes/NEnumType.java
index 2232b30..e0ff8d0 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NEnumType.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NEnumType.java
@@ -80,7 +80,7 @@
     String binaryName = NamingTools.getClassBinaryNameFromDescriptor(signature);
     String simpleName = NamingTools.getSimpleClassNameFromBinaryName(binaryName);
     SourceInfo jSourceInfo = sourceInfo.exportAsJast(
-        new ExportSession(loader.getLookup(), enclosingPackage.getProgram(), NodeLevel.TYPES));
+        new ExportSession(loader.getLookup(), enclosingPackage.getSession(), NodeLevel.TYPES));
     JDefinedEnum jEnumType =
         new JDefinedEnum(jSourceInfo, simpleName, modifiers, enclosingPackage, loader);
     return jEnumType;
@@ -91,7 +91,7 @@
     assert sourceInfo != null;
     assert signature != null;
     JDefinedEnum jEnumType = (JDefinedEnum) loading;
-    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getJProgram(),
+    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getSession(),
         NodeLevel.STRUCTURE);
     exportSession.setCurrentType(jEnumType);
       try {
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NInterfaceType.java b/jack/src/com/android/jack/jayce/v0002/nodes/NInterfaceType.java
index b6257bb..70f5c4e 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NInterfaceType.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NInterfaceType.java
@@ -103,7 +103,7 @@
     String binaryName = NamingTools.getClassBinaryNameFromDescriptor(signature);
     String simpleName = NamingTools.getSimpleClassNameFromBinaryName(binaryName);
     SourceInfo jSourceInfo = sourceInfo.exportAsJast(
-        new ExportSession(loader.getLookup(), enclosingPackage.getProgram(), NodeLevel.TYPES));
+        new ExportSession(loader.getLookup(), enclosingPackage.getSession(), NodeLevel.TYPES));
     JDefinedInterface jInterfaceType =
         new JDefinedInterface(jSourceInfo, simpleName, modifiers, enclosingPackage, loader);
     return jInterfaceType;
@@ -115,7 +115,7 @@
     assert sourceInfo != null;
     assert signature != null;
     JDefinedInterface jInterfaceType = (JDefinedInterface) loading;
-    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getJProgram(),
+    ExportSession exportSession = new ExportSession(loader.getLookup(), loading.getSession(),
         NodeLevel.STRUCTURE);
     exportSession.setCurrentType(jInterfaceType);
     for (String superInterface : superInterfaces) {
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NMethod.java b/jack/src/com/android/jack/jayce/v0002/nodes/NMethod.java
index 64fa4ad..39da324 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NMethod.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NMethod.java
@@ -22,7 +22,7 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JParameter;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.MethodKind;
 import com.android.jack.jayce.JayceClassOrInterfaceLoader;
 import com.android.jack.jayce.JayceMethodLoader;
@@ -144,8 +144,8 @@
   @Override
   public JAbstractMethodBody loadBody(@Nonnull JMethod method) {
     if (body != null) {
-      JProgram program = method.getParent(JProgram.class);
-      ExportSession exportSession = new ExportSession(program.getPhantomLookup(), program,
+      JSession session = method.getParent(JSession.class);
+      ExportSession exportSession = new ExportSession(session.getPhantomLookup(), session,
           NodeLevel.FULL);
       exportSession.setCurrentMethod(method);
 
diff --git a/jack/src/com/android/jack/jayce/v0002/nodes/NProgram.java b/jack/src/com/android/jack/jayce/v0002/nodes/NProgram.java
index 57f9223..ce4ad19 100644
--- a/jack/src/com/android/jack/jayce/v0002/nodes/NProgram.java
+++ b/jack/src/com/android/jack/jayce/v0002/nodes/NProgram.java
@@ -17,7 +17,7 @@
 package com.android.jack.jayce.v0002.nodes;
 
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.jayce.v0002.NNode;
 import com.android.jack.jayce.v0002.io.ExportSession;
 import com.android.jack.jayce.v0002.io.ImportHelper;
@@ -44,20 +44,19 @@
 
   @Override
   public void importFromJast(@Nonnull ImportHelper loader, @Nonnull  Object node) {
-    JProgram jProgram = (JProgram) node;
-    assert jProgram.codeGenTypes.isEmpty();
-    allTypes = loader.load(NDeclaredType.class, jProgram.getTypesToEmit());
+    JSession session = (JSession) node;
+    allTypes = loader.load(NDeclaredType.class, session.getTypesToEmit());
   }
 
   @Override
   @Nonnull
-  public JProgram exportAsJast(@Nonnull ExportSession exportSession) {
-    JProgram jProgram = new JProgram();
+  public JSession exportAsJast(@Nonnull ExportSession exportSession) {
+    JSession session = new JSession();
     for (NDeclaredType declaredType : allTypes) {
       JDefinedClassOrInterface jDeclaredType = declaredType.exportAsJast(exportSession);
-      jProgram.addTypeToEmit(jDeclaredType);
+      session.addTypeToEmit(jDeclaredType);
     }
-    return jProgram;
+    return session;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/load/ComposedPackageLoader.java b/jack/src/com/android/jack/load/ComposedPackageLoader.java
index 52a53e4..4de2ea7 100644
--- a/jack/src/com/android/jack/load/ComposedPackageLoader.java
+++ b/jack/src/com/android/jack/load/ComposedPackageLoader.java
@@ -72,7 +72,7 @@
       }
     }
     if (loader != null) {
-      JPackage subPackage = new JPackage(simpleName, loading.getProgram(), loading, loader);
+      JPackage subPackage = new JPackage(simpleName, loading.getSession(), loading, loader);
       subPackage.updateParents(loading);
       return subPackage;
     } else {
diff --git a/jack/src/com/android/jack/lookup/JNodeLookup.java b/jack/src/com/android/jack/lookup/JNodeLookup.java
index fab3a80..c83d447 100644
--- a/jack/src/com/android/jack/lookup/JNodeLookup.java
+++ b/jack/src/com/android/jack/lookup/JNodeLookup.java
@@ -29,6 +29,11 @@
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JTypeLookupException;
 import com.android.jack.util.NamingTools;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
+import com.android.sched.util.log.stats.Percent;
+import com.android.sched.util.log.stats.PercentImpl;
+import com.android.sched.util.log.stats.StatisticId;
 
 import java.util.Iterator;
 import java.util.Map;
@@ -40,10 +45,17 @@
  * Jack lookup.
  */
 public class JNodeLookup extends JLookup {
+  @Nonnull
+  public static final StatisticId<Percent> SUCCESS_LOOKUP = new StatisticId<Percent>(
+      "jack.lookup.success", "Lookup requests returning a JDefinedClassOrInterface",
+      PercentImpl.class, Percent.class);
 
   @Nonnull
   private final Map<String, JType> types = new ConcurrentHashMap<String, JType>();
 
+  @Nonnull
+  private final Tracer tracer = TracerFactory.getTracer();
+
   /**
    * Initialize lookup.
    */
@@ -73,13 +85,15 @@
   @Override
   @Nonnull
   public JType getType(@Nonnull String typeName) throws JTypeLookupException {
+    Percent statistic = tracer.getStatistic(SUCCESS_LOOKUP);
+    statistic.addFalse();
     synchronized (types) {
       JType result = types.get(typeName);
 
       if (result == null) {
         int typeNameLength = typeName.length();
         assert typeNameLength > 1 : "Invalid signature or missing primitive type '" + typeName
-          + "'";
+        + "'";
         if (typeName.charAt(0) == '[') {
           JArrayType arrayType = getArrayType(typeName);
           types.put(typeName, arrayType);
@@ -105,7 +119,8 @@
         result = currentPackage.getType(simpleName);
         types.put(typeName, result);
       }
-
+      statistic.removeFalse();
+      statistic.addTrue();
       return result;
     }
   }
diff --git a/jack/src/com/android/jack/optimizations/NotSimplifier.java b/jack/src/com/android/jack/optimizations/NotSimplifier.java
index 087e626..530ef3f 100644
--- a/jack/src/com/android/jack/optimizations/NotSimplifier.java
+++ b/jack/src/com/android/jack/optimizations/NotSimplifier.java
@@ -78,7 +78,7 @@
     @Override
     public boolean visit(@Nonnull JExpression expr) {
       assert expr.getType() instanceof JBooleanType || expr.getType()
-          == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+          == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       opAfterTransformation++;
       return false;
     }
@@ -86,7 +86,7 @@
     @Override
     public boolean visit(@Nonnull JBinaryOperation binaryOp) {
       assert binaryOp.getType() instanceof JBooleanType || binaryOp.getType()
-          == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+          == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       opBeforeTransformation++;
       JBinaryOperator op = binaryOp.getOp();
 
@@ -131,7 +131,7 @@
     @Override
     public boolean visit(@Nonnull JExpression expr) {
       assert expr.getType() instanceof JBooleanType || expr.getType()
-          == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+          == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       tr.append(new Replace(expr, new JPrefixNotOperation(expr.getSourceInfo(), expr)));
       return false;
     }
@@ -139,7 +139,7 @@
     @Override
     public boolean visit(@Nonnull JBinaryOperation binaryOp) {
       assert binaryOp.getType() instanceof JBooleanType || binaryOp.getType()
-          == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+          == Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       JBinaryOperator op = binaryOp.getOp();
 
       if (op.isComparison() || op.isConditionalOperation()
diff --git a/jack/src/com/android/jack/scheduling/adapter/JDefinedClassOrInterfaceAdaptor.java b/jack/src/com/android/jack/scheduling/adapter/JDefinedClassOrInterfaceAdaptor.java
index ef9a3f6..529d2aa 100644
--- a/jack/src/com/android/jack/scheduling/adapter/JDefinedClassOrInterfaceAdaptor.java
+++ b/jack/src/com/android/jack/scheduling/adapter/JDefinedClassOrInterfaceAdaptor.java
@@ -15,7 +15,7 @@
 package com.android.jack.scheduling.adapter;
 
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.schedulable.AdapterSchedulable;
 
@@ -25,22 +25,22 @@
 import javax.annotation.Nonnull;
 
 /**
- * Adapts a process on {@code JProgram} onto one or several processes on each
- * {@code JDefinedClassOrInterface} declared by this program.
+ * Adapts a process on {@code JSession} onto one or several processes on each
+ * {@code JDefinedClassOrInterface} to emit during this session.
  */
-@Description("Adapts process on JProgram to one or several processes on each of its " +
+@Description("Adapts process on JSession to one or several processes on each of its " +
   "JDefinedClassOrInterface")
 public class JDefinedClassOrInterfaceAdaptor
-    implements AdapterSchedulable<JProgram, JDefinedClassOrInterface> {
+    implements AdapterSchedulable<JSession, JDefinedClassOrInterface> {
 
   /**
-   * Return every {@code JDefinedClassOrInterface} declared in the given {@code JProgram}.
+   * Return every {@code JDefinedClassOrInterface} to emit during the given {@code JSession}.
    */
   @Override
   @Nonnull
-  public Iterator<JDefinedClassOrInterface> adapt(@Nonnull JProgram program)
+  public Iterator<JDefinedClassOrInterface> adapt(@Nonnull JSession session)
       throws Exception {
     // Use a copy to scan types in order to support concurrent modification.
-    return new ArrayList<JDefinedClassOrInterface>(program.getTypesToEmit()).iterator();
+    return new ArrayList<JDefinedClassOrInterface>(session.getTypesToEmit()).iterator();
   }
 }
diff --git a/jack/src/com/android/jack/scheduling/adapter/JPackageAdapter.java b/jack/src/com/android/jack/scheduling/adapter/JPackageAdapter.java
index 69ce38a..2f6a8ba 100644
--- a/jack/src/com/android/jack/scheduling/adapter/JPackageAdapter.java
+++ b/jack/src/com/android/jack/scheduling/adapter/JPackageAdapter.java
@@ -19,7 +19,7 @@
 import com.google.common.collect.Iterators;
 
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
 import com.android.sched.schedulable.AdapterSchedulable;
@@ -31,12 +31,12 @@
 import javax.annotation.Nonnull;
 
 /**
- * Adapts a process on {@code JProgram} onto one or several processes on
- * each {@code JPackage} declared by this program.
+ * Adapts a process on {@code JSession} onto one or several processes on
+ * each {@code JPackage} known by this session.
  */
-@Description("Adapts process on JProgram to one or several processes on each of its JPackage")
+@Description("Adapts process on JSession to one or several processes on each of its JPackage")
 @Name("JPackageAdapter")
-public class JPackageAdapter implements AdapterSchedulable<JProgram, JPackage> {
+public class JPackageAdapter implements AdapterSchedulable<JSession, JPackage> {
   @Nonnull
   private Iterator<JPackage> process(@Nonnull JPackage pack)
       throws Exception {
@@ -53,14 +53,14 @@
   }
 
   /**
-   * Returns every {@code JPackage} declared in the given {@code JProgram}.
+   * Returns every {@code JPackage} known by the given {@code JSession}.
    */
   @Override
   @Nonnull
-  public Iterator<JPackage> adapt(@Nonnull JProgram program)
+  public Iterator<JPackage> adapt(@Nonnull JSession session)
       throws Exception {
-    return Iterators.concat(Iterators.singletonIterator(program.getTopLevelPackage()),
-        process(program.getTopLevelPackage()));
+    return Iterators.concat(Iterators.singletonIterator(session.getTopLevelPackage()),
+        process(session.getTopLevelPackage()));
   }
 
 }
diff --git a/jack/src/com/android/jack/scheduling/feature/DexNonZipOutput.java b/jack/src/com/android/jack/scheduling/feature/DexNonZipOutput.java
index cd28688..0827957 100644
--- a/jack/src/com/android/jack/scheduling/feature/DexNonZipOutput.java
+++ b/jack/src/com/android/jack/scheduling/feature/DexNonZipOutput.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/feature/DexZipOutput.java b/jack/src/com/android/jack/scheduling/feature/DexZipOutput.java
index 8695cde..65ee1b8 100644
--- a/jack/src/com/android/jack/scheduling/feature/DexZipOutput.java
+++ b/jack/src/com/android/jack/scheduling/feature/DexZipOutput.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/feature/DxLegacy.java b/jack/src/com/android/jack/scheduling/feature/DxLegacy.java
index 66372cd..8822eb8 100644
--- a/jack/src/com/android/jack/scheduling/feature/DxLegacy.java
+++ b/jack/src/com/android/jack/scheduling/feature/DxLegacy.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/feature/JackFileNonZipOutput.java b/jack/src/com/android/jack/scheduling/feature/JackFileNonZipOutput.java
index 8643256..71ca439 100644
--- a/jack/src/com/android/jack/scheduling/feature/JackFileNonZipOutput.java
+++ b/jack/src/com/android/jack/scheduling/feature/JackFileNonZipOutput.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/feature/JackFileZipOutput.java b/jack/src/com/android/jack/scheduling/feature/JackFileZipOutput.java
index a206c96..7428a7b 100644
--- a/jack/src/com/android/jack/scheduling/feature/JackFileZipOutput.java
+++ b/jack/src/com/android/jack/scheduling/feature/JackFileZipOutput.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/feature/SourceVersion7.java b/jack/src/com/android/jack/scheduling/feature/SourceVersion7.java
index ddd19b0..1ba59e9 100644
--- a/jack/src/com/android/jack/scheduling/feature/SourceVersion7.java
+++ b/jack/src/com/android/jack/scheduling/feature/SourceVersion7.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.scheduling.feature;
 
 import com.android.sched.item.Description;
diff --git a/jack/src/com/android/jack/scheduling/marker/DexFileMarker.java b/jack/src/com/android/jack/scheduling/marker/DexFileMarker.java
index 972a727..5a621b9 100644
--- a/jack/src/com/android/jack/scheduling/marker/DexFileMarker.java
+++ b/jack/src/com/android/jack/scheduling/marker/DexFileMarker.java
@@ -17,7 +17,7 @@
 package com.android.jack.scheduling.marker;
 
 import com.android.jack.dx.dex.file.DexFile;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.ComposedOf;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
@@ -31,7 +31,7 @@
  * A marker which contains a {@code DexFile} instance.
  */
 @Description("A marker which contains a DexFile instance.")
-@ValidOn(JProgram.class)
+@ValidOn(JSession.class)
 public final class DexFileMarker implements Marker {
   @Nonnull
   private final DexFile dexFile;
diff --git a/jack/src/com/android/jack/shrob/SeedPrinter.java b/jack/src/com/android/jack/shrob/SeedPrinter.java
index c612c6d..d303109 100644
--- a/jack/src/com/android/jack/shrob/SeedPrinter.java
+++ b/jack/src/com/android/jack/shrob/SeedPrinter.java
@@ -23,7 +23,7 @@
 import com.android.jack.ir.ast.JField;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JParameter;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.shrob.obfuscation.OriginalNames;
 import com.android.jack.shrob.proguard.GrammarActions;
@@ -59,7 +59,7 @@
 @Description("Visitor that prints the seeds")
 @Produce(SeedFile.class)
 @Constraint(need = OriginalNames.class)
-public class SeedPrinter implements RunnableSchedulable<JProgram> {
+public class SeedPrinter implements RunnableSchedulable<JSession> {
 
   @Nonnull
   public static final PropertyId<StreamFile> SEEDS_OUTPUT_FILE = PropertyId.create(
@@ -91,9 +91,9 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
 
-    for (JDefinedClassOrInterface type : program.getTypesToEmit()) {
+    for (JDefinedClassOrInterface type : session.getTypesToEmit()) {
       boolean matched = false;
       List<FieldSpecification> matchedFieldSpecs = new ArrayList<FieldSpecification>();
       List<MethodSpecification> matchedMethodSpecs = new ArrayList<MethodSpecification>();
diff --git a/jack/src/com/android/jack/shrob/obfuscation/MappingApplier.java b/jack/src/com/android/jack/shrob/obfuscation/MappingApplier.java
index a44fb3c..941bd0a 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/MappingApplier.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/MappingApplier.java
@@ -27,7 +27,7 @@
 import com.android.jack.ir.ast.JField;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JTypeLookupException;
 import com.android.jack.lookup.JLookupException;
@@ -64,9 +64,6 @@
   private static final char[] EMPTY_STOP_CHARS = new char[] {};
 
   @Nonnull
-  private static final char[] OLD_NAME_STOP_CHARS = new char[] {'-'};
-
-  @Nonnull
   private static final char[] CLASSINFO_STOP_CHARS = new char[] {':'};
 
   @Nonnull
@@ -102,14 +99,14 @@
 
   @CheckForNull
   private JDefinedClassOrInterface createMappingForType(@Nonnull String oldName,
-      @Nonnull String newName, @Nonnull JProgram program, @Nonnull File mappingFile,
+      @Nonnull String newName, @Nonnull JSession session, @Nonnull File mappingFile,
       int lineNumber) {
     JClassOrInterface type = null;
-    JNodeLookup lookup = program.getLookup();
+    JNodeLookup lookup = session.getLookup();
     try {
       String typeSignature = NamingTools.getTypeSignatureName(oldName);
       type = (JClassOrInterface) lookup.getType(typeSignature);
-      if (!program.getTypesToEmit().contains(type)) {
+      if (!session.getTypesToEmit().contains(type)) {
         logger.log(Level.WARNING, "{0}:{1}: Type {2} has a mapping but was removed",
             new Object[] {mappingFile.getAbsolutePath(), Integer.valueOf(lineNumber), oldName});
         return null;
@@ -167,6 +164,31 @@
     return index;
   }
 
+  /**
+   * Reads this string until a whitespace or the '->' separator is read
+   * or until the end of the string, starting the search at the specified index.
+   * @param line the line to read from.
+   * @param index the index to start the reading from.
+   * @return the index of the first occurrence of a whitespace, the '->' separator
+   * or the end of the string.
+   */
+  private int readNameUntilSeparatorOrWhitespace(@Nonnull String line, int index) {
+    int length = line.length();
+    char c = line.charAt(index);
+    while (!Character.isWhitespace(c)) {
+      if (c == '-' && line.charAt(index + 1) == '>') {
+        // We check the second char to avoid bad parsing of names containing '-'
+        break;
+      }
+      if (++index < length) {
+        c = line.charAt(index);
+      } else {
+        break;
+      }
+    }
+    return index;
+  }
+
   private int readWhiteSpaces(@Nonnull String line, int index) {
     char c = line.charAt(index);
     while (Character.isWhitespace(c)) {
@@ -187,11 +209,11 @@
 
   @CheckForNull
   private JDefinedClassOrInterface readClassInfo(
-      @Nonnull String line, @Nonnull JProgram program, @Nonnull File mappingFile, int lineNumber) {
+      @Nonnull String line, @Nonnull JSession session, @Nonnull File mappingFile, int lineNumber) {
     // qualifiedOldClassName -> newClassName:
     try {
       int startIndex = readWhiteSpaces(line, 0);
-      int endIndex = readName(line, startIndex, OLD_NAME_STOP_CHARS);
+      int endIndex = readNameUntilSeparatorOrWhitespace(line, startIndex);
       String qualifiedOldClassName = line.substring(startIndex, endIndex);
       startIndex = readWhiteSpaces(line, endIndex);
       startIndex = readSeparator(line, startIndex, mappingFile, lineNumber);
@@ -199,7 +221,7 @@
       endIndex = readName(line, startIndex, CLASSINFO_STOP_CHARS);
       String newClassName = line.substring(startIndex, endIndex);
       return createMappingForType(
-          qualifiedOldClassName, newClassName, program, mappingFile, lineNumber);
+          qualifiedOldClassName, newClassName, session, mappingFile, lineNumber);
     } catch (ArrayIndexOutOfBoundsException e) {
       throwException(
           mappingFile, lineNumber, "The mapping file is badly formatted (class mapping expected)");
@@ -227,7 +249,7 @@
       int endIndex = readName(line, startIndex, EMPTY_STOP_CHARS);
       String typeSignature = GrammarActions.getSignature(line.substring(startIndex, endIndex));
       startIndex = readWhiteSpaces(line, endIndex);
-      endIndex = readName(line, startIndex, OLD_NAME_STOP_CHARS);
+      endIndex = readNameUntilSeparatorOrWhitespace(line, startIndex);
       String oldName = line.substring(startIndex, endIndex);
       int index = readWhiteSpaces(line, endIndex);
       index = readSeparator(line, index, mappingFile, lineNumber);
@@ -324,7 +346,16 @@
 
   protected void renameMethod(
       @Nonnull JMethod method, @Nonnull File mappingFile, int lineNumber, @Nonnull String newName) {
-    rename(method.getMethodId(), mappingFile, lineNumber, newName);
+    String oldName = method.getName();
+    if (oldName.equals(NamingTools.INIT_NAME)) {
+      logger.log(Level.WARNING, "{0}:{1}: Constructors cannot be renamed",
+          new Object[] {mappingFile.getAbsolutePath(), Integer.valueOf(lineNumber)});
+    } else if (oldName.equals(NamingTools.STATIC_INIT_NAME)) {
+      logger.log(Level.WARNING, "{0}:{1}: Static initializers cannot be renamed",
+          new Object[] {mappingFile.getAbsolutePath(), Integer.valueOf(lineNumber)});
+    } else {
+      rename(method.getMethodId(), mappingFile, lineNumber, newName);
+    }
   }
 
   /**
@@ -335,10 +366,10 @@
    * type must be in the java form (e.g. java.lang.String, boolean).
    *
    * @param mappingFile
-   * @param program
+   * @param session
    * @throws JackIOException
    */
-  public void applyMapping(@Nonnull File mappingFile, @Nonnull JProgram program)
+  public void applyMapping(@Nonnull File mappingFile, @Nonnull JSession session)
       throws JackIOException {
     LineNumberReader reader = null;
     try {
@@ -348,12 +379,12 @@
 
       while (line != null) {
         if (isClassInfo(line)) {
-          currentType = readClassInfo(line, program, mappingFile, reader.getLineNumber());
+          currentType = readClassInfo(line, session, mappingFile, reader.getLineNumber());
         } else {
           if (currentType != null) {
             if (isMethodInfo(line)) {
               readMethodInfo(line, currentType, mappingFile, reader.getLineNumber(),
-                  program.getLookup());
+                  session.getLookup());
             } else {
               readFieldInfo(line, currentType, mappingFile, reader.getLineNumber());
             }
diff --git a/jack/src/com/android/jack/shrob/obfuscation/MappingPrinter.java b/jack/src/com/android/jack/shrob/obfuscation/MappingPrinter.java
index 35a1904..3df9dcb 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/MappingPrinter.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/MappingPrinter.java
@@ -28,7 +28,7 @@
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JPackage;
 import com.android.jack.ir.ast.JParameter;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.shrob.proguard.GrammarActions;
@@ -61,7 +61,7 @@
 @Produce(Mapping.class)
 @Optional(@ToSupport(
     feature = Obfuscation.class, add = @Constraint(need = OriginalNameMarker.class)))
-public class MappingPrinter implements RunnableSchedulable<JProgram> {
+public class MappingPrinter implements RunnableSchedulable<JSession> {
 
   @Nonnull
   public static final PropertyId<StreamFile> MAPPING_OUTPUT_FILE = PropertyId.create(
@@ -195,7 +195,7 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram t) throws Exception {
+  public void run(@Nonnull JSession t) throws Exception {
     Visitor visitor = new Visitor();
     visitor.accept(t);
     stream.close();
diff --git a/jack/src/com/android/jack/shrob/obfuscation/NameKeeper.java b/jack/src/com/android/jack/shrob/obfuscation/NameKeeper.java
index a64cbe6..67e9674 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/NameKeeper.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/NameKeeper.java
@@ -24,7 +24,6 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.shrob.proguard.GrammarActions;
 import com.android.jack.shrob.shrink.NodeFinder;
@@ -91,7 +90,7 @@
 
     @Override
     public boolean visit(@Nonnull JMethod m) {
-      if (JProgram.isClinit(m) || m instanceof JConstructor) {
+      if (JMethod.isClinit(m) || m instanceof JConstructor) {
         keepName(m);
       }
       return false;
diff --git a/jack/src/com/android/jack/shrob/obfuscation/ObfuscationEventType.java b/jack/src/com/android/jack/shrob/obfuscation/ObfuscationEventType.java
index b72000f..9b9a27d 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/ObfuscationEventType.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/ObfuscationEventType.java
@@ -25,22 +25,13 @@
  */
 public enum ObfuscationEventType implements EventType {
 
-  FINDING_OBFUSCATION_SEEDS("Finding seeds", "black");
+  FINDING_OBFUSCATION_SEEDS("Finding seeds");
 
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
-  ObfuscationEventType(@Nonnull String name, @Nonnull String cssColor) {
+  ObfuscationEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/shrob/obfuscation/Renamer.java b/jack/src/com/android/jack/shrob/obfuscation/Renamer.java
index ec76e31..5807e60 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/Renamer.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/Renamer.java
@@ -27,7 +27,7 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.shrob.obfuscation.nameprovider.NameProvider;
 import com.android.jack.shrob.proguard.GrammarActions;
@@ -67,13 +67,13 @@
 @Transform(add = {OriginalNameMarker.class, OriginalPackageMarker.class},
   remove = OriginalNames.class)
 @Use(MappingApplier.class)
-public class Renamer implements RunnableSchedulable<JProgram> {
+public class Renamer implements RunnableSchedulable<JSession> {
 
   @Nonnull
   public static final
       BooleanPropertyId USE_PACKAGE_OBFUSCATION_DICTIONARY = BooleanPropertyId.create(
           "jack.obfuscation.packagedictionary",
-          "Use obfuscation dictionary for packages").addDefaultValue("false");
+          "Use obfuscation dictionary for packages").addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<File> PACKAGE_OBFUSCATION_DICTIONARY = PropertyId.create(
@@ -83,7 +83,7 @@
   @Nonnull
   public static final BooleanPropertyId USE_CLASS_OBFUSCATION_DICTIONARY = BooleanPropertyId.create(
       "jack.obfuscation.classdictionary", "Use obfuscation dictionary for classes")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<File> CLASS_OBFUSCATION_DICTIONARY = PropertyId.create(
@@ -93,7 +93,7 @@
   @Nonnull
   public static final BooleanPropertyId USE_OBFUSCATION_DICTIONARY = BooleanPropertyId.create(
       "jack.obfuscation.dictionary", "Use obfuscation dictionary for members")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<File> OBFUSCATION_DICTIONARY = PropertyId.create(
@@ -103,7 +103,7 @@
   @Nonnull
   public static final BooleanPropertyId USE_MAPPING = BooleanPropertyId.create(
       "jack.obfuscation.mapping", "Use mapping for types and members")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<File> MAPPING_FILE = PropertyId.create(
@@ -115,7 +115,7 @@
   public static final BooleanPropertyId REPACKAGE_CLASSES = BooleanPropertyId.create(
       "jack.obfuscation.repackageclasses",
       "Change package for all renamed classes")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<String> PACKAGE_FOR_RENAMED_CLASSES = PropertyId.create(
@@ -127,7 +127,7 @@
   public static final BooleanPropertyId FLATTEN_PACKAGE = BooleanPropertyId.create(
       "jack.obfuscation.flattenpackage",
       "Change package for all renamed packages")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<String> PACKAGE_FOR_RENAMED_PACKAGES = PropertyId.create(
@@ -139,7 +139,7 @@
   public static final BooleanPropertyId USE_UNIQUE_CLASSMEMBERNAMES = BooleanPropertyId.create(
       "jack.obfuscation.uniqueclassmembernames",
       "All members with the same name must have the same obfuscated name")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   public static boolean mustBeRenamed(@Nonnull AbstractMarkerManager node) {
     return !node.containsMarker(KeepNameMarker.class)
@@ -253,7 +253,7 @@
 
     @Nonnull
     private final JPackage packageForRenamedClasses
-      = Jack.getProgram().getLookup().getOrCreatePackage(packageNameForRenamedClasses);
+      = Jack.getSession().getLookup().getOrCreatePackage(packageNameForRenamedClasses);
 
     private RepackagerVisitor(@Nonnull TransformationRequest request) {
       this.request = request;
@@ -290,7 +290,7 @@
 
     @Nonnull
     private final JPackage packageForRenamedPackages
-      = Jack.getProgram().getLookup().getOrCreatePackage(packageNameForRenamedPackages);
+      = Jack.getSession().getLookup().getOrCreatePackage(packageNameForRenamedPackages);
 
     @Nonnull
     private final NameProvider packageNameProvider =
@@ -350,14 +350,14 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
-    allTypes = program.getTypesToEmit();
+  public void run(@Nonnull JSession session) throws Exception {
+    allTypes = session.getTypesToEmit();
     Map<String, String> fieldNames = new HashMap<String, String>();
     Map<String, String> methodNames = new HashMap<String, String>();
     boolean useUniqueClassMemberNames =
         ThreadConfig.get(USE_UNIQUE_CLASSMEMBERNAMES).booleanValue();
     if (ThreadConfig.get(USE_MAPPING).booleanValue()) {
-      TransformationRequest request = new TransformationRequest(program);
+      TransformationRequest request = new TransformationRequest(session);
       MappingApplier mappingApplier;
       if (useUniqueClassMemberNames) {
         mappingApplier = new CollectingMappingApplier(request);
@@ -366,7 +366,7 @@
       } else {
         mappingApplier = new MappingApplier(request);
       }
-      mappingApplier.applyMapping(ThreadConfig.get(MAPPING_FILE), program);
+      mappingApplier.applyMapping(ThreadConfig.get(MAPPING_FILE), session);
       request.commit();
     }
 
@@ -386,18 +386,18 @@
     }
 
     if (ThreadConfig.get(REPACKAGE_CLASSES).booleanValue()) {
-      TransformationRequest request = new TransformationRequest(program);
+      TransformationRequest request = new TransformationRequest(session);
       Visitor visitor = new RepackagerVisitor(request);
-      visitor.accept(program);
+      visitor.accept(session);
       request.commit();
     } else if (ThreadConfig.get(FLATTEN_PACKAGE).booleanValue()) {
-      TransformationRequest request = new TransformationRequest(program);
+      TransformationRequest request = new TransformationRequest(session);
       Visitor visitor = new FlattenerVisitor(request);
-      visitor.accept(program);
+      visitor.accept(session);
       request.commit();
     } else {
       Visitor visitor = new Visitor();
-      visitor.accept(program);
+      visitor.accept(session);
     }
   }
 }
diff --git a/jack/src/com/android/jack/shrob/obfuscation/annotation/AnnotationRemover.java b/jack/src/com/android/jack/shrob/obfuscation/annotation/AnnotationRemover.java
index 6ab2ed6..bebf64e 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/annotation/AnnotationRemover.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/annotation/AnnotationRemover.java
@@ -35,12 +35,12 @@
   public static final
       BooleanPropertyId EMIT_RUNTIME_INVISIBLE_ANNOTATION = BooleanPropertyId.create(
           "jack.annotation.runtimeinvisible", "Emit annotations that are runtime invisible")
-          .addDefaultValue("true");
+          .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final BooleanPropertyId EMIT_RUNTIME_VISIBLE_ANNOTATION = BooleanPropertyId.create(
       "jack.annotation.runtimevisible", "Emit annotations that are runtime visible")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   private final Logger logger = LoggerFactory.getLogger();
diff --git a/jack/src/com/android/jack/shrob/obfuscation/annotation/ParameterAnnotationRemover.java b/jack/src/com/android/jack/shrob/obfuscation/annotation/ParameterAnnotationRemover.java
index 195a7d0..a63a00c 100644
--- a/jack/src/com/android/jack/shrob/obfuscation/annotation/ParameterAnnotationRemover.java
+++ b/jack/src/com/android/jack/shrob/obfuscation/annotation/ParameterAnnotationRemover.java
@@ -52,13 +52,13 @@
   public static final
       BooleanPropertyId EMIT_RUNTIME_VISIBLE_PARAMETER_ANNOTATION = BooleanPropertyId.create(
           "jack.annotation.runtimevisible.parameter",
-          "Emit parameters annotations that are runtime visible").addDefaultValue("true");
+          "Emit parameters annotations that are runtime visible").addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final
       BooleanPropertyId EMIT_RUNTIME_INVISIBLE_PARAMETER_ANNOTATION = BooleanPropertyId.create(
           "jack.annotation.runtimeinvisible.parameter",
-          "Emit parameters annotations that are runtime invisible").addDefaultValue("true");
+          "Emit parameters annotations that are runtime invisible").addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   private final Logger logger = LoggerFactory.getLogger();
diff --git a/jack/src/com/android/jack/shrob/shrink/KeepMarker.java b/jack/src/com/android/jack/shrob/shrink/KeepMarker.java
index fadba68..469c7d4 100644
--- a/jack/src/com/android/jack/shrob/shrink/KeepMarker.java
+++ b/jack/src/com/android/jack/shrob/shrink/KeepMarker.java
@@ -31,6 +31,16 @@
 @Description("Indicates that this class or member should not be removed when shrinking.")
 public class KeepMarker implements Marker {
 
+  private boolean mustTraceOverridingMethods = false;
+
+  public void setMustTraceOverridingMethods(boolean mustTraceOverridingMethods) {
+    this.mustTraceOverridingMethods = mustTraceOverridingMethods;
+  }
+
+  public boolean mustTraceOverridingMethods() {
+    return mustTraceOverridingMethods;
+  }
+
   @Override
   public Marker cloneIfNeeded() {
     return this;
diff --git a/jack/src/com/android/jack/shrob/shrink/Keeper.java b/jack/src/com/android/jack/shrob/shrink/Keeper.java
index 174f0b4..1df2405 100644
--- a/jack/src/com/android/jack/shrob/shrink/Keeper.java
+++ b/jack/src/com/android/jack/shrob/shrink/Keeper.java
@@ -141,11 +141,38 @@
         }
       }
     }
+
+    @Override
+    protected boolean mustTraceOverridingMethod(@Nonnull JMethod method) {
+      if (method.getEnclosingType().isExternal()) {
+        return true;
+      } else {
+        synchronized (method) {
+          KeepMarker marker = method.getMarker(KeepMarker.class);
+          if (marker != null) {
+            return marker.mustTraceOverridingMethods();
+          }
+        }
+      }
+      return false;
+    }
+
+    @Override
+    protected void setMustTraceOverridingMethods(@Nonnull JMethod method) {
+      synchronized (method) {
+        KeepMarker marker = method.getMarker(KeepMarker.class);
+        if (marker != null) {
+          marker.setMustTraceOverridingMethods(true);
+        } else {
+          assert method.getEnclosingType().isExternal();
+        }
+      }
+    }
   }
 
   public static final BooleanPropertyId KEEP_ENCLOSING_METHOD = BooleanPropertyId.create(
       "jack.shrink.keep.enclosing.method",
-      "Keep the enclosing method of annonymous classes").addDefaultValue("false");
+      "Keep the enclosing method of annonymous classes").addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   private final Flags flags = ThreadConfig.get(Options.FLAGS);
diff --git a/jack/src/com/android/jack/shrob/shrink/ShrinkEventType.java b/jack/src/com/android/jack/shrob/shrink/ShrinkEventType.java
index 9a645f2..302bd80 100644
--- a/jack/src/com/android/jack/shrob/shrink/ShrinkEventType.java
+++ b/jack/src/com/android/jack/shrob/shrink/ShrinkEventType.java
@@ -25,23 +25,14 @@
  */
 public enum ShrinkEventType implements EventType {
 
-  FINDING_SEEDS("Finding seeds", "Blue"),
-  OVERRIDING_METHODS("Searching for overridding methods", "Red");
+  FINDING_SEEDS("Finding seeds"),
+  OVERRIDING_METHODS("Searching for overridding methods");
 
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
-  ShrinkEventType(@Nonnull String name, @Nonnull String cssColor) {
+  ShrinkEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/shrob/shrink/Tracer.java b/jack/src/com/android/jack/shrob/shrink/Tracer.java
index 882a10c..d523bb6 100644
--- a/jack/src/com/android/jack/shrob/shrink/Tracer.java
+++ b/jack/src/com/android/jack/shrob/shrink/Tracer.java
@@ -52,7 +52,6 @@
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JParameter;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JTypeStringLiteral;
 import com.android.jack.ir.ast.JVariable;
@@ -113,13 +112,14 @@
     if (superClOrI instanceof JDefinedClassOrInterface) {
       JDefinedClassOrInterface definedSuperClOrI = (JDefinedClassOrInterface) superClOrI;
       for (JMethod method : definedSuperClOrI.getMethods()) {
-        if (isMarked(method)) {
+        if (isMarked(method) && mustTraceOverridingMethod(method)) {
           JMethodId methodId = method.getMethodId();
           JType returnType = method.getType();
           JMethod implementation =
               findImplementation(methodId, returnType, extendingOrImplementingClass);
           if (implementation != null) {
-            trace(methodId, implementation.getEnclosingType(), returnType);
+            trace(methodId, implementation.getEnclosingType(), returnType,
+                true /* mustTraceOverridingMethods */);
           }
         }
       }
@@ -134,11 +134,15 @@
     }
   }
 
+  protected abstract boolean mustTraceOverridingMethod(@Nonnull JMethod method);
+
+  protected abstract void setMustTraceOverridingMethods(@Nonnull JMethod method);
+
   protected void trace(@Nonnull JDefinedClassOrInterface t) {
     if (markIfNecessary(t)) {
       traceAnnotations(t);
       for (JMethod m : t.getMethods()) {
-        if (!isMarked(m) && (JProgram.isClinit(m) || isNullaryConstructor(m))) {
+        if (!isMarked(m) && (JMethod.isClinit(m) || isNullaryConstructor(m))) {
           trace(m);
         }
       }
@@ -205,11 +209,14 @@
   /**
    * Traces the methods corresponding to a method id whose enclosing type is a subclass of
    * receiverType
-   * @param mid
-   * @param receiverType
+   * @param mid the methodId of the searched method
+   * @param receiverType the type with which the methodId was used
+   * @param returnType the return type of the searched method
+   * @param mustTraceOverridingMethods indicates if the overriding methods of the traced method
+   * should be traced as well
    */
-  protected void trace(
-      @Nonnull JMethodId mid, @Nonnull JClassOrInterface receiverType, @Nonnull JType returnType) {
+  protected void trace(@Nonnull JMethodId mid, @Nonnull JClassOrInterface receiverType,
+      @Nonnull JType returnType, boolean mustTraceOverridingMethods) {
     for (JType paramType : mid.getParamTypes()) {
       trace(paramType);
     }
@@ -217,9 +224,12 @@
     JMethod foundMethod = findMethod(mid, receiverType, returnType);
     if (foundMethod != null) {
       trace(foundMethod);
+      if (mustTraceOverridingMethods) {
+        setMustTraceOverridingMethods(foundMethod);
+      }
     }
 
-    if (receiverType instanceof JDefinedClassOrInterface) {
+    if (receiverType instanceof JDefinedClassOrInterface && mustTraceOverridingMethods) {
       ExtendingOrImplementingClassMarker marker =
           ((LocalMarkerManager) receiverType).getMarker(ExtendingOrImplementingClassMarker.class);
       if (marker != null) {
@@ -228,12 +238,12 @@
             JMethod implementation = findImplementation(mid, returnType, subClass);
             if (implementation != null) {
               trace(implementation);
+              setMustTraceOverridingMethods(implementation);
             }
           }
         }
       }
     }
-
   }
 
   protected void trace(@Nonnull JMethod m) {
@@ -313,7 +323,7 @@
       tracingStartingPoint = receiverType;
     }
     trace(tracingStartingPoint);
-    trace(methodId, tracingStartingPoint, returnType);
+    trace(methodId, tracingStartingPoint, returnType, true /* mustTraceOverridingMethods */);
   }
 
   @Override
@@ -321,7 +331,8 @@
     JClass returnType = newInstance.getType();
     trace(returnType);
     JMethodId methodId = newInstance.getMethodId();
-    trace(methodId, returnType, JPrimitiveTypeEnum.VOID.getType());
+    trace(methodId, returnType, JPrimitiveTypeEnum.VOID.getType(),
+        false /* mustTraceOverridingMethods */);
   }
 
   /**
diff --git a/jack/src/com/android/jack/shrob/shrink/TypeAndMemberLister.java b/jack/src/com/android/jack/shrob/shrink/TypeAndMemberLister.java
index 71fdd39..fa1d6d0 100644
--- a/jack/src/com/android/jack/shrob/shrink/TypeAndMemberLister.java
+++ b/jack/src/com/android/jack/shrob/shrink/TypeAndMemberLister.java
@@ -20,7 +20,7 @@
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JField;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.formatter.BinarySignatureFormatter;
 import com.android.jack.ir.formatter.TypeAndMethodFormatter;
@@ -48,13 +48,13 @@
 @HasKeyId
 @Description("lists all members and types")
 @Produce(TypeAndMemberListing.class)
-public class TypeAndMemberLister implements RunnableSchedulable<JProgram> {
+public class TypeAndMemberLister implements RunnableSchedulable<JSession> {
 
   @Nonnull
   public static final BooleanPropertyId TYPE_AND_MEMBER_LISTING = BooleanPropertyId.create(
       "jack.listing",
       "List all types and members")
-      .addDefaultValue("false");
+      .addDefaultValue(Boolean.FALSE);
 
   @Nonnull
   public static final PropertyId<StreamFile> TYPE_AND_MEMBER_LISTING_FILE = PropertyId.create(
@@ -122,7 +122,7 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram t) throws Exception {
+  public void run(@Nonnull JSession t) throws Exception {
     try {
       Visitor visitor = new Visitor();
       visitor.accept(t);
diff --git a/jack/src/com/android/jack/shrob/spec/MethodSpecification.java b/jack/src/com/android/jack/shrob/spec/MethodSpecification.java
index 71714c3..2ffffba 100644
--- a/jack/src/com/android/jack/shrob/spec/MethodSpecification.java
+++ b/jack/src/com/android/jack/shrob/spec/MethodSpecification.java
@@ -19,6 +19,7 @@
 import com.android.jack.ir.ast.JConstructor;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.shrob.proguard.GrammarActions;
+import com.android.jack.util.NamingTools;
 
 import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
@@ -57,12 +58,12 @@
 
     String signature = GrammarActions.getSignatureFormatter().getName(t);
     if (t instanceof JConstructor) {
-      String methodName = signature.replace("<init>", t.getEnclosingType().getName());
+      String methodName = signature.replace(NamingTools.INIT_NAME, t.getEnclosingType().getName());
       if (sigPattern.matches(methodName)) {
         return true;
       }
-      methodName = signature.replace(
-          "<init>", GrammarActions.getBinaryNameFormatter().getName(t.getEnclosingType()));
+      methodName = signature.replace(NamingTools.INIT_NAME,
+          GrammarActions.getBinaryNameFormatter().getName(t.getEnclosingType()));
       if (sigPattern.matches(methodName)) {
         return true;
       }
diff --git a/jack/src/com/android/jack/signature/GenericSignatureAction.java b/jack/src/com/android/jack/signature/GenericSignatureAction.java
index 6c276a6..8786f1d 100644
--- a/jack/src/com/android/jack/signature/GenericSignatureAction.java
+++ b/jack/src/com/android/jack/signature/GenericSignatureAction.java
@@ -16,20 +16,23 @@
 
 package com.android.jack.signature;
 
+import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
  * Actions triggered by the generic signature parser.
  */
-public interface GenericSignatureAction {
+public interface GenericSignatureAction<T> {
 
   public void parsedSymbol(char symbol);
 
   public void parsedIdentifier(@Nonnull String identifier);
 
-  public void parsedTypeName(@Nonnull String name);
+  @CheckForNull
+  public T parsedTypeName(@Nonnull String name);
 
-  public void parsedInnerTypeName(@Nonnull String name);
+  @CheckForNull
+  public T parsedInnerTypeName(@CheckForNull T enclosingType, @Nonnull String name);
 
   public void start();
 
diff --git a/jack/src/com/android/jack/signature/GenericSignatureParser.java b/jack/src/com/android/jack/signature/GenericSignatureParser.java
index 539a90c..07154f1 100644
--- a/jack/src/com/android/jack/signature/GenericSignatureParser.java
+++ b/jack/src/com/android/jack/signature/GenericSignatureParser.java
@@ -63,10 +63,10 @@
  * VoidDescriptor ::= "V".
  * </pre>
  */
-public class GenericSignatureParser {
+public class GenericSignatureParser<T> {
 
   @Nonnull
-  private final GenericSignatureAction actions;
+  private final GenericSignatureAction<T> actions;
 
   /*
    * Parser:
@@ -89,7 +89,7 @@
   @Nonnegative
   private int pos;
 
-  public GenericSignatureParser(@Nonnull GenericSignatureAction actions) {
+  public GenericSignatureParser(@Nonnull GenericSignatureAction<T> actions) {
     this.actions = actions;
   }
 
@@ -219,7 +219,7 @@
     String packageName;
 
     qualIdent.append(this.identifier);
-    actions.parsedTypeName(qualIdent.toString());
+    T parsedEnclosingType = actions.parsedTypeName(qualIdent.toString());
 
     updateOptTypeArguments();
 
@@ -229,7 +229,7 @@
       scanSymbol();
       scanIdentifier();
       assert identifier != null;
-      actions.parsedInnerTypeName(identifier);
+      parsedEnclosingType = actions.parsedInnerTypeName(parsedEnclosingType, identifier);
       updateOptTypeArguments();
     }
 
diff --git a/jack/src/com/android/jack/statistics/BlockCountMarker.java b/jack/src/com/android/jack/statistics/BlockCountMarker.java
index badcbc1..51ce558 100644
--- a/jack/src/com/android/jack/statistics/BlockCountMarker.java
+++ b/jack/src/com/android/jack/statistics/BlockCountMarker.java
@@ -16,7 +16,7 @@
 
 package com.android.jack.statistics;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.marker.Marker;
 import com.android.sched.marker.ValidOn;
@@ -28,7 +28,7 @@
  * Statistics about block and extra created block.
  */
 @Description("Statistics about block and extra created block.")
-@ValidOn(JProgram.class)
+@ValidOn(JSession.class)
 public class BlockCountMarker implements Marker {
 
   @Nonnegative
diff --git a/jack/src/com/android/jack/statistics/BlockStatistics.java b/jack/src/com/android/jack/statistics/BlockStatistics.java
index 3d320cd..1d9ea42 100644
--- a/jack/src/com/android/jack/statistics/BlockStatistics.java
+++ b/jack/src/com/android/jack/statistics/BlockStatistics.java
@@ -23,7 +23,7 @@
 import com.android.jack.ir.ast.JLabeledStatement;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JNode;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.ast.JWhileStatement;
 import com.android.sched.item.Description;
@@ -114,11 +114,11 @@
       return;
     }
 
-    JProgram jProgram = method.getEnclosingType().getJProgram();
-    BlockCountMarker bcm = jProgram.getMarker(BlockCountMarker.class);
+    JSession session = method.getEnclosingType().getSession();
+    BlockCountMarker bcm = session.getMarker(BlockCountMarker.class);
     if (bcm == null) {
       bcm = new BlockCountMarker();
-      jProgram.addMarker(bcm);
+      session.addMarker(bcm);
     }
 
     BlockStatisticsVisitor statistics = new BlockStatisticsVisitor(bcm);
diff --git a/jack/src/com/android/jack/transformations/AssertionTransformer.java b/jack/src/com/android/jack/transformations/AssertionTransformer.java
index a7b362a..c80233a 100644
--- a/jack/src/com/android/jack/transformations/AssertionTransformer.java
+++ b/jack/src/com/android/jack/transformations/AssertionTransformer.java
@@ -39,7 +39,6 @@
 import com.android.jack.ir.ast.JNewInstance;
 import com.android.jack.ir.ast.JPrefixNotOperation;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JThrowStatement;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
@@ -139,7 +138,7 @@
 
       // A.$assertionsDisabled = !A.class.desiredAssertionStatus();
       JClass javaLangClass =
-          Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS);
+          Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS);
       JClassLiteral thisClass = new JClassLiteral(sourceInfo, type, javaLangClass);
       JFieldRef lhs = new JFieldRef(sourceInfo, null, assertionStatusId, type);
       JExpression rhs = new JPrefixNotOperation(sourceInfo,
@@ -175,15 +174,15 @@
       List<JType> ctorDescriptor = new ArrayList<JType>();
       if (assertSt.getArg() != null) {
         ctorDescriptor.add(
-            Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT));
+            Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT));
       }
 
       JClass assertionError =
-          Jack.getProgram().getPhantomLookup()
+          Jack.getSession().getPhantomLookup()
               .getClass(CommonTypes.JAVA_LANG_ASSERTION_ERROR);
       JNewInstance newAssertionError = new JNewInstance(assertSt.getSourceInfo(),
           assertionError,
-          assertionError.getOrCreateMethodId(JProgram.INIT_NAME, ctorDescriptor,
+          assertionError.getOrCreateMethodId(NamingTools.INIT_NAME, ctorDescriptor,
               MethodKind.INSTANCE_NON_VIRTUAL));
 
       if (assertSt.getArg() != null) {
diff --git a/jack/src/com/android/jack/transformations/AssertionTransformerSchedulingSeparator.java b/jack/src/com/android/jack/transformations/AssertionTransformerSchedulingSeparator.java
index f782c67..e8fbe32 100644
--- a/jack/src/com/android/jack/transformations/AssertionTransformerSchedulingSeparator.java
+++ b/jack/src/com/android/jack/transformations/AssertionTransformerSchedulingSeparator.java
@@ -16,7 +16,7 @@
 
 package com.android.jack.transformations;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.item.Tag;
 import com.android.sched.schedulable.Constraint;
@@ -32,10 +32,10 @@
 @Description("A separation between AssertionTransformer and FieldInitializer")
 @Transform(remove = AssertionTransformerSchedulingSeparator.SeparatorTag.class)
 @Constraint(need = AssertionTransformerSchedulingSeparator.SeparatorTag.class)
-public class AssertionTransformerSchedulingSeparator implements RunnableSchedulable<JProgram> {
+public class AssertionTransformerSchedulingSeparator implements RunnableSchedulable<JSession> {
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     // do nothing
   }
 
diff --git a/jack/src/com/android/jack/transformations/EmptyClinitRemover.java b/jack/src/com/android/jack/transformations/EmptyClinitRemover.java
index b8969a2..9f1ab65 100644
--- a/jack/src/com/android/jack/transformations/EmptyClinitRemover.java
+++ b/jack/src/com/android/jack/transformations/EmptyClinitRemover.java
@@ -19,7 +19,6 @@
 import com.android.jack.Options;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JReturnStatement;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.transformations.request.Remove;
@@ -47,7 +46,7 @@
 
   @Override
   public void run(@Nonnull JMethod method) throws Exception {
-    if (JProgram.isClinit(method) && filter.accept(this.getClass(), method)) {
+    if (JMethod.isClinit(method) && filter.accept(this.getClass(), method)) {
       JMethodBody body = (JMethodBody) method.getBody();
       assert body != null;
       List<JStatement> stmts = body.getStatements();
diff --git a/jack/src/com/android/jack/transformations/FieldInitializer.java b/jack/src/com/android/jack/transformations/FieldInitializer.java
index 7cc840a..2089b6a 100644
--- a/jack/src/com/android/jack/transformations/FieldInitializer.java
+++ b/jack/src/com/android/jack/transformations/FieldInitializer.java
@@ -21,12 +21,12 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.shrob.obfuscation.OriginalNames;
 import com.android.jack.transformations.request.PrependStatement;
 import com.android.jack.transformations.request.TransformationRequest;
 import com.android.jack.transformations.threeaddresscode.ThreeAddressCodeForm;
+import com.android.jack.util.NamingTools;
 import com.android.sched.item.Description;
 import com.android.sched.schedulable.Constraint;
 import com.android.sched.schedulable.RunnableSchedulable;
@@ -58,7 +58,7 @@
       TransformationRequest request = new TransformationRequest(field);
 
       // Lookup for clinit
-      JMethod clinit = field.getEnclosingType().getMethod(JProgram.STATIC_INIT_NAME,
+      JMethod clinit = field.getEnclosingType().getMethod(NamingTools.STATIC_INIT_NAME,
           JPrimitiveTypeEnum.VOID.getType());
       JMethodBody body = (JMethodBody) clinit.getBody();
       assert body != null;
diff --git a/jack/src/com/android/jack/transformations/ast/CompoundAssignmentRemover.java b/jack/src/com/android/jack/transformations/ast/CompoundAssignmentRemover.java
index 5488d36..27d5c12 100644
--- a/jack/src/com/android/jack/transformations/ast/CompoundAssignmentRemover.java
+++ b/jack/src/com/android/jack/transformations/ast/CompoundAssignmentRemover.java
@@ -184,7 +184,7 @@
     }
 
     JClass javaLangString = method.getEnclosingType()
-        .getJProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
+        .getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
     TransformationRequest tr = new TransformationRequest(method);
     RemoveComplexAssignVisitor rca = new RemoveComplexAssignVisitor(tr, javaLangString);
     rca.accept(method);
diff --git a/jack/src/com/android/jack/transformations/ast/ConcatRemover.java b/jack/src/com/android/jack/transformations/ast/ConcatRemover.java
index 1ddbfa9..fe3ea56 100644
--- a/jack/src/com/android/jack/transformations/ast/ConcatRemover.java
+++ b/jack/src/com/android/jack/transformations/ast/ConcatRemover.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.transformations.ast;
 
-import com.android.jack.Jack;
 import com.android.jack.Options;
 import com.android.jack.ir.SourceInfo;
 import com.android.jack.ir.ast.JAsgConcatOperation;
@@ -33,7 +32,7 @@
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JPrimitiveType;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.ast.MethodKind;
@@ -42,6 +41,7 @@
 import com.android.jack.transformations.request.Replace;
 import com.android.jack.transformations.request.TransformationRequest;
 import com.android.jack.transformations.threeaddresscode.ThreeAddressCodeForm;
+import com.android.jack.util.NamingTools;
 import com.android.jack.util.filter.Filter;
 import com.android.sched.item.Description;
 import com.android.sched.schedulable.Constraint;
@@ -76,7 +76,7 @@
   private static final String CHAR_SEQUENCE_SIGNATURE = "Ljava/lang/CharSequence;";
 
   @Nonnull
-  private static final String STRING_BUILDER_CONSTRUCTOR_NAME = "<init>";
+  private static final String STRING_BUILDER_CONSTRUCTOR_NAME = NamingTools.INIT_NAME;
 
   @Nonnull
   private static final String TO_STRING = "toString";
@@ -84,7 +84,7 @@
   @Nonnull
   private final Filter<JMethod> filter = ThreadConfig.get(Options.METHOD_FILTER);
   @CheckForNull
-  private JProgram program;
+  private JSession session;
   @CheckForNull
   private JClassOrInterface stringBuilder;
   @CheckForNull
@@ -130,11 +130,12 @@
           JMethodId stringBuilderToString =
               stringBuilder.getOrCreateMethodId(TO_STRING, Lists.<JType>create(),
                   MethodKind.INSTANCE_VIRTUAL);
+          assert session != null;
           JMethodCall toString = new JMethodCall(sourceInfo,
               appendRhs,
               stringBuilder,
               stringBuilderToString,
-              Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING),
+              session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING),
               stringBuilderToString.canBeVirtual());
 
           tr.append(new Replace(binary, toString));
@@ -164,7 +165,7 @@
       return;
     }
 
-    program = enclosingType.getJProgram();
+    session = enclosingType.getSession();
 
     Visitor visitor = new Visitor(method);
     visitor.accept(method);
@@ -173,9 +174,9 @@
   @Nonnull
   private JClassOrInterface getStringBuilder() {
     if (stringBuilder == null) {
-      assert program != null;
+      assert session != null;
       stringBuilder =
-          (JClassOrInterface) program.getPhantomLookup().getType(STRING_BUILDER_SIGNATURE);
+          (JClassOrInterface) session.getPhantomLookup().getType(STRING_BUILDER_SIGNATURE);
     }
 
     assert stringBuilder != null;
@@ -185,9 +186,9 @@
   @Nonnull
   private JClassOrInterface getCharSequence() {
     if (charSequence == null) {
-      assert program != null;
+      assert session != null;
       charSequence =
-          (JClassOrInterface) program.getPhantomLookup().getType(CHAR_SEQUENCE_SIGNATURE);
+          (JClassOrInterface) session.getPhantomLookup().getType(CHAR_SEQUENCE_SIGNATURE);
     }
 
     assert charSequence != null;
@@ -202,6 +203,7 @@
 
     JType appendArgType = elementType;
 
+    assert session != null;
     if (elementType instanceof JPrimitiveType) {
       JPrimitiveTypeEnum primitiveType = ((JPrimitiveType) elementType).getPrimitiveTypeEnum();
       switch (primitiveType) {
@@ -224,14 +226,15 @@
           throw new AssertionError();
       }
     } else if (elementType
-        == Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING)) {
-      appendArgType = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
+        == session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING)) {
+      appendArgType = session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING);
     } else {
       JType charSequence = getCharSequence();
+      assert session != null; // FINDBUGS
       if (elementType == charSequence){
         appendArgType = charSequence;
       } else {
-        appendArgType = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+        appendArgType = session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
       }
     }
 
diff --git a/jack/src/com/android/jack/transformations/ast/MultiDimensionNewArrayRemover.java b/jack/src/com/android/jack/transformations/ast/MultiDimensionNewArrayRemover.java
index e3dde54..237cabb 100644
--- a/jack/src/com/android/jack/transformations/ast/MultiDimensionNewArrayRemover.java
+++ b/jack/src/com/android/jack/transformations/ast/MultiDimensionNewArrayRemover.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.transformations.ast;
 
-import com.android.jack.Jack;
 import com.android.jack.Options;
 import com.android.jack.ir.SourceInfo;
 import com.android.jack.ir.ast.JAbsentArrayDimension;
@@ -30,7 +29,7 @@
 import com.android.jack.ir.ast.JMethodCall;
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JNewArray;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.ast.MethodKind;
@@ -78,13 +77,13 @@
     @CheckForNull
     private JClassOrInterface reflectArray;
     @Nonnull
-    private final JProgram program;
+    private final JSession session;
     @CheckForNull
     private JMethodId newInstance;
 
-    public Visitor(@Nonnull TransformationRequest tr, @Nonnull JProgram program) {
+    public Visitor(@Nonnull TransformationRequest tr, @Nonnull JSession session) {
       this.tr = tr;
-      this.program = program;
+      this.session = session;
     }
 
     @Override
@@ -99,11 +98,11 @@
           JClassOrInterface reflectArrayType = getReflectArrayType();
           JMethodId newInstanceId = getNewInstanceId(reflectArrayType);
           JMethodCall call = new JMethodCall(sourceInfo, null, reflectArrayType, newInstanceId,
-              Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT),
+              session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT),
               newInstanceId.canBeVirtual());
           call.addArg(new JClassLiteral(
               sourceInfo, getComponentTypeForNewInstance(newArray, nbPresentDimensions),
-              program.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS)));
+              session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS)));
          call.addArg(JNewArray.createWithInits(sourceInfo, getIntArrayType(), presentDimensions));
           tr.append(new Replace(newArray, new JDynamicCastOperation(sourceInfo, newArray
               .getArrayType(), call)));
@@ -116,7 +115,7 @@
     private JMethodId getNewInstanceId(JClassOrInterface reflectArrayType) {
       if (newInstance == null) {
         List<JType> argsType = new ArrayList<JType>(2);
-        argsType.add(Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS));
+        argsType.add(session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS));
         argsType.add(getIntArrayType());
         newInstance = reflectArrayType.getOrCreateMethodId("newInstance", argsType,
             MethodKind.STATIC);
@@ -163,7 +162,7 @@
     private JClassOrInterface getReflectArrayType() {
       if (reflectArray == null) {
         reflectArray =
-            (JClassOrInterface) program.getPhantomLookup().getType("Ljava/lang/reflect/Array;");
+            (JClassOrInterface) session.getPhantomLookup().getType("Ljava/lang/reflect/Array;");
       }
 
       assert reflectArray != null;
@@ -176,7 +175,7 @@
     @Nonnull
     private JArrayType getIntArrayType() {
       if (intArrayType == null) {
-        intArrayType = (JArrayType) program.getLookup().getType("[I");
+        intArrayType = (JArrayType) session.getLookup().getType("[I");
       }
 
       assert intArrayType != null;
@@ -194,7 +193,7 @@
     }
 
     TransformationRequest tr = new TransformationRequest(method);
-    Visitor visitor = new Visitor(tr, enclosingType.getJProgram());
+    Visitor visitor = new Visitor(tr, enclosingType.getSession());
     visitor.accept(method);
     tr.commit();
   }
diff --git a/jack/src/com/android/jack/transformations/ast/PrimitiveClassTransformer.java b/jack/src/com/android/jack/transformations/ast/PrimitiveClassTransformer.java
index 3dc01ac..78df2ac 100644
--- a/jack/src/com/android/jack/transformations/ast/PrimitiveClassTransformer.java
+++ b/jack/src/com/android/jack/transformations/ast/PrimitiveClassTransformer.java
@@ -75,7 +75,7 @@
         JClass receiverType = getType((JPrimitiveType) classLiteral.getRefType());
         JFieldRef fieldAccess = new JFieldRef(classLiteral.getSourceInfo(),
             null, receiverType.getFieldId(FIELD_TYPE_NAME,
-                Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS),
+                Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS),
                 FieldKind.STATIC), receiverType);
         tr.append(new Replace(classLiteral, fieldAccess));
       }
@@ -86,7 +86,7 @@
     // available.
     @Nonnull
     private JClass getType(@Nonnull JPrimitiveType primType) {
-      JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+      JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
       switch (primType.getPrimitiveTypeEnum()) {
         case BOOLEAN:
           return lookup.getClass(CommonTypes.JAVA_LANG_BOOLEAN);
diff --git a/jack/src/com/android/jack/transformations/ast/SynchronizeTransformer.java b/jack/src/com/android/jack/transformations/ast/SynchronizeTransformer.java
index d70020e..854aedb 100644
--- a/jack/src/com/android/jack/transformations/ast/SynchronizeTransformer.java
+++ b/jack/src/com/android/jack/transformations/ast/SynchronizeTransformer.java
@@ -33,7 +33,7 @@
 import com.android.jack.ir.ast.JLock;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JSynchronizedBlock;
 import com.android.jack.ir.ast.JThisRef;
@@ -91,7 +91,7 @@
   public static final BooleanPropertyId REUSE_SYNC_VARIABLE = BooleanPropertyId.create(
       "jack.transformation.reusesyncvariable",
       "Reduce the 'get class' usage in static synchronized methods by reusing a local variable")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   private final boolean reuseSyncVariable = ThreadConfig.get(REUSE_SYNC_VARIABLE).booleanValue();
 
@@ -100,15 +100,15 @@
     @Nonnull
     private final TransformationRequest tr;
     @Nonnull
-    private final JProgram program;
+    private final JSession session;
     @Nonnull
     private final LocalVarCreator lvCreator;
 
-    public Visitor(@Nonnull TransformationRequest tr, @Nonnull JProgram program,
+    public Visitor(@Nonnull TransformationRequest tr, @Nonnull JSession session,
         @Nonnull LocalVarCreator lvCreator) {
       this.tr = tr;
       this.lvCreator = lvCreator;
-      this.program = program;
+      this.session = session;
     }
 
     @Override
@@ -202,7 +202,7 @@
 
     @Nonnull
     private JClass getJLClass() {
-      return program.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS);
+      return session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CLASS);
     }
   }
 
@@ -216,7 +216,7 @@
 
     TransformationRequest tr = new TransformationRequest(method);
     LocalVarCreator lvCreator = new LocalVarCreator(method, "sync");
-    Visitor visitor = new Visitor(tr, enclosingType.getJProgram(), lvCreator);
+    Visitor visitor = new Visitor(tr, enclosingType.getSession(), lvCreator);
     visitor.accept(method);
     tr.commit();
   }
diff --git a/jack/src/com/android/jack/transformations/ast/TryWithResourcesTransformer.java b/jack/src/com/android/jack/transformations/ast/TryWithResourcesTransformer.java
index f40594c..c5a9104 100644
--- a/jack/src/com/android/jack/transformations/ast/TryWithResourcesTransformer.java
+++ b/jack/src/com/android/jack/transformations/ast/TryWithResourcesTransformer.java
@@ -138,7 +138,7 @@
         JBlock finalTryBlock = new JBlock(x.getSourceInfo());
 
         // Declare exception to throw in the end, if any, and initialize it to null;
-        JClass throwableClass = Jack.getProgram().getPhantomLookup().getClass(THROWABLE_SIGNATURE);
+        JClass throwableClass = Jack.getSession().getPhantomLookup().getClass(THROWABLE_SIGNATURE);
         JLocal exceptionToThrow =
             localVarCreator.createTempLocal(throwableClass, firstLineSourceInfos, request);
         JAsgOperation assign = new JAsgOperation(
@@ -184,7 +184,7 @@
 
         // Lookup AutoCloseable.close() method
         JInterface autoCloseableInterface =
-            Jack.getProgram().getPhantomLookup().getInterface(AUTO_CLOSEABLE_SIGNATURE);
+            Jack.getSession().getPhantomLookup().getInterface(AUTO_CLOSEABLE_SIGNATURE);
         JMethodId closeMethodId = autoCloseableInterface.getMethodId(
             CLOSE_METHOD_NAME, Collections.<JType>emptyList(), MethodKind.INSTANCE_VIRTUAL);
 
diff --git a/jack/src/com/android/jack/transformations/ast/TypeLegalizer.java b/jack/src/com/android/jack/transformations/ast/TypeLegalizer.java
index 3bfe0a3..5a7a069 100644
--- a/jack/src/com/android/jack/transformations/ast/TypeLegalizer.java
+++ b/jack/src/com/android/jack/transformations/ast/TypeLegalizer.java
@@ -353,7 +353,7 @@
       String methodName;
       JType returnType;
 
-      JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+      JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
 
       if (isBoxingType(lookup, typeToUnbox, CommonTypes.JAVA_LANG_BOOLEAN)) {
         methodName = "booleanValue";
@@ -408,7 +408,7 @@
         @Nonnull JPrimitiveType pType) {
       JClassOrInterface wrapperType = type;
       JType argType;
-      JPhantomLookup lookup = Jack.getProgram().getPhantomLookup();
+      JPhantomLookup lookup = Jack.getSession().getPhantomLookup();
       if (isBoxingType(lookup, wrapperType, CommonTypes.JAVA_LANG_BOOLEAN)) {
         argType = JPrimitiveTypeEnum.BOOLEAN.getType();
       } else if (isBoxingType(lookup, wrapperType, CommonTypes.JAVA_LANG_BYTE)) {
diff --git a/jack/src/com/android/jack/transformations/ast/inner/InnerAccessorSchedulingSeparator.java b/jack/src/com/android/jack/transformations/ast/inner/InnerAccessorSchedulingSeparator.java
index 86e7d3d..08d7b00 100644
--- a/jack/src/com/android/jack/transformations/ast/inner/InnerAccessorSchedulingSeparator.java
+++ b/jack/src/com/android/jack/transformations/ast/inner/InnerAccessorSchedulingSeparator.java
@@ -16,7 +16,7 @@
 
 package com.android.jack.transformations.ast.inner;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.item.Tag;
 import com.android.sched.schedulable.Constraint;
@@ -32,10 +32,10 @@
 @Description("A separation between InnerAccessorGenerator and InnerAccessorAdder")
 @Transform(remove = InnerAccessorSchedulingSeparator.SeparatorTag.class)
 @Constraint(need = InnerAccessorSchedulingSeparator.SeparatorTag.class)
-public class InnerAccessorSchedulingSeparator implements RunnableSchedulable<JProgram> {
+public class InnerAccessorSchedulingSeparator implements RunnableSchedulable<JSession> {
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     // do nothing
   }
 
diff --git a/jack/src/com/android/jack/transformations/ast/string/FieldGenericSignatureSplitter.java b/jack/src/com/android/jack/transformations/ast/string/FieldGenericSignatureSplitter.java
index a7a2dba..9178b5f 100644
--- a/jack/src/com/android/jack/transformations/ast/string/FieldGenericSignatureSplitter.java
+++ b/jack/src/com/android/jack/transformations/ast/string/FieldGenericSignatureSplitter.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.ir.ast.JAbstractStringLiteral;
 import com.android.jack.ir.ast.JField;
+import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.marker.OriginalTypeInfo;
 import com.android.jack.signature.GenericSignatureParser;
 import com.android.sched.item.Description;
@@ -44,7 +45,7 @@
       JAbstractStringLiteral oldSignature = marker.getGenericSignature();
       if (oldSignature != null) {
         GenericSignatureRefiner parserActions = new GenericSignatureRefiner();
-        GenericSignatureParser parser = new GenericSignatureParser(parserActions);
+        GenericSignatureParser<JType> parser = new GenericSignatureParser<JType>(parserActions);
         String strOldSignature = oldSignature.getValue();
         parser.parseFieldSignature(strOldSignature);
         assert parserActions.getNewSignature().getValue().equals(strOldSignature);
diff --git a/jack/src/com/android/jack/transformations/ast/string/GenericSignatureRefiner.java b/jack/src/com/android/jack/transformations/ast/string/GenericSignatureRefiner.java
index 9290304..b833d7c 100644
--- a/jack/src/com/android/jack/transformations/ast/string/GenericSignatureRefiner.java
+++ b/jack/src/com/android/jack/transformations/ast/string/GenericSignatureRefiner.java
@@ -21,8 +21,11 @@
 import com.android.jack.ir.ast.JAbstractStringLiteral;
 import com.android.jack.ir.ast.JCompositeStringLiteral;
 import com.android.jack.ir.ast.JStringLiteral;
+import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.JTypeStringLiteral;
 import com.android.jack.ir.ast.JTypeStringLiteral.Kind;
+import com.android.jack.ir.formatter.BinaryQualifiedNameFormatter;
+import com.android.jack.ir.formatter.TypeFormatter;
 import com.android.jack.lookup.JLookup;
 import com.android.jack.lookup.JLookupException;
 import com.android.jack.shrob.obfuscation.OriginalNames;
@@ -39,7 +42,7 @@
  */
 @Constraint(need = OriginalNames.class)
 @Transform(add = {JTypeStringLiteral.class, JCompositeStringLiteral.class, JStringLiteral.class})
-public class GenericSignatureRefiner implements GenericSignatureAction {
+public class GenericSignatureRefiner implements GenericSignatureAction<JType> {
 
   @CheckForNull
   private JAbstractStringLiteral jstringLiteral = null;
@@ -50,8 +53,11 @@
   @Nonnull
   private final  JLookup jlookup;
 
+  @Nonnull
+  private final TypeFormatter formatter = BinaryQualifiedNameFormatter.getFormatter();
+
   public GenericSignatureRefiner() {
-    jlookup = Jack.getProgram().getLookup();
+    jlookup = Jack.getSession().getLookup();
   }
 
   @Override
@@ -65,27 +71,36 @@
   }
 
   @Override
-  public void parsedTypeName(@Nonnull String name) {
+  @CheckForNull
+  public JType parsedTypeName(@Nonnull String name) {
     updateJStringLiteral(getJStringLiteralFromBuffer());
     try {
-    updateJStringLiteral(new JTypeStringLiteral(SourceOrigin.UNKNOWN, Kind.BINARY_QN, jlookup
-        .getType(NamingTools.getTypeSignatureName(name))));
+      JType type = jlookup.getType(NamingTools.getTypeSignatureName(name));
+      updateJStringLiteral(new JTypeStringLiteral(SourceOrigin.UNKNOWN, Kind.BINARY_QN, type));
+      return type;
     } catch (JLookupException e) {
-      // Type not found, kept it as a JStringLiteral
+      // Type not found, keep it as a JStringLiteral
       updateJStringLiteral(new JStringLiteral(SourceOrigin.UNKNOWN, name));
+      return null;
     }
   }
 
   @Override
-  public void parsedInnerTypeName(@Nonnull String name) {
+  @CheckForNull
+  public JType parsedInnerTypeName(@CheckForNull JType enclosingType, @Nonnull String name) {
     updateJStringLiteral(getJStringLiteralFromBuffer());
-    try {
-      updateJStringLiteral(new JTypeStringLiteral(SourceOrigin.UNKNOWN, Kind.SIMPLE_NAME,
-          jlookup.getType(NamingTools.getTypeSignatureName(name))));
-    } catch (JLookupException e) {
-      // Type not found, kept it as a JStringLiteral
-      updateJStringLiteral(new JStringLiteral(SourceOrigin.UNKNOWN, name));
+    if (enclosingType != null) {
+      try {
+        JType type = jlookup.getType(NamingTools.getTypeSignatureName(
+            formatter.getName(enclosingType) + '$' + name));
+        updateJStringLiteral(new JTypeStringLiteral(SourceOrigin.UNKNOWN, Kind.SIMPLE_NAME, type));
+        return type;
+      } catch (JLookupException e) {
+        // Type not found, keep it as a JStringLiteral
+      }
     }
+    updateJStringLiteral(new JStringLiteral(SourceOrigin.UNKNOWN, name));
+    return null;
   }
 
   @Override
diff --git a/jack/src/com/android/jack/transformations/ast/string/MethodGenericSignatureSplitter.java b/jack/src/com/android/jack/transformations/ast/string/MethodGenericSignatureSplitter.java
index d37aa5b..d5ecc79 100644
--- a/jack/src/com/android/jack/transformations/ast/string/MethodGenericSignatureSplitter.java
+++ b/jack/src/com/android/jack/transformations/ast/string/MethodGenericSignatureSplitter.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.ir.ast.JAbstractStringLiteral;
 import com.android.jack.ir.ast.JMethod;
+import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.marker.OriginalTypeInfo;
 import com.android.jack.signature.GenericSignatureParser;
 import com.android.sched.item.Description;
@@ -44,7 +45,7 @@
       JAbstractStringLiteral oldSignature = marker.getGenericSignature();
       if (oldSignature != null) {
         GenericSignatureRefiner parserActions = new GenericSignatureRefiner();
-        GenericSignatureParser parser = new GenericSignatureParser(parserActions);
+        GenericSignatureParser<JType> parser = new GenericSignatureParser<JType>(parserActions);
         String strOldSignature = oldSignature.getValue();
         parser.parseMethodSignature(strOldSignature);
         assert parserActions.getNewSignature().getValue().equals(strOldSignature);
diff --git a/jack/src/com/android/jack/transformations/ast/string/StringLiteralRefinerVisitor.java b/jack/src/com/android/jack/transformations/ast/string/StringLiteralRefinerVisitor.java
index 849d541..5935b38 100644
--- a/jack/src/com/android/jack/transformations/ast/string/StringLiteralRefinerVisitor.java
+++ b/jack/src/com/android/jack/transformations/ast/string/StringLiteralRefinerVisitor.java
@@ -52,7 +52,7 @@
 
   public StringLiteralRefinerVisitor(@Nonnull TransformationRequest tr) {
     this.tr = tr;
-    lookup = Jack.getProgram().getLookup();
+    lookup = Jack.getSession().getLookup();
   }
 
   @Override
diff --git a/jack/src/com/android/jack/transformations/ast/string/TypeGenericSignatureSplitter.java b/jack/src/com/android/jack/transformations/ast/string/TypeGenericSignatureSplitter.java
index dd61df6..0ddb569 100644
--- a/jack/src/com/android/jack/transformations/ast/string/TypeGenericSignatureSplitter.java
+++ b/jack/src/com/android/jack/transformations/ast/string/TypeGenericSignatureSplitter.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.ir.ast.JAbstractStringLiteral;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
+import com.android.jack.ir.ast.JType;
 import com.android.jack.ir.ast.marker.OriginalTypeInfo;
 import com.android.jack.ir.ast.marker.ThisRefTypeInfo;
 import com.android.jack.signature.GenericSignatureParser;
@@ -71,7 +72,7 @@
     }
 
     GenericSignatureRefiner parserActions = new GenericSignatureRefiner();
-    GenericSignatureParser parser = new GenericSignatureParser(parserActions);
+    GenericSignatureParser<JType> parser = new GenericSignatureParser<JType>(parserActions);
     String strOldSignature = oldSignature.getValue();
     parser.parseClassSignature(strOldSignature);
     assert parserActions.getNewSignature().getValue().equals(strOldSignature);
diff --git a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicLongIntUpdaterParameterRefiner.java b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicLongIntUpdaterParameterRefiner.java
index 8fb4919..6f0a84a 100644
--- a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicLongIntUpdaterParameterRefiner.java
+++ b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicLongIntUpdaterParameterRefiner.java
@@ -45,12 +45,12 @@
 
   @Nonnull
   private final JClassOrInterface atomicIntegerFieldUpdater =
-      (JClassOrInterface) Jack.getProgram().getPhantomLookup()
+      (JClassOrInterface) Jack.getSession().getPhantomLookup()
           .getType(CommonTypes.JAVA_UTIL_CONCURRENT_ATOMIC_ATOMICINTEGERFIELDUPDATER);
 
   @Nonnull
   private final JClassOrInterface atomicLongFieldUpdater =
-      (JClassOrInterface) Jack.getProgram().getPhantomLookup()
+      (JClassOrInterface) Jack.getSession().getPhantomLookup()
           .getType(CommonTypes.JAVA_UTIL_CONCURRENT_ATOMIC_ATOMICLONGFIELDUPDATER);
 
   @Override
diff --git a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicReferenceUpdaterParameterRefiner.java b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicReferenceUpdaterParameterRefiner.java
index b77e853..8ff706f 100644
--- a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicReferenceUpdaterParameterRefiner.java
+++ b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/AtomicReferenceUpdaterParameterRefiner.java
@@ -35,7 +35,7 @@
 
   @Nonnull
   private final JClassOrInterface atomicFieldUpdater =
-      (JClassOrInterface) Jack.getProgram().getPhantomLookup()
+      (JClassOrInterface) Jack.getSession().getPhantomLookup()
           .getType(CommonTypes.JAVA_UTIL_CONCURRENT_ATOMIC_ATOMICREFERENCEFIELDUPDATER);
 
   @Override
diff --git a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/CommonStringParameterRefiner.java b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/CommonStringParameterRefiner.java
index 5fd7483..e141bee 100644
--- a/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/CommonStringParameterRefiner.java
+++ b/jack/src/com/android/jack/transformations/ast/string/parameterrefiners/CommonStringParameterRefiner.java
@@ -66,8 +66,8 @@
   protected static final TypeFormatter formatter = BinarySignatureFormatter.getFormatter();
 
   CommonStringParameterRefiner() {
-    lookup = Jack.getProgram().getLookup();
-    JPhantomLookup phantomLookup = Jack.getProgram().getPhantomLookup();
+    lookup = Jack.getSession().getLookup();
+    JPhantomLookup phantomLookup = Jack.getSession().getPhantomLookup();
     javaLangClass = phantomLookup.getClass(CommonTypes.JAVA_LANG_CLASS);
     javaLangString = phantomLookup.getClass(CommonTypes.JAVA_LANG_STRING);
     javaLangClassArray = javaLangClass.getArray();
diff --git a/jack/src/com/android/jack/transformations/ast/switches/SwitchStringSupport.java b/jack/src/com/android/jack/transformations/ast/switches/SwitchStringSupport.java
index 35479ea..68d6aa3 100644
--- a/jack/src/com/android/jack/transformations/ast/switches/SwitchStringSupport.java
+++ b/jack/src/com/android/jack/transformations/ast/switches/SwitchStringSupport.java
@@ -37,7 +37,7 @@
 import com.android.jack.ir.ast.JMethodCall;
 import com.android.jack.ir.ast.JMethodId;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JSwitchStatement;
 import com.android.jack.ir.ast.JType;
@@ -96,8 +96,8 @@
 
     public Visitor(@Nonnull TransformationRequest tr, @Nonnull JMethod method) {
       this.tr = tr;
-      JProgram program = method.getEnclosingType().getJProgram();
-      JPhantomLookup lookup = program.getPhantomLookup();
+      JSession session = method.getEnclosingType().getSession();
+      JPhantomLookup lookup = session.getPhantomLookup();
       JClass jlo = lookup.getClass(CommonTypes.JAVA_LANG_OBJECT);
       JClass jls = lookup.getClass(CommonTypes.JAVA_LANG_STRING);
       equalsMethodId =
diff --git a/jack/src/com/android/jack/transformations/enums/EnumMappingSchedulingSeparator.java b/jack/src/com/android/jack/transformations/enums/EnumMappingSchedulingSeparator.java
index 87724bc..b2041cd 100644
--- a/jack/src/com/android/jack/transformations/enums/EnumMappingSchedulingSeparator.java
+++ b/jack/src/com/android/jack/transformations/enums/EnumMappingSchedulingSeparator.java
@@ -16,7 +16,7 @@
 
 package com.android.jack.transformations.enums;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.item.Tag;
 import com.android.sched.schedulable.Constraint;
@@ -32,10 +32,10 @@
 @Description("A separation between SwitchEnumSupport and EnumMappingMarkerRemover")
 @Transform(remove = EnumMappingSchedulingSeparator.SeparatorTag.class)
 @Constraint(need = EnumMappingSchedulingSeparator.SeparatorTag.class)
-public class EnumMappingSchedulingSeparator implements RunnableSchedulable<JProgram> {
+public class EnumMappingSchedulingSeparator implements RunnableSchedulable<JSession> {
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     // do nothing
   }
 
diff --git a/jack/src/com/android/jack/transformations/enums/SwitchEnumSupport.java b/jack/src/com/android/jack/transformations/enums/SwitchEnumSupport.java
index 13b564a..35c3383 100644
--- a/jack/src/com/android/jack/transformations/enums/SwitchEnumSupport.java
+++ b/jack/src/com/android/jack/transformations/enums/SwitchEnumSupport.java
@@ -159,7 +159,7 @@
         @Nonnull JDefinedClassOrInterface currentClass) {
       this.tr = tr;
       this.currentClass = currentClass;
-      this.lookup = Jack.getProgram().getPhantomLookup();
+      this.lookup = Jack.getSession().getPhantomLookup();
     }
 
     @Override
diff --git a/jack/src/com/android/jack/transformations/exceptions/TryCatchRemover.java b/jack/src/com/android/jack/transformations/exceptions/TryCatchRemover.java
index 3776b79..19edd3f 100644
--- a/jack/src/com/android/jack/transformations/exceptions/TryCatchRemover.java
+++ b/jack/src/com/android/jack/transformations/exceptions/TryCatchRemover.java
@@ -209,7 +209,7 @@
           int catchTypesCount = catchTypes.size();
 
           for (JClass catchedType : bb.getCatchTypes()) {
-            if (catchedType == Jack.getProgram().getPhantomLookup()
+            if (catchedType == Jack.getSession().getPhantomLookup()
                 .getClass(CommonTypes.JAVA_LANG_OBJECT)) {
               assert bb.getCatchTypes().size() == 1;
               stmt.appendCatchBlock(bb);
diff --git a/jack/src/com/android/jack/transformations/exceptions/TryStatementSchedulingSeparator.java b/jack/src/com/android/jack/transformations/exceptions/TryStatementSchedulingSeparator.java
index 3439b18..a6b42f2 100644
--- a/jack/src/com/android/jack/transformations/exceptions/TryStatementSchedulingSeparator.java
+++ b/jack/src/com/android/jack/transformations/exceptions/TryStatementSchedulingSeparator.java
@@ -16,7 +16,7 @@
 
 package com.android.jack.transformations.exceptions;
 
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.item.Description;
 import com.android.sched.item.Tag;
 import com.android.sched.schedulable.Constraint;
@@ -33,10 +33,10 @@
 @Description("A separation between a Schedulable and TryCatchRemover")
 @Transform(remove = TryStatementSchedulingSeparator.SeparatorTag.class)
 @Constraint(need = TryStatementSchedulingSeparator.SeparatorTag.class)
-public class TryStatementSchedulingSeparator implements RunnableSchedulable<JProgram> {
+public class TryStatementSchedulingSeparator implements RunnableSchedulable<JSession> {
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     // do nothing
   }
 
diff --git a/jack/src/com/android/jack/transformations/finallyblock/FinallyRemover.java b/jack/src/com/android/jack/transformations/finallyblock/FinallyRemover.java
index 70c72e1..1605145 100644
--- a/jack/src/com/android/jack/transformations/finallyblock/FinallyRemover.java
+++ b/jack/src/com/android/jack/transformations/finallyblock/FinallyRemover.java
@@ -410,7 +410,7 @@
     JDefinedClassOrInterface enclosingType = method.getEnclosingType();
     assert enclosingType != null;
 
-    JClass throwableType = enclosingType.getJProgram().getPhantomLookup().getClass(
+    JClass throwableType = enclosingType.getSession().getPhantomLookup().getClass(
         CommonTypes.JAVA_LANG_OBJECT);
 
     TransformationRequest trRequest = new TransformationRequest(method);
diff --git a/jack/src/com/android/jack/transformations/flow/FlowNormalizerSchedulingSeparator.java b/jack/src/com/android/jack/transformations/flow/FlowNormalizerSchedulingSeparator.java
index a6408fe..2a7bc3c 100644
--- a/jack/src/com/android/jack/transformations/flow/FlowNormalizerSchedulingSeparator.java
+++ b/jack/src/com/android/jack/transformations/flow/FlowNormalizerSchedulingSeparator.java
@@ -40,7 +40,7 @@
   implements RunnableSchedulable<JDefinedClassOrInterface> {
 
   @Override
-  public void run(@Nonnull JDefinedClassOrInterface program) throws Exception {
+  public void run(@Nonnull JDefinedClassOrInterface coi) throws Exception {
     // do nothing
   }
   /**
diff --git a/jack/src/com/android/jack/transformations/parent/PackageChecker.java b/jack/src/com/android/jack/transformations/parent/PackageChecker.java
index f6a22b7..5026149 100644
--- a/jack/src/com/android/jack/transformations/parent/PackageChecker.java
+++ b/jack/src/com/android/jack/transformations/parent/PackageChecker.java
@@ -19,7 +19,7 @@
 import com.android.jack.ir.ast.JClassOrInterface;
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.transformations.SanityChecks;
 import com.android.sched.item.Description;
 import com.android.sched.item.Name;
@@ -49,7 +49,7 @@
     }
 
     JNode parent = pack.getParent();
-    if (parent instanceof JProgram) {
+    if (parent instanceof JSession) {
       if (pack.getEnclosingPackage() != null) {
         throw new AssertionError("Wrong enclosing package");
       }
diff --git a/jack/src/com/android/jack/transformations/parent/ParentSetterChecker.java b/jack/src/com/android/jack/transformations/parent/ParentSetterChecker.java
index e48119c..53bd662 100644
--- a/jack/src/com/android/jack/transformations/parent/ParentSetterChecker.java
+++ b/jack/src/com/android/jack/transformations/parent/ParentSetterChecker.java
@@ -17,7 +17,7 @@
 package com.android.jack.transformations.parent;
 
 import com.android.jack.ir.ast.JNode;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.transformations.SanityChecks;
 import com.android.sched.item.Description;
@@ -35,7 +35,7 @@
 @Description("Check that parent of JNode are correctly set.")
 @Name("ParentSetterChecker")
 @Support(SanityChecks.class)
-public class ParentSetterChecker implements RunnableSchedulable<JProgram> {
+public class ParentSetterChecker implements RunnableSchedulable<JSession> {
 
   private static class ParentSetterCheckerVisitor extends JVisitor {
     @Nonnull
@@ -47,9 +47,9 @@
 
     @Override
     public boolean visit(@Nonnull JNode node) {
-      if (node instanceof JProgram) {
+      if (node instanceof JSession) {
         if (node.getParent() != null) {
-          throw new AssertionError("Parent of JProgram must be null.");
+          throw new AssertionError("Parent of JSession must be null.");
         }
       } else {
         if (node.getParent() != nodes.peek()) {
@@ -71,8 +71,8 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     ParentSetterCheckerVisitor checker = new ParentSetterCheckerVisitor();
-    checker.accept(program);
+    checker.accept(session);
   }
 }
\ No newline at end of file
diff --git a/jack/src/com/android/jack/transformations/renamepackage/PackageRenamer.java b/jack/src/com/android/jack/transformations/renamepackage/PackageRenamer.java
index 3cdcf81..7aa2ac5 100644
--- a/jack/src/com/android/jack/transformations/renamepackage/PackageRenamer.java
+++ b/jack/src/com/android/jack/transformations/renamepackage/PackageRenamer.java
@@ -23,7 +23,7 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JStringLiteral;
 import com.android.jack.ir.ast.JVisitor;
 import com.android.jack.ir.formatter.BinaryQualifiedNameFormatter;
@@ -61,7 +61,7 @@
 @Name("PackageRenamer")
 @Support(Jarjar.class)
 @Transform(add = {JStringLiteral.class, JPackage.class}, modify = JDefinedClassOrInterface.class)
-public class PackageRenamer implements RunnableSchedulable<JProgram>{
+public class PackageRenamer implements RunnableSchedulable<JSession>{
 
   @Nonnull
   public static final PropertyId<File> JARJAR_FILE = PropertyId.create(
@@ -79,7 +79,7 @@
     private final Stack<JNode> transformationRequestRoot = new Stack<JNode>();
 
     @Nonnull
-    private final JLookup lookup = Jack.getProgram().getLookup();
+    private final JLookup lookup = Jack.getSession().getLookup();
     @Nonnull
     private final TypeFormatter formatter = BinaryQualifiedNameFormatter.getFormatter();
 
@@ -139,11 +139,11 @@
   }
 
   @Override
-  public void run(@Nonnull JProgram program) throws Exception {
+  public void run(@Nonnull JSession session) throws Exception {
     List<PatternElement> result = RulesFileParser.parse(jarjarRulesFile);
     List<Wildcard> wildcards = PatternElement.createWildcards(result);
-    new Visitor(wildcards).accept(program);
-    program.getLookup().clear();
-    program.getPhantomLookup().clear();
+    new Visitor(wildcards).accept(session);
+    session.getLookup().clear();
+    session.getPhantomLookup().clear();
   }
 }
diff --git a/jack/src/com/android/jack/transformations/request/ChangeEnclosingPackage.java b/jack/src/com/android/jack/transformations/request/ChangeEnclosingPackage.java
index bf1e762..af93961 100644
--- a/jack/src/com/android/jack/transformations/request/ChangeEnclosingPackage.java
+++ b/jack/src/com/android/jack/transformations/request/ChangeEnclosingPackage.java
@@ -20,7 +20,7 @@
 import com.android.jack.ir.ast.HasEnclosingPackage;
 import com.android.jack.ir.ast.JNode;
 import com.android.jack.ir.ast.JPackage;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.sched.transform.TransformStep;
 
 import javax.annotation.Nonnull;
@@ -37,11 +37,11 @@
   private final HasEnclosingPackage existingNode;
 
   @Nonnull
-  private final JProgram program = Jack.getProgram();
+  private final JSession session = Jack.getSession();
 
   public ChangeEnclosingPackage(
       @Nonnull HasEnclosingPackage existingNode, @Nonnull JPackage newEnclosingPackage) {
-    assert existingNode != program.getTopLevelPackage()
+    assert existingNode != session.getTopLevelPackage()
         : "The default package can't change its enclosing package";
     this.newEnclosingPackage = newEnclosingPackage;
     this.existingNode = existingNode;
diff --git a/jack/src/com/android/jack/util/NamingTools.java b/jack/src/com/android/jack/util/NamingTools.java
index 4f175ed..cd3ca90 100644
--- a/jack/src/com/android/jack/util/NamingTools.java
+++ b/jack/src/com/android/jack/util/NamingTools.java
@@ -35,6 +35,10 @@
 
   public static final char SIGNATURE_SEPARATOR = JLookup.PACKAGE_SEPARATOR;
 
+  public static final String STATIC_INIT_NAME = "<clinit>";
+
+  public static final String INIT_NAME = "<init>";
+
   /**
    * Return a string representing a valid name for generated files and which does not conflict with
    * name coming from Java source files.
diff --git a/jack/src/com/android/jack/util/filter/AllMethods.java b/jack/src/com/android/jack/util/filter/AllMethods.java
index 83532d0..e316133 100644
--- a/jack/src/com/android/jack/util/filter/AllMethods.java
+++ b/jack/src/com/android/jack/util/filter/AllMethods.java
@@ -18,12 +18,14 @@
 
 import com.android.jack.ir.ast.JMethod;
 import com.android.sched.schedulable.RunnableSchedulable;
+import com.android.sched.util.codec.ImplementationName;
 
 import javax.annotation.Nonnull;
 
 /**
  * {@link AllMethods} accepts all methods.
  */
+@ImplementationName(iface = Filter.class, name = "all-methods")
 public class AllMethods implements Filter<JMethod> {
 
   @Override
diff --git a/jack/src/com/android/jack/util/filter/RejectAllMethods.java b/jack/src/com/android/jack/util/filter/RejectAllMethods.java
index 3cbc65a..f91de31 100644
--- a/jack/src/com/android/jack/util/filter/RejectAllMethods.java
+++ b/jack/src/com/android/jack/util/filter/RejectAllMethods.java
@@ -18,12 +18,14 @@
 
 import com.android.jack.ir.ast.JMethod;
 import com.android.sched.schedulable.RunnableSchedulable;
+import com.android.sched.util.codec.ImplementationName;
 
 import javax.annotation.Nonnull;
 
 /**
  * {@code RejectAllMethods} allows to reject all methods, such as no body will be generated.
  */
+@ImplementationName(iface = Filter.class, name = "reject-all-methods")
 public class RejectAllMethods implements Filter<JMethod> {
 
   @Override
diff --git a/jack/src/com/android/jack/util/filter/SignatureCodec.java b/jack/src/com/android/jack/util/filter/SignatureCodec.java
new file mode 100644
index 0000000..69776bc
--- /dev/null
+++ b/jack/src/com/android/jack/util/filter/SignatureCodec.java
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack.util.filter;
+
+import com.android.sched.util.codec.CodecContext;
+import com.android.sched.util.codec.StringCodec;
+
+import javax.annotation.CheckForNull;
+import javax.annotation.Nonnull;
+
+
+/**
+ * This {@link SignatureCodec} is used to check that the string is a valid signature
+ */
+public class SignatureCodec implements StringCodec<String>{
+
+  @Override
+  @Nonnull
+  public String getUsage() {
+    return "a method signature (for instance \"methodname(ILpackage1/package2/Classname;)B\")";
+  }
+
+  @Override
+  @Nonnull
+  public String parseString(@Nonnull CodecContext context, @Nonnull String string) {
+    return string;
+  }
+
+  @Override
+  @CheckForNull
+  public String checkString(@Nonnull CodecContext context, @Nonnull String string) {
+    return string;
+  }
+
+  @Override
+  public void checkValue(@Nonnull CodecContext context, @Nonnull String data) {
+  }
+
+  @Override
+  @Nonnull
+  public String formatValue(@Nonnull String name) {
+    return name;
+  }
+}
diff --git a/jack/src/com/android/jack/util/filter/SignatureMethodFilter.java b/jack/src/com/android/jack/util/filter/SignatureMethodFilter.java
new file mode 100644
index 0000000..abdcb04
--- /dev/null
+++ b/jack/src/com/android/jack/util/filter/SignatureMethodFilter.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack.util.filter;
+
+import com.android.jack.Jack;
+import com.android.jack.Options;
+import com.android.jack.ir.ast.JMethod;
+import com.android.sched.schedulable.RunnableSchedulable;
+import com.android.sched.util.codec.ImplementationName;
+import com.android.sched.util.config.HasKeyId;
+import com.android.sched.util.config.ThreadConfig;
+import com.android.sched.util.config.id.ImplementationPropertyId;
+import com.android.sched.util.config.id.PropertyId;
+
+import javax.annotation.Nonnull;
+
+@HasKeyId
+@ImplementationName(iface = Filter.class, name = "method-with-signature")
+public class SignatureMethodFilter implements Filter<JMethod> {
+
+  @SuppressWarnings({"unchecked", "rawtypes"})
+  @Nonnull
+  public static final PropertyId<String> METHOD_SIGNATURE_FILTER = PropertyId.create(
+      "jack.internal.filter.method.signature",
+      "Method signature that will be accepted by the filter",
+      new SignatureCodec()).requiredIf(
+      ((ImplementationPropertyId<Filter>) (Object) Options.METHOD_FILTER).getClazz()
+          .isImplementedBy(SignatureMethodFilter.class));
+
+  @Nonnull
+  private final String methodSignature;
+
+  public SignatureMethodFilter() {
+    this.methodSignature = ThreadConfig.get(METHOD_SIGNATURE_FILTER);
+  }
+
+  @Override
+  public boolean accept(
+      @Nonnull Class<? extends RunnableSchedulable<?>> runnableSchedulable,
+      @Nonnull JMethod method) {
+    return (Jack.getLookupFormatter().getName(method).equals(methodSignature));
+  }
+}
\ No newline at end of file
diff --git a/jack/src/com/android/jack/util/filter/SupportedMethods.java b/jack/src/com/android/jack/util/filter/SupportedMethods.java
index e5d5957..772fb5d 100644
--- a/jack/src/com/android/jack/util/filter/SupportedMethods.java
+++ b/jack/src/com/android/jack/util/filter/SupportedMethods.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.ir.ast.JMethod;
 import com.android.sched.schedulable.RunnableSchedulable;
+import com.android.sched.util.codec.ImplementationName;
 
 import javax.annotation.Nonnull;
 
@@ -26,6 +27,7 @@
  * exists. Otherwise methods are accepted only for a specific set of {@link RunnableSchedulable}
  * specify by {@link RunnableSchedulableFilter}.
  */
+@ImplementationName(iface = Filter.class, name = "supported-methods")
 public class SupportedMethods implements Filter<JMethod> {
 
   @Override
diff --git a/jack/tests/com/android/jack/AllTests.java b/jack/tests/com/android/jack/AllTests.java
index be9072f..33de0e6 100644
--- a/jack/tests/com/android/jack/AllTests.java
+++ b/jack/tests/com/android/jack/AllTests.java
@@ -38,8 +38,7 @@
 @RunWith(Suite.class)
 @SuiteClasses(value = {
     AnnotationTest.class,
-    Arithmetic001Test.class,
-    Arithmetic002Test.class,
+    ArithmeticTest.class,
     ArrayTest.class,
     AssertionTest.class,
     AssignmentTest.class,
@@ -83,6 +82,7 @@
     OpcodesTest.class,
     OrderTest.class,
     ReachingDefsTest.class,
+    ResourceTest.class,
     ReturnTest.class,
     RopRegisterManagerTest.class,
     StaticValuesTest.class,
diff --git a/jack/tests/com/android/jack/Arithmetic001Test.java b/jack/tests/com/android/jack/Arithmetic001Test.java
deleted file mode 100644
index 94582d6..0000000
--- a/jack/tests/com/android/jack/Arithmetic001Test.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.jack;
-
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import java.io.File;
-
-/**
- * JUnit test for compilation of arithmetic tests.
- */
-public class Arithmetic001Test {
-  private static final File PATH = TestTools.getJackTestsWithJackFolder("arithmetic/test001");
-
-  private static final File[] JAVA_SOURCES = {
-    new File(PATH, "Add.java"),
-    new File(PATH, "And.java"),
-    new File(PATH, "Div.java"),
-    new File(PATH, "Mod.java"),
-    new File(PATH, "Mul.java"),
-    new File(PATH, "Or.java"),
-    new File(PATH, "Shl.java"),
-    new File(PATH, "Shr.java"),
-    new File(PATH, "Sub.java"),
-    new File(PATH, "Ushr.java"),
-    new File(PATH, "Xor.java")
-    };
-
-  @BeforeClass
-  public static void setUpClass() {
-    Main.class.getClassLoader().setDefaultAssertionStatus(true);
-  }
-
-  /**
-   * Verifies that the test source can compiled from source to dex file.
-   */
-  @Test
-  public void testCompile() throws Exception {
-    TestTools.runCompilation(TestTools.buildCommandLineArgs(JAVA_SOURCES));
-  }
-}
diff --git a/jack/tests/com/android/jack/Arithmetic002Test.java b/jack/tests/com/android/jack/Arithmetic002Test.java
deleted file mode 100644
index 0b3adc9..0000000
--- a/jack/tests/com/android/jack/Arithmetic002Test.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.jack;
-
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import java.io.File;
-
-/**
- * JUnit test for compilation of arithmetic tests.
- */
-public class Arithmetic002Test {
-  private static final File PATH = TestTools.getJackTestsWithJackFolder("arithmetic/test002");
-
-  private static final File[] JAVA_SOURCES = {
-    new File(PATH, "Add.java"),
-    new File(PATH, "And.java"),
-    new File(PATH, "Div.java"),
-    new File(PATH, "Mod.java"),
-    new File(PATH, "Mul.java"),
-    new File(PATH, "Or.java"),
-    new File(PATH, "Shl.java"),
-    new File(PATH, "Shr.java"),
-    new File(PATH, "Sub.java"),
-    new File(PATH, "Ushr.java"),
-    new File(PATH, "Xor.java")
-    };
-
-  @BeforeClass
-  public static void setUpClass() {
-    Main.class.getClassLoader().setDefaultAssertionStatus(true);
-  }
-
-  /**
-   * Verifies that the test source can compiled from source to dex file.
-   */
-  @Test
-  public void testCompile() throws Exception {
-    TestTools.runCompilation(TestTools.buildCommandLineArgs(JAVA_SOURCES));
-  }
-}
diff --git a/jack/tests/com/android/jack/ArithmeticTest.java b/jack/tests/com/android/jack/ArithmeticTest.java
new file mode 100644
index 0000000..5f64099
--- /dev/null
+++ b/jack/tests/com/android/jack/ArithmeticTest.java
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack;
+
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+/**
+ * JUnit test for compilation of arithmetic.
+ */
+public class ArithmeticTest {
+
+  @BeforeClass
+  public static void setUpClass() {
+    Main.class.getClassLoader().setDefaultAssertionStatus(true);
+  }
+
+  @Test
+  public void testNew001() throws Exception {
+    TestTools.runCompilation(TestTools.buildCommandLineArgs(TestTools
+        .getJackTestsWithJackFolder("arithmetic/test001")));
+  }
+
+  @Test
+  public void testNew002() throws Exception {
+    TestTools.runCompilation(TestTools.buildCommandLineArgs(TestTools
+        .getJackTestsWithJackFolder("arithmetic/test002")));
+  }
+
+  @Test
+  public void testNew003() throws Exception {
+    TestTools.runCompilation(TestTools.buildCommandLineArgs(TestTools
+        .getJackTestsWithJackFolder("arithmetic/test003")));
+  }
+
+  @Test
+  public void testNew004() throws Exception {
+    TestTools.runCompilation(TestTools.buildCommandLineArgs(TestTools
+        .getJackTestsWithJackFolder("arithmetic/test004")));
+  }
+}
diff --git a/jack/tests/com/android/jack/ConditionalTest.java b/jack/tests/com/android/jack/ConditionalTest.java
index ab7d91f..1e13a45 100644
--- a/jack/tests/com/android/jack/ConditionalTest.java
+++ b/jack/tests/com/android/jack/ConditionalTest.java
@@ -24,7 +24,7 @@
 import com.android.jack.ir.ast.JParameter;
 import com.android.jack.ir.ast.JParameterRef;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.lookup.CommonTypes;
 import com.android.jack.lookup.JPhantomLookup;
 import com.android.sched.util.RunnableHooks;
@@ -92,8 +92,8 @@
     Options options = new Options();
     options.checkValidity(new RunnableHooks());
     ThreadConfig.setConfig(options.getConfig());
-    JProgram prog = Jack.getProgram();
-    JPhantomLookup lookup = prog.getPhantomLookup();
+    JSession session = Jack.getSession();
+    JPhantomLookup lookup = session.getPhantomLookup();
 
     JArrayType arrayInt = lookup.getArrayType(JPrimitiveTypeEnum.INT.getType(), 1);
     JArrayType arrayByte = lookup.getArrayType(JPrimitiveTypeEnum.BYTE.getType(), 1);
@@ -111,7 +111,7 @@
         new JParameter(SourceOrigin.UNKNOWN, "pArrayIntIntInt", arrayIntIntInt, 0, null);
     JParameter pArrayByte = new JParameter(SourceOrigin.UNKNOWN, "pArrayByte", arrayByte, 0, null);
     JClass javaLangObject =
-        Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+        Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
     JParameter pObject =
         new JParameter(SourceOrigin.UNKNOWN, "pArrayByte", javaLangObject, 0,
             null);
diff --git a/jack/tests/com/android/jack/FibonacciThreeAddressTest.java b/jack/tests/com/android/jack/FibonacciThreeAddressTest.java
index e872697..fc39b4c 100644
--- a/jack/tests/com/android/jack/FibonacciThreeAddressTest.java
+++ b/jack/tests/com/android/jack/FibonacciThreeAddressTest.java
@@ -19,10 +19,9 @@
 import com.android.jack.dx.dex.file.ClassDefItem;
 import com.android.jack.dx.dex.file.DexFile;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.marker.DexFileMarker;
 import com.android.jack.util.FileUtils;
-import com.android.jack.util.filter.RejectAllMethods;
 
 import junit.framework.Assert;
 
@@ -54,10 +53,10 @@
    */
   @Test
   public void testLoadFiboInJAst() throws Exception {
-    JProgram program = TestTools.buildJAst(TestTools.buildCommandLineArgs(JAVA_FILEPATH));
-    Assert.assertNotNull(program);
+    JSession session = TestTools.buildJAst(TestTools.buildCommandLineArgs(JAVA_FILEPATH));
+    Assert.assertNotNull(session);
 
-    JDefinedClassOrInterface fibo = (JDefinedClassOrInterface) program.getLookup().getType(CLASS_SIGNATURE);
+    JDefinedClassOrInterface fibo = (JDefinedClassOrInterface) session.getLookup().getType(CLASS_SIGNATURE);
     Assert.assertNotNull(fibo);
   }
 
@@ -68,13 +67,13 @@
   @Test
   public void testBuildFiboDexFile() throws Exception {
     Options fiboArgs = TestTools.buildCommandLineArgs(JAVA_FILEPATH);
-    fiboArgs.setFilter(new RejectAllMethods());
-    JProgram program = TestTools.buildProgram(fiboArgs);
+    fiboArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
+    JSession session = TestTools.buildSession(fiboArgs);
 
-    JDefinedClassOrInterface fibo = (JDefinedClassOrInterface) program.getLookup().getType(CLASS_SIGNATURE);
+    JDefinedClassOrInterface fibo = (JDefinedClassOrInterface) session.getLookup().getType(CLASS_SIGNATURE);
     Assert.assertNotNull(fibo);
 
-    DexFileMarker marker = program.getMarker(DexFileMarker.class);
+    DexFileMarker marker = session.getMarker(DexFileMarker.class);
     Assert.assertNotNull(marker);
     assert marker != null;
 
diff --git a/jack/tests/com/android/jack/FinallyTest.java b/jack/tests/com/android/jack/FinallyTest.java
index b886bd4..900a90b 100644
--- a/jack/tests/com/android/jack/FinallyTest.java
+++ b/jack/tests/com/android/jack/FinallyTest.java
@@ -95,8 +95,8 @@
     String methodSignature = "get()V";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new checkUselessIf().accept(m);
diff --git a/jack/tests/com/android/jack/MainTest.java b/jack/tests/com/android/jack/MainTest.java
index d4b7676..625aea3 100644
--- a/jack/tests/com/android/jack/MainTest.java
+++ b/jack/tests/com/android/jack/MainTest.java
@@ -17,7 +17,7 @@
 package com.android.jack;
 
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 
 import junit.framework.Assert;
 
@@ -53,10 +53,10 @@
    */
   @Test
   public void testLoadFiboInJAst() throws Exception {
-    JProgram program = TestTools.buildJAst(
+    JSession session = TestTools.buildJAst(
         TestTools.buildCommandLineArgs(TestTools.getJackTestFromBinaryName(CLASS_BINARY_NAME)));
     JDefinedClassOrInterface fibo =
-        (JDefinedClassOrInterface) program.getLookup().getType(CLASS_SIGNATURE);
+        (JDefinedClassOrInterface) session.getLookup().getType(CLASS_SIGNATURE);
     Assert.assertNotNull(fibo);
     // TODO(yroussel): make further checks
   }
diff --git a/jack/tests/com/android/jack/ResourceTest.java b/jack/tests/com/android/jack/ResourceTest.java
new file mode 100644
index 0000000..5f67828
--- /dev/null
+++ b/jack/tests/com/android/jack/ResourceTest.java
@@ -0,0 +1,337 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack;
+
+import com.android.jack.category.KnownBugs;
+import com.android.jack.util.BytesStreamSucker;
+
+import junit.framework.Assert;
+
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.util.Collections;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipFile;
+import java.util.zip.ZipOutputStream;
+
+import javax.annotation.Nonnull;
+
+/**
+ * JUnit tests for resource support.
+ */
+public class ResourceTest {
+
+  @Nonnull
+  private static final String COMMON_PATH = "com/android/jack/resource/test001/jack/";
+  @Nonnull
+  private static final String JACK_FILE_PATH = COMMON_PATH + "IrrelevantForTest.jack";
+  @Nonnull
+  private static final String RESOURCE1_SHORTPATH = "Resource1";
+  @Nonnull
+  private static final String RESOURCE2_SHORTPATH = "Resource2";
+  @Nonnull
+  private static final String RESOURCE3_SHORTPATH = "pack/Resource3";
+  @Nonnull
+  private static final String RESOURCE4_SHORTPATH = "pack/Resource4";
+  @Nonnull
+  private static final String RESOURCE1_LONGPATH = COMMON_PATH + RESOURCE1_SHORTPATH;
+  @Nonnull
+  private static final String RESOURCE2_LONGPATH = COMMON_PATH + RESOURCE2_SHORTPATH;
+  @Nonnull
+  private static final String RESOURCE3_LONGPATH = COMMON_PATH + RESOURCE3_SHORTPATH;
+  @Nonnull
+  private static final String RESOURCE4_LONGPATH = COMMON_PATH + RESOURCE4_SHORTPATH;
+
+  @Nonnull
+  private static final File FILE =
+      TestTools.getJackTestsWithJackFolder("resource/test001");
+
+  @BeforeClass
+  public static void setUpClass() {
+    Main.class.getClassLoader().setDefaultAssertionStatus(true);
+  }
+
+  @Test
+  public void testJackArchiveToDexArchive() throws Exception {
+    // compile source file to a Jack archive and add resources
+    File jackAr = createJackArchiveWithResources();
+
+    // compile Jack archive to dex archive
+    File dexAr = TestTools.createTempFile("resourcetestdex", ".zip");
+    TestTools.compileJackToDex(new Options(), jackAr, dexAr, true /* zipped */);
+
+    // check that resources are contained in dex archive
+    ZipFile zipFile = new ZipFile(dexAr);
+    checkResourceContent(zipFile, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(zipFile, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(zipFile, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(zipFile, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Test
+  @Category(KnownBugs.class)
+  public void testJackDirToDexArchive() throws Exception {
+    // compile source file to a Jack dir
+    File jackFolder = TestTools.createTempDir("tempjack", "dir");
+    TestTools.compileSourceToJack(new Options(), FILE, TestTools.getDefaultBootclasspathString(),
+        jackFolder, false /* non-zipped */);
+
+    // add resources to Jack dir
+    copyFileToDir(new File(FILE, RESOURCE1_SHORTPATH), RESOURCE1_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE2_SHORTPATH), RESOURCE2_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE3_SHORTPATH), RESOURCE3_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE4_SHORTPATH), RESOURCE4_LONGPATH, jackFolder);
+
+    // compile Jack dir to dex archive
+    File dexAr = TestTools.createTempFile("resourcetestdex", ".zip");
+    TestTools.compileJackToDex(new Options(), jackFolder, dexAr, true /* zipped */);
+
+    // check that resources are contained in dex archive
+    ZipFile zipFile = new ZipFile(dexAr);
+    checkResourceContent(zipFile, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(zipFile, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(zipFile, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(zipFile, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Test
+  public void testJackArchiveToJackArchive() throws Exception {
+    // compile source file to a Jack archive and add resources
+    File jackAr = createJackArchiveWithResources();
+
+    // run shrobbing from Jack archive to Jack archive
+    File shrobbedJackAr = TestTools.createTempFile("shrobbedJackAr", ".zip");
+    ProguardFlags flags = new ProguardFlags(new File(FILE, "proguard.flags"));
+    TestTools.shrobJackToJack(new Options(),
+        jackAr,
+        null /* classpath */,
+        shrobbedJackAr,
+        Collections.singletonList(flags),
+        true /* zipped */);
+
+    // check that resources are contained in dex archive
+    ZipFile zipFile = new ZipFile(shrobbedJackAr);
+    checkResourceContent(zipFile, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(zipFile, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(zipFile, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(zipFile, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Test
+  @Category(KnownBugs.class)
+  public void testJackDirToJackArchive() throws Exception {
+    // compile source file to a Jack dir
+    File jackFolder = TestTools.createTempDir("tempjack", "dir");
+    TestTools.compileSourceToJack(new Options(), FILE, TestTools.getDefaultBootclasspathString(),
+        jackFolder, false /* non-zipped */);
+
+    // add resources to Jack dir
+    copyFileToDir(new File(FILE, RESOURCE1_SHORTPATH), RESOURCE1_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE2_SHORTPATH), RESOURCE2_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE3_SHORTPATH), RESOURCE3_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE4_SHORTPATH), RESOURCE4_LONGPATH, jackFolder);
+
+    // run shrobbing from Jack dir to Jack archive
+    File shrobbedJackAr = TestTools.createTempFile("shrobbedJackAr", ".zip");
+    ProguardFlags flags = new ProguardFlags(new File(FILE, "proguard.flags"));
+    TestTools.shrobJackToJack(new Options(),
+        jackFolder,
+        null /* classpath */,
+        shrobbedJackAr,
+        Collections.singletonList(flags),
+        true /* zipped */);
+
+    // check that resources are contained in Jack archive
+    ZipFile zipFile = new ZipFile(shrobbedJackAr);
+    checkResourceContent(zipFile, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(zipFile, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(zipFile, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(zipFile, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Test
+  @Category(KnownBugs.class)
+  public void testJackArchiveToJackDir() throws Exception {
+    // compile source file to a Jack archive and add resources
+    File jackAr = createJackArchiveWithResources();
+
+    // run shrobbing from Jack archive to Jack dir
+    File shrobbedJackDir = TestTools.createTempDir("shrobbedJack", "dir");
+    ProguardFlags flags = new ProguardFlags(new File(FILE, "proguard.flags"));
+    TestTools.shrobJackToJack(new Options(),
+        jackAr,
+        null /* classpath */,
+        shrobbedJackDir,
+        Collections.singletonList(flags),
+        false /* non-zipped */);
+
+    // check that resources are contained in Jack dir
+    checkResourceContent(shrobbedJackDir, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(shrobbedJackDir, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(shrobbedJackDir, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(shrobbedJackDir, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Test
+  @Category(KnownBugs.class)
+  public void testJackDirToJackDir() throws Exception {
+    /// compile source file to a Jack dir
+    File jackFolder = TestTools.createTempDir("tempjack", "dir");
+    TestTools.compileSourceToJack(new Options(), FILE, TestTools.getDefaultBootclasspathString(),
+        jackFolder, false /* non-zipped */);
+
+    // add resources to Jack dir
+    copyFileToDir(new File(FILE, RESOURCE1_SHORTPATH), RESOURCE1_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE2_SHORTPATH), RESOURCE2_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE3_SHORTPATH), RESOURCE3_LONGPATH, jackFolder);
+    copyFileToDir(new File(FILE, RESOURCE4_SHORTPATH), RESOURCE4_LONGPATH, jackFolder);
+
+    // run shrobbing from Jack dir to Jack dir
+    File shrobbedJackDir = TestTools.createTempDir("shrobbedJack", "dir");
+    ProguardFlags flags = new ProguardFlags(new File(FILE, "proguard.flags"));
+    TestTools.shrobJackToJack(new Options(),
+        jackFolder,
+        null /* classpath */,
+        shrobbedJackDir,
+        Collections.singletonList(flags),
+        false /* non-zipped */);
+
+    // check that resources are contained in Jack dir
+    checkResourceContent(shrobbedJackDir, RESOURCE1_LONGPATH, "Res1");
+    checkResourceContent(shrobbedJackDir, RESOURCE2_LONGPATH, "Res2");
+    checkResourceContent(shrobbedJackDir, RESOURCE3_LONGPATH, "Res3");
+    checkResourceContent(shrobbedJackDir, RESOURCE4_LONGPATH, "Res4");
+  }
+
+  @Nonnull
+  private File createJackArchiveWithResources() throws Exception {
+    // compile source file to a Jack file
+    File tempJackFolder = TestTools.createTempDir("jack", "dir");
+    TestTools.compileSourceToJack(new Options(), FILE, TestTools.getDefaultBootclasspathString(),
+        tempJackFolder, false /* non-zipped */);
+
+    // create Jack archive with resources
+    File singleJackFile = new File(tempJackFolder, JACK_FILE_PATH);
+    File jackAr = TestTools.createTempFile("resourcetestjack", ".zip");
+    ZipOutputStream zos = null;
+    try {
+      zos = new ZipOutputStream(new FileOutputStream(jackAr));
+
+      copyFileToZip(singleJackFile, JACK_FILE_PATH, zos);
+      copyFileToZip(new File(FILE, RESOURCE1_SHORTPATH), RESOURCE1_LONGPATH, zos);
+      copyFileToZip(new File(FILE, RESOURCE2_SHORTPATH), RESOURCE2_LONGPATH, zos);
+      copyFileToZip(new File(FILE, RESOURCE3_SHORTPATH), RESOURCE3_LONGPATH, zos);
+      copyFileToZip(new File(FILE, RESOURCE4_SHORTPATH), RESOURCE4_LONGPATH, zos);
+    } finally {
+      if (zos != null) {
+        zos.close();
+      }
+    }
+    return jackAr;
+  }
+
+  private void checkResourceContent(@Nonnull ZipFile zipFile, @Nonnull String entryName,
+      @Nonnull String expectedContent) throws IOException {
+    ZipEntry entry = zipFile.getEntry(entryName);
+    Assert.assertNotNull(entry);
+    BufferedReader reader = null;
+    try {
+      InputStream in = zipFile.getInputStream(entry);
+      reader = new BufferedReader(new InputStreamReader(in));
+      String line = reader.readLine();
+      Assert.assertEquals(expectedContent, line);
+    } finally {
+      if (reader != null) {
+        reader.close();
+      }
+    }
+  }
+
+  private void checkResourceContent(@Nonnull File dir, @Nonnull String path,
+      @Nonnull String expectedContent) throws IOException {
+    assert dir.isDirectory();
+    File file = new File(dir, path);
+    Assert.assertTrue(file.exists());
+    BufferedReader reader = null;
+    try {
+      InputStream in = new FileInputStream(file);
+      reader = new BufferedReader(new InputStreamReader(in));
+      String line = reader.readLine();
+      Assert.assertEquals(expectedContent, line);
+    } finally {
+      if (reader != null) {
+        reader.close();
+      }
+    }
+  }
+
+  private void copyFileToDir(@Nonnull File fileToCopy, @Nonnull String relativePath,
+      @Nonnull File dir) throws IOException {
+    FileOutputStream fos = null;
+    FileInputStream fis = null;
+    try {
+      fis = new FileInputStream(fileToCopy);
+      File copiedFile = new File(dir, relativePath);
+      File parentDir = copiedFile.getParentFile();
+      if (!parentDir.exists()) {
+        boolean res = parentDir.mkdirs();
+        if (!res) {
+          throw new AssertionError();
+        }
+      }
+      try {
+        fos = new FileOutputStream(copiedFile);
+        BytesStreamSucker sucker = new BytesStreamSucker(fis, fos);
+        sucker.run();
+      } finally {
+        if (fos != null) {
+          fos.close();
+        }
+      }
+    } finally {
+      if (fis != null) {
+        fis.close();
+      }
+    }
+  }
+
+  private void copyFileToZip(@Nonnull File fileToCopy, @Nonnull String entryName,
+      @Nonnull ZipOutputStream zos)
+      throws IOException {
+    FileInputStream fis = null;
+    try {
+      fis = new FileInputStream(fileToCopy);
+      ZipEntry sourceEntry = new ZipEntry(entryName);
+      zos.putNextEntry(sourceEntry);
+      BytesStreamSucker sucker = new BytesStreamSucker(fis, zos);
+      sucker.run();
+    } finally {
+      if (fis != null) {
+        fis.close();
+      }
+    }
+  }
+}
diff --git a/jack/tests/com/android/jack/SignatureMethodFilter.java b/jack/tests/com/android/jack/SignatureMethodFilter.java
deleted file mode 100644
index ff51d6f..0000000
--- a/jack/tests/com/android/jack/SignatureMethodFilter.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.jack;
-
-import com.android.jack.ir.ast.JMethod;
-import com.android.jack.util.filter.Filter;
-import com.android.sched.schedulable.RunnableSchedulable;
-
-import javax.annotation.Nonnull;
-
-public class SignatureMethodFilter implements Filter<JMethod> {
-
-  final String methodSignature;
-
-  public SignatureMethodFilter(String methodSignature) {
-    this.methodSignature = methodSignature;
-  }
-
-  @Override
-  public boolean accept(
-      @Nonnull Class<? extends RunnableSchedulable<?>> runnableSchedulable,
-      @Nonnull JMethod method) {
-    return (Jack.getLookupFormatter().getName(method).equals(methodSignature));
-  }
-}
\ No newline at end of file
diff --git a/jack/tests/com/android/jack/StaticValuesTest.java b/jack/tests/com/android/jack/StaticValuesTest.java
index 87b1903..2cd87e6 100644
--- a/jack/tests/com/android/jack/StaticValuesTest.java
+++ b/jack/tests/com/android/jack/StaticValuesTest.java
@@ -23,10 +23,9 @@
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
 import com.android.jack.scheduling.adapter.JFieldAdaptor;
-import com.android.jack.util.filter.SupportedMethods;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
 import com.android.sched.scheduler.Scheduler;
@@ -104,10 +103,10 @@
 
   public static JMethod compileAndGetClinit(String classBinaryName, Options options)
       throws Exception {
-    options.setFilter(new SupportedMethods());
+    options.addProperty(Options.METHOD_FILTER.getName(), "supported-methods");
 
-    JProgram jprogram = TestTools.buildJAst(options);
-    Assert.assertNotNull(jprogram);
+    JSession session = TestTools.buildJAst(options);
+    Assert.assertNotNull(session);
 
 
     Scheduler scheduler = Scheduler.getScheduler();
@@ -119,16 +118,16 @@
     set.add(JFieldInitializer.class);
     sr.addInitialTagsOrMarkers(set);
 
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
     SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-        progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+        planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JField> fieldPlan = typePlan.appendSubPlan(JFieldAdaptor.class);
     fieldPlan.append(FieldInitializerRemover.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
     JDefinedClassOrInterface declaredType =
-        (JDefinedClassOrInterface) jprogram.getLookup().getType("L" + classBinaryName + ";");
+        (JDefinedClassOrInterface) session.getLookup().getType("L" + classBinaryName + ";");
     return declaredType.getMethod(CLINIT, JPrimitiveTypeEnum.VOID.getType());
   }
 
diff --git a/jack/tests/com/android/jack/TestTools.java b/jack/tests/com/android/jack/TestTools.java
index 89f1410..7a968a4 100644
--- a/jack/tests/com/android/jack/TestTools.java
+++ b/jack/tests/com/android/jack/TestTools.java
@@ -22,7 +22,7 @@
 import com.android.jack.dx.dex.file.DexFile;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.formatter.MethodFormatter;
 import com.android.jack.lookup.JMethodSignatureLookupException;
 import com.android.jack.scheduling.marker.DexFileMarker;
@@ -31,8 +31,7 @@
 import com.android.jack.shrob.spec.Flags;
 import com.android.jack.util.ExecuteFile;
 import com.android.jack.util.TextUtils;
-import com.android.jack.util.filter.Filter;
-import com.android.jack.util.filter.SupportedMethods;
+import com.android.jack.util.filter.SignatureMethodFilter;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
 import com.android.sched.util.RunnableHooks;
@@ -512,28 +511,28 @@
   }
 
   @Nonnull
-  public static JProgram buildJAst(@Nonnull Options options) throws Exception {
+  public static JSession buildJAst(@Nonnull Options options) throws Exception {
     RunnableHooks hooks = new RunnableHooks();
     try {
       options.checkValidity(hooks);
       ThreadConfig.setConfig(options.getConfig());
 
-      JProgram jprogram = Jack.buildProgram(options, hooks);
+      JSession session = Jack.buildSession(options, hooks);
 
-      return (jprogram);
+      return (session);
     } finally {
       hooks.runHooks();
     }
   }
 
   /**
-   * Build a {@code JProgram} by using the monolithic plan.
+   * Build a {@code JSession} by using the monolithic plan.
    */
   @Nonnull
-  public static JProgram buildProgram(@Nonnull Options options) throws Exception {
+  public static JSession buildSession(@Nonnull Options options) throws Exception {
     RunnableHooks hooks = new RunnableHooks();
     try {
-      return buildProgram(options, hooks);
+      return buildSession(options, hooks);
     } finally {
       hooks.runHooks();
     }
@@ -541,10 +540,10 @@
   }
 
   /**
-   * Build a {@code JProgram} by using the monolithic plan.
+   * Build a {@code JSession} by using the monolithic plan.
    */
   @Nonnull
-  public static JProgram buildProgram(@Nonnull Options options, @Nonnull RunnableHooks hooks) throws Exception {
+  public static JSession buildSession(@Nonnull Options options, @Nonnull RunnableHooks hooks) throws Exception {
     if (options.proguardFlagsFiles != null && !options.proguardFlagsFiles.isEmpty()) {
       if (options.flags == null) {
         options.flags = new Flags();
@@ -558,7 +557,7 @@
     options.checkValidity(hooks);
     ThreadConfig.setConfig(options.getConfig());
 
-    JProgram jprogram = Jack.buildProgram(options, hooks);
+    JSession session = Jack.buildSession(options, hooks);
 
     Request request = Jack.createInitialRequest();
     request.addInitialTagsOrMarkers(Jack.getJavaSourceInitialTagSet());
@@ -567,13 +566,13 @@
       request.addProduction(JackFormatProduct.class);
     }
 
-    PlanBuilder<JProgram> planBuilder = request.getPlanBuilder(JProgram.class);
+    PlanBuilder<JSession> planBuilder = request.getPlanBuilder(JSession.class);
     Jack.fillDexPlan(options, planBuilder);
     request.addTargetIncludeTagOrMarker(DexFileMarker.Complete.class);
 
-    planBuilder.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
-    return (jprogram);
+    return (session);
   }
 
   public static void checkStructure(@CheckForNull File[] bootclasspath,
@@ -677,7 +676,7 @@
     if (flags != null) {
     jackOptions.applyShrobFlags();
     }
-    jackOptions.setFilter(new SupportedMethods());
+    jackOptions.addProperty(Options.METHOD_FILTER.getName(), "supported-methods");
 
     File out = TestTools.createTempFile("checklisting", ".dex");
     TestTools.compileSourceToDex(jackOptions,
@@ -695,7 +694,7 @@
     Options jackOptions = new Options();
     File candidateNodeListing = TestTools.createTempFile("nodeListing", ".txt");
     jackOptions.typeAndMemberListing = candidateNodeListing;
-    jackOptions.setFilter(new SupportedMethods());
+    jackOptions.addProperty(Options.METHOD_FILTER.getName(), "supported-methods");
     jackOptions.disableDxOptimizations();
 
     File out = TestTools.createTempFile("checklisting", ".dex");
@@ -721,15 +720,39 @@
   }
 
   @Nonnull
-  public static JMethod getJMethod(@Nonnull File fileName, @Nonnull String className,
-      @Nonnull String methodSignature, @Nonnull Filter<JMethod> filter) throws Exception {
+  public static JMethod getJMethodWithRejectAllFilter(@Nonnull File fileName,
+      @Nonnull String className, @Nonnull String methodSignature) throws Exception {
     Options commandLineArgs = TestTools.buildCommandLineArgs(fileName);
-    commandLineArgs.setFilter(filter);
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
     commandLineArgs.keepMethodBody = true;
-    JProgram program = TestTools.buildProgram(commandLineArgs);
-    Assert.assertNotNull(program);
+    JSession session = TestTools.buildSession(commandLineArgs);
+    Assert.assertNotNull(session);
 
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(className);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(className);
+    Assert.assertNotNull(type);
+
+    JMethod foundMethod = null;
+    foundMethod = getMethod(type, methodSignature);
+
+    Assert.assertNotNull(foundMethod);
+
+    return foundMethod;
+  }
+
+  @Nonnull
+  public static JMethod getJMethodWithSignatureFilter(@Nonnull File fileName,
+      @Nonnull String className, @Nonnull String methodSignature) throws Exception {
+    Options commandLineArgs = TestTools.buildCommandLineArgs(fileName);
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
+    commandLineArgs.keepMethodBody = true;
+    JSession session = TestTools.buildSession(commandLineArgs);
+    Assert.assertNotNull(session);
+
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(className);
     Assert.assertNotNull(type);
 
     JMethod foundMethod = null;
diff --git a/jack/tests/com/android/jack/Types.java b/jack/tests/com/android/jack/Types.java
index 8f00850..75f2e2e 100644
--- a/jack/tests/com/android/jack/Types.java
+++ b/jack/tests/com/android/jack/Types.java
@@ -36,7 +36,7 @@
 import com.android.jack.ir.ast.JPrefixBitNotOperation;
 import com.android.jack.ir.ast.JPrefixNotOperation;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShlOperation;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JType;
@@ -61,8 +61,8 @@
     options.getConfigBuilder().setDebug();
     ThreadConfig.setConfig(options.getConfig());
 
-    JProgram program = Jack.getProgram();
-    program.getLookup().getOrCreatePackage("java/lang");
+    JSession session = Jack.getSession();
+    session.getLookup().getOrCreatePackage("java/lang");
   }
 
   @BeforeClass
@@ -97,7 +97,7 @@
     Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JPrefixNotOperation(
         SourceOrigin.UNKNOWN, new JBooleanLiteral(SourceOrigin.UNKNOWN, true)).getType());
 
-    JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+    JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
     Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JPrefixNotOperation(
         SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l)).getType());
@@ -139,7 +139,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JPrefixBitNotOperation(SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l))
           .getType();
@@ -158,7 +158,7 @@
     Assert.assertEquals(JPrimitiveTypeEnum.LONG.getType(), new JPrefixBitNotOperation(
         SourceOrigin.UNKNOWN, new JLongLiteral(SourceOrigin.UNKNOWN, 1l)).getType());
 
-    JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CHAR);
+    JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_CHAR);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
     Assert.assertEquals(JPrimitiveTypeEnum.INT.getType(), new JPrefixBitNotOperation(
         SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l)).getType());
@@ -180,7 +180,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JPostfixDecOperation(SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l))
           .getType();
@@ -202,7 +202,7 @@
     Assert.assertEquals(JPrimitiveTypeEnum.LONG.getType(), new JPostfixDecOperation(
         SourceOrigin.UNKNOWN, new JLongLiteral(SourceOrigin.UNKNOWN, 1l)).getType());
 
-    JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
+    JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
     Assert.assertEquals(JPrimitiveTypeEnum.INT.getType(), new JPostfixDecOperation(
         SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l)).getType());
@@ -234,7 +234,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JShlOperation(SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l),
           new JIntLiteral(SourceOrigin.UNKNOWN, 1)).getType();
@@ -246,7 +246,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JShlOperation(SourceOrigin.UNKNOWN, new JIntLiteral(SourceOrigin.UNKNOWN, 1),
           new JLocalRef(SourceOrigin.UNKNOWN, l)).getType();
@@ -273,8 +273,8 @@
         new JShortLiteral(SourceOrigin.UNKNOWN, (short) 1)).getType());
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
-      JType t1 = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
+      JType t1 = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       JLocal l1 = new JLocal(SourceOrigin.UNKNOWN, "test2", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.INT.getType(), new JShlOperation(SourceOrigin.UNKNOWN,
@@ -283,7 +283,7 @@
     }
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_LONG);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_LONG);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       JLocal l1 = new JLocal(SourceOrigin.UNKNOWN, "test2", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.LONG.getType(), new JShlOperation(SourceOrigin.UNKNOWN,
@@ -307,7 +307,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JLteOperation(SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l),
           new JFloatLiteral(SourceOrigin.UNKNOWN, 1)).getType();
@@ -318,7 +318,7 @@
     Assert.assertTrue(catched);
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_DOUBLE);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JLteOperation(SourceOrigin.UNKNOWN,
           new JLocalRef(SourceOrigin.UNKNOWN, l), new JIntLiteral(SourceOrigin.UNKNOWN, 1))
@@ -334,7 +334,7 @@
         .getType());
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BYTE);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       JLocal l1 = new JLocal(SourceOrigin.UNKNOWN, "test2", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JLteOperation(SourceOrigin.UNKNOWN,
@@ -361,7 +361,7 @@
         new JBooleanLiteral(SourceOrigin.UNKNOWN, true)).getType());
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JBitAndOperation(SourceOrigin.UNKNOWN,
           new JLocalRef(SourceOrigin.UNKNOWN, l), new JLocalRef(SourceOrigin.UNKNOWN, l))
@@ -369,7 +369,7 @@
     }
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       Assert.assertEquals(JPrimitiveTypeEnum.INT.getType(), new JBitAndOperation(SourceOrigin.UNKNOWN,
           new JLocalRef(SourceOrigin.UNKNOWN, l), new JLocalRef(SourceOrigin.UNKNOWN, l))
@@ -377,9 +377,9 @@
     }
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_INTEGER);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
-      JType t1 = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+      JType t1 = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
       JLocal l1 = new JLocal(SourceOrigin.UNKNOWN, "test", t1, JModifier.DEFAULT, null);
       try {
         catched = false;
@@ -393,7 +393,7 @@
     }
 
     {
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_FLOAT);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_FLOAT);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       try {
         catched = false;
@@ -445,7 +445,7 @@
 
     try {
       catched = false;
-      JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+      JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
       JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
       new JEqOperation(SourceOrigin.UNKNOWN, new JLocalRef(SourceOrigin.UNKNOWN, l),
           new JIntLiteral(SourceOrigin.UNKNOWN, 1)).getType();
@@ -455,7 +455,7 @@
     }
     Assert.assertTrue(catched);
 
-    JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+    JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
     Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JEqOperation(SourceOrigin.UNKNOWN,
         new JLocalRef(SourceOrigin.UNKNOWN, l), new JLocalRef(SourceOrigin.UNKNOWN, l)).getType());
@@ -479,7 +479,7 @@
     }
     Assert.assertTrue(catched);
 
-    JType t = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
+    JType t = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_BOOLEAN);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", t, JModifier.DEFAULT, null);
     Assert.assertEquals(JPrimitiveTypeEnum.BOOLEAN.getType(), new JAndOperation(SourceOrigin.UNKNOWN,
         new JLocalRef(SourceOrigin.UNKNOWN, l), new JLocalRef(SourceOrigin.UNKNOWN, l)).getType());
@@ -488,7 +488,7 @@
   @Test
   public void arithmeticGetType() throws Exception {
     boolean catched;
-    JType objectType = Jack.getProgram().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
+    JType objectType = Jack.getSession().getPhantomLookup().getClass(CommonTypes.JAVA_LANG_OBJECT);
     JLocal l = new JLocal(SourceOrigin.UNKNOWN, "test", objectType, JModifier.DEFAULT, null);
 
     try {
diff --git a/jack/tests/com/android/jack/UnaryTest.java b/jack/tests/com/android/jack/UnaryTest.java
index cf5d1d1..2b04da4 100644
--- a/jack/tests/com/android/jack/UnaryTest.java
+++ b/jack/tests/com/android/jack/UnaryTest.java
@@ -78,8 +78,8 @@
     String classBinaryName = "com/android/jack/unary/test005/jack/UnaryNot";
     String methodSignature = "getValue1(II)I";
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
 
     Assert.assertNotNull(m);
     CountIfStatement cis = new CountIfStatement();
@@ -88,8 +88,8 @@
 
     methodSignature = "getValue2(IIII)I";
     m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
 
     Assert.assertNotNull(m);
     cis = new CountIfStatement();
diff --git a/jack/tests/com/android/jack/analysis/dfa/reachingdefs/ReachingDefsTest.java b/jack/tests/com/android/jack/analysis/dfa/reachingdefs/ReachingDefsTest.java
index d6fdaca..b1765dd 100644
--- a/jack/tests/com/android/jack/analysis/dfa/reachingdefs/ReachingDefsTest.java
+++ b/jack/tests/com/android/jack/analysis/dfa/reachingdefs/ReachingDefsTest.java
@@ -18,7 +18,6 @@
 
 import com.android.jack.Main;
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.analysis.DefinitionMarker;
 import com.android.jack.cfg.BasicBlock;
@@ -28,6 +27,7 @@
 import com.android.jack.ir.ast.JIntLiteral;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JVariableRef;
+import com.android.jack.util.filter.SignatureMethodFilter;
 import com.android.sched.util.codec.ImplementationName;
 
 import junit.framework.Assert;
@@ -83,7 +83,9 @@
   public void testDfa001() throws Exception {
     Options options = TestTools.buildCommandLineArgs(TestTools
         .getJackTestsWithJackFolder("analysis/dfa/reachingdefs/test001"));
-    options.setFilter(new SignatureMethodFilter("dfaWithSwitch(I)I"));
+    options.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    options.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        "dfaWithSwitch(I)I");
     options.addProperty(ReachingDefinitions.REACHING_DEFS_CHECKER.getName(), "test001Checker");
     TestTools.runCompilation(options);
   }
diff --git a/jack/tests/com/android/jack/cfg/BuildCfgErrorTest.java b/jack/tests/com/android/jack/cfg/BuildCfgErrorTest.java
index c25a31d..110602f 100644
--- a/jack/tests/com/android/jack/cfg/BuildCfgErrorTest.java
+++ b/jack/tests/com/android/jack/cfg/BuildCfgErrorTest.java
@@ -20,7 +20,6 @@
 
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.util.filter.RejectAllMethods;
 import com.android.jack.util.graph.GraphException;
 
 import org.junit.Before;
@@ -41,9 +40,10 @@
    */
   @Test
   public void cfgError001() throws Exception {
-    JMethod method = TestTools.getJMethod(
-        TestTools.getJackTestFromBinaryName(CLASS_BINARY_NAME), "L" + CLASS_BINARY_NAME + ";",
-        "fibonacci(I)I", new RejectAllMethods());
+    JMethod method =
+        TestTools.getJMethodWithRejectAllFilter(
+            TestTools.getJackTestFromBinaryName(CLASS_BINARY_NAME), "L" + CLASS_BINARY_NAME + ";",
+            "fibonacci(I)I");
     ControlFlowGraph cfg = new ControlFlowGraph(method);
     NormalBasicBlock b0 = new NormalBasicBlock(cfg, BasicBlock.EMPTY_STATEMENT_LIST);
     NormalBasicBlock b1 = new NormalBasicBlock(cfg, BasicBlock.EMPTY_STATEMENT_LIST);
diff --git a/jack/tests/com/android/jack/cfg/BuildCfgTest.java b/jack/tests/com/android/jack/cfg/BuildCfgTest.java
index c55d10d..4640658 100644
--- a/jack/tests/com/android/jack/cfg/BuildCfgTest.java
+++ b/jack/tests/com/android/jack/cfg/BuildCfgTest.java
@@ -18,13 +18,13 @@
 
 
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JAsgOperation;
 import com.android.jack.ir.ast.JExpressionStatement;
 import com.android.jack.ir.ast.JIfStatement;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JStatement;
+import com.android.jack.util.filter.SignatureMethodFilter;
 
 import junit.framework.Assert;
 
@@ -47,7 +47,9 @@
     File fileName = TestTools.getJackTestFromBinaryName(CLASS_BINARY_NAME);
     final String methodSignature = "fibonacci(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(fileName);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method = CfgTools.buildCfg(classSignature, methodSignature, commandLineArgs);
 
diff --git a/jack/tests/com/android/jack/cfg/CfgTools.java b/jack/tests/com/android/jack/cfg/CfgTools.java
index 8520ac6..d81af75 100644
--- a/jack/tests/com/android/jack/cfg/CfgTools.java
+++ b/jack/tests/com/android/jack/cfg/CfgTools.java
@@ -26,7 +26,7 @@
 import com.android.jack.ir.ast.JFieldInitializer;
 import com.android.jack.ir.ast.JLoop;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JSynchronizedBlock;
 import com.android.jack.ir.ast.JTryStatement;
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
@@ -50,8 +50,8 @@
 
   public static JMethod buildCfg(
       String classSignature, String methodSignature, Options options) throws Exception {
-    JProgram jprogram = TestTools.buildJAst(options);
-    Assert.assertNotNull(jprogram);
+    JSession session = TestTools.buildJAst(options);
+    Assert.assertNotNull(session);
 
 
     Scheduler scheduler = Scheduler.getScheduler();
@@ -74,8 +74,8 @@
     set.remove(JFieldInitializer.class);
     sr.addInitialTagsOrMarkers(set);
 
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
-    SubPlanBuilder<JDefinedClassOrInterface> typePlan = progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
+    SubPlanBuilder<JDefinedClassOrInterface> typePlan = planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
     methodPlan.append(ImplicitBlocks.class);
     methodPlan.append(ImplicitBlocksChecker.class);
@@ -83,10 +83,10 @@
     methodPlan.append(TryCatchRemover.class);
     methodPlan.append(CfgBuilder.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
     JDefinedClassOrInterface type = (JDefinedClassOrInterface)
-        jprogram.getLookup().getType(classSignature);
+        session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod foundMethod = TestTools.getMethod(type, methodSignature);
diff --git a/jack/tests/com/android/jack/frontend/AllTests.java b/jack/tests/com/android/jack/frontend/AllTests.java
index 7e3ee65..c3041fa 100644
--- a/jack/tests/com/android/jack/frontend/AllTests.java
+++ b/jack/tests/com/android/jack/frontend/AllTests.java
@@ -25,6 +25,7 @@
     TypeModifierTest.class,
     FieldModifierTest.class,
     MethodModifierTest.class,
+    MissingClassTest.class,
     ClinitTest.class,
     InitTest.class,
     InstanceTest.class,
diff --git a/jack/tests/com/android/jack/frontend/ArrayTest.java b/jack/tests/com/android/jack/frontend/ArrayTest.java
index 94c3cce..fe722a1 100644
--- a/jack/tests/com/android/jack/frontend/ArrayTest.java
+++ b/jack/tests/com/android/jack/frontend/ArrayTest.java
@@ -18,7 +18,6 @@
 
 
 import com.android.jack.TestTools;
-import com.android.jack.util.filter.RejectAllMethods;
 
 import org.junit.Before;
 import org.junit.Test;
@@ -33,7 +32,7 @@
   @Test
   public void arrayReuse() throws Exception {
     String binaryName = "com/android/jack/newarray/test003/jack/ArrayReuse";
-    TestTools.getJMethod(TestTools.getJackTestFromBinaryName(binaryName),
-        "L" + binaryName + ";", "arrayDimReuse()V", new RejectAllMethods());
+    TestTools.getJMethodWithRejectAllFilter(TestTools.getJackTestFromBinaryName(binaryName), "L"
+        + binaryName + ";", "arrayDimReuse()V");
   }
 }
diff --git a/jack/tests/com/android/jack/frontend/ClinitTest.java b/jack/tests/com/android/jack/frontend/ClinitTest.java
index 799316b..e438566 100644
--- a/jack/tests/com/android/jack/frontend/ClinitTest.java
+++ b/jack/tests/com/android/jack/frontend/ClinitTest.java
@@ -24,9 +24,8 @@
 import com.android.jack.ir.ast.JExpressionStatement;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
 import com.android.jack.ir.ast.JStatement;
-import com.android.jack.util.filter.RejectAllMethods;
+import com.android.jack.util.NamingTools;
 
 import junit.framework.Assert;
 
@@ -49,10 +48,10 @@
 
   @Test
   public void searchStaticInit() throws Exception {
-    JMethod clinit = TestTools.getJMethod(
+    JMethod clinit = TestTools.getJMethodWithRejectAllFilter(
         TestTools.getJackTestFromBinaryName(CLASS_WITH_VARIABLE_INIT_BINARY_NAME),
         "L" + CLASS_WITH_VARIABLE_INIT_BINARY_NAME + ";",
-        JProgram.STATIC_INIT_NAME + "()V", new RejectAllMethods());
+        NamingTools.STATIC_INIT_NAME + "()V");
 
     JMethodBody body = (JMethodBody) clinit.getBody();
     assert body != null;
@@ -75,9 +74,9 @@
 
   @Test
   public void searchEmptyStaticInit() throws Exception {
-    JMethod clinit = TestTools.getJMethod(
+    JMethod clinit = TestTools.getJMethodWithRejectAllFilter(
         TestTools.getJackTestFromBinaryName(CLASS_BINARY_NAME),
-        "L" + CLASS_BINARY_NAME + ";", JProgram.STATIC_INIT_NAME + "()V",new RejectAllMethods());
+        "L" + CLASS_BINARY_NAME + ";", NamingTools.STATIC_INIT_NAME + "()V");
 
     Assert.assertEquals(0, ((JMethodBody)clinit.getBody()).getStatements().size());
   }
diff --git a/jack/tests/com/android/jack/frontend/ConstantReuseTest.java b/jack/tests/com/android/jack/frontend/ConstantReuseTest.java
index 971beec..3253449 100644
--- a/jack/tests/com/android/jack/frontend/ConstantReuseTest.java
+++ b/jack/tests/com/android/jack/frontend/ConstantReuseTest.java
@@ -18,7 +18,6 @@
 
 
 import com.android.jack.TestTools;
-import com.android.jack.util.filter.RejectAllMethods;
 
 import org.junit.Before;
 import org.junit.Test;
@@ -38,73 +37,73 @@
 
   @Test
   public void intConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "intConstantReuse()V", new RejectAllMethods());
+        "intConstantReuse()V");
   }
 
   @Test
   public void byteConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "byteConstantReuse()V", new RejectAllMethods());
+        "byteConstantReuse()V");
   }
 
   @Test
   public void shortConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "shortConstantReuse()V", new RejectAllMethods());
+        "shortConstantReuse()V");
   }
 
   @Test
   public void charConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "charConstantReuse()V", new RejectAllMethods());
+        "charConstantReuse()V");
   }
 
   @Test
   public void floatConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "floatConstantReuse()V", new RejectAllMethods());
+        "floatConstantReuse()V");
   }
 
   @Test
   public void longConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "longConstantReuse()V",new RejectAllMethods());
+        "longConstantReuse()V");
   }
 
   @Test
   public void doubleConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "doubleConstantReuse()V",new RejectAllMethods());
+        "doubleConstantReuse()V");
   }
 
   @Test
   public void booleanConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "booleanConstantReuse()V", new RejectAllMethods());
+        "booleanConstantReuse()V");
   }
 
   @Test
   public void nullConstantReuse() throws Exception {
-    TestTools.getJMethod(
+    TestTools.getJMethodWithRejectAllFilter(
         TEST_FILE,
         CLASS_SIGNATURE,
-        "nullConstantReuse()V", new RejectAllMethods());
+        "nullConstantReuse()V");
   }
 }
diff --git a/jack/tests/com/android/jack/frontend/FieldModifierTest.java b/jack/tests/com/android/jack/frontend/FieldModifierTest.java
index b4ed809..e8d4427 100644
--- a/jack/tests/com/android/jack/frontend/FieldModifierTest.java
+++ b/jack/tests/com/android/jack/frontend/FieldModifierTest.java
@@ -21,8 +21,7 @@
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JField;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.util.filter.RejectAllMethods;
+import com.android.jack.ir.ast.JSession;
 
 import junit.framework.Assert;
 
@@ -31,27 +30,31 @@
 
 public class FieldModifierTest {
 
-  private JProgram program;
+  private JSession session;
 
-  private final static String FIELD_MODIFIER_BINARY_NAME = "com/android/jack/modifier/jack/FieldModifier";
+  private final static String FIELD_MODIFIER_BINARY_NAME =
+      "com/android/jack/modifier/jack/FieldModifier";
   private final static String FIELD_MODIFIER_SIGNATURE = "L" + FIELD_MODIFIER_BINARY_NAME + ";";
-  private final static String FIELD_ENUM_BINARY_NAME = "com/android/jack/modifier/jack/FieldEnumModifier";
+  private final static String FIELD_ENUM_BINARY_NAME =
+      "com/android/jack/modifier/jack/FieldEnumModifier";
 
   @Before
   public void setUp() throws Exception {
     FieldModifierTest.class.getClassLoader().setDefaultAssertionStatus(true);
 
-    Options jackArgs = TestTools.buildCommandLineArgs(
-        TestTools.getJackTestFromBinaryName(FIELD_MODIFIER_BINARY_NAME));
-    jackArgs.setFilter(new RejectAllMethods());
+    Options jackArgs =
+        TestTools.buildCommandLineArgs(TestTools
+            .getJackTestFromBinaryName(FIELD_MODIFIER_BINARY_NAME));
+    jackArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
 
-    program = TestTools.buildProgram(jackArgs);
-    Assert.assertNotNull(program);
+    session = TestTools.buildSession(jackArgs);
+    Assert.assertNotNull(session);
   }
 
   @Test
   public void fieldPublicModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldPublic");
@@ -62,7 +65,8 @@
 
   @Test
   public void fieldProtectedModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldProtected");
@@ -73,7 +77,8 @@
 
   @Test
   public void fieldPrivateModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldPrivate");
@@ -84,7 +89,8 @@
 
   @Test
   public void fieldStaticModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldStatic");
@@ -95,7 +101,8 @@
 
   @Test
   public void fieldVolatileModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldVolatile");
@@ -106,7 +113,8 @@
 
   @Test
   public void fieldFinalModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldFinal");
@@ -117,7 +125,8 @@
 
   @Test
   public void fieldTransientModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldTransient");
@@ -128,7 +137,8 @@
 
   @Test
   public void fieldPublicFinalModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldPublicFinal");
@@ -139,7 +149,8 @@
 
   @Test
   public void fieldMultipleFinalModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(FIELD_MODIFIER_SIGNATURE);
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "fieldProtectedStaticVolatileTransient");
@@ -153,12 +164,14 @@
   public void fieldEnumModifier() throws Exception {
     Options args = TestTools.buildCommandLineArgs(
         TestTools.getJackTestFromBinaryName(FIELD_ENUM_BINARY_NAME));
-    args.setFilter(new RejectAllMethods());
+    args.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
 
-    JProgram program = TestTools.buildProgram(args);
-    Assert.assertNotNull(program);
+    JSession session = TestTools.buildSession(args);
+    Assert.assertNotNull(session);
 
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType("L" + FIELD_ENUM_BINARY_NAME + "$Select;");
+    JDefinedClassOrInterface type =
+        (JDefinedClassOrInterface) session.getLookup().getType(
+            "L" + FIELD_ENUM_BINARY_NAME + "$Select;");
     Assert.assertNotNull(type);
 
     JField field = getFieldFromName(type, "ONE");
diff --git a/jack/tests/com/android/jack/frontend/FrontendTools.java b/jack/tests/com/android/jack/frontend/FrontendTools.java
index 64f0983..6a3bbbf 100644
--- a/jack/tests/com/android/jack/frontend/FrontendTools.java
+++ b/jack/tests/com/android/jack/frontend/FrontendTools.java
@@ -20,7 +20,7 @@
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 
 import junit.framework.Assert;
 
@@ -29,10 +29,10 @@
   public static JMethod parseMethod(
       String classSignature, String methodSignature, Options options)
       throws Exception {
-    JProgram jprogram = TestTools.buildJAst(options);
-    Assert.assertNotNull(jprogram);
+    JSession session = TestTools.buildJAst(options);
+    Assert.assertNotNull(session);
 
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) jprogram.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod foundMethod = TestTools.getMethod(type, methodSignature);
diff --git a/jack/tests/com/android/jack/frontend/GotoTest.java b/jack/tests/com/android/jack/frontend/GotoTest.java
index 6da6520..570b08a 100644
--- a/jack/tests/com/android/jack/frontend/GotoTest.java
+++ b/jack/tests/com/android/jack/frontend/GotoTest.java
@@ -27,7 +27,6 @@
 import com.android.jack.ir.ast.JMethodBody;
 import com.android.jack.ir.ast.JReturnStatement;
 import com.android.jack.ir.ast.JStatement;
-import com.android.jack.util.filter.RejectAllMethods;
 
 import junit.framework.Assert;
 import junit.framework.AssertionFailedError;
@@ -47,9 +46,9 @@
 
   @Test
   public void dumpGoto() throws Exception {
-    JMethod dumpGoto = TestTools.getJMethod(
+    JMethod dumpGoto = TestTools.getJMethodWithRejectAllFilter(
         TestTools.getJackUnitTestFromBinaryName(TEST_CLASS_BINARY_NAME),
-        "L" + TEST_CLASS_BINARY_NAME + ";", "synthetizeCode()V", new RejectAllMethods());
+        "L" + TEST_CLASS_BINARY_NAME + ";", "synthetizeCode()V");
 
     JMethodBody body = (JMethodBody) dumpGoto.getBody();
     assert body != null;
diff --git a/jack/tests/com/android/jack/frontend/InitTest.java b/jack/tests/com/android/jack/frontend/InitTest.java
index 156ff48..b32790d 100644
--- a/jack/tests/com/android/jack/frontend/InitTest.java
+++ b/jack/tests/com/android/jack/frontend/InitTest.java
@@ -19,8 +19,7 @@
 import com.android.jack.Options;
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.util.filter.RejectAllMethods;
+import com.android.jack.util.NamingTools;
 
 import junit.framework.Assert;
 
@@ -37,10 +36,10 @@
   @Test
   public void searchInit() throws Exception {
     String binaryName = "com/android/jack/fibonacci/jack/Fibo";
-    JMethod init = TestTools.getJMethod(
+    JMethod init = TestTools.getJMethodWithRejectAllFilter(
         TestTools.getJackTestFromBinaryName(binaryName),
         "L" + binaryName + ";",
-        JProgram.INIT_NAME+"()V", new RejectAllMethods());
+        NamingTools.INIT_NAME+"()V");
 
     Assert.assertNotNull(init);
   }
diff --git a/jack/tests/com/android/jack/frontend/MethodModifierTest.java b/jack/tests/com/android/jack/frontend/MethodModifierTest.java
index d82d639..c0e1d22 100644
--- a/jack/tests/com/android/jack/frontend/MethodModifierTest.java
+++ b/jack/tests/com/android/jack/frontend/MethodModifierTest.java
@@ -22,8 +22,7 @@
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.util.filter.RejectAllMethods;
+import com.android.jack.ir.ast.JSession;
 
 import junit.framework.Assert;
 
@@ -33,7 +32,7 @@
 
 public class MethodModifierTest {
 
-  private JProgram program;
+  private JSession session;
   private final String classBinaryName = "com/android/jack/modifier/jack/MethodModifier";
   private final String classSignature = "L" + classBinaryName + ";";
 
@@ -43,15 +42,15 @@
 
     Options jackArgs = TestTools.buildCommandLineArgs(
         TestTools.getJackTestFromBinaryName(classBinaryName));
-    jackArgs.setFilter(new RejectAllMethods());
+    jackArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
 
-    program = TestTools.buildProgram(jackArgs);
-    Assert.assertNotNull(program);
+    session = TestTools.buildSession(jackArgs);
+    Assert.assertNotNull(session);
   }
 
   @Test
   public void methodPublicModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodPublic()V");
@@ -62,7 +61,7 @@
 
   @Test
   public void methodProtectedModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodProtected()V");
@@ -73,7 +72,7 @@
 
   @Test
   public void methodPrivateModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodPrivate()V");
@@ -84,7 +83,7 @@
 
   @Test
   public void methodStaticModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodStatic()V");
@@ -95,7 +94,7 @@
 
   @Test
   public void methodFinalModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodFinal()V");
@@ -106,7 +105,7 @@
 
   @Test
   public void methodPublicFinalModifier() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodPublicFinal()V");
@@ -117,7 +116,7 @@
 
   @Test
   public void methodSynchronized() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodSynchronized()V");
@@ -128,7 +127,7 @@
 
   @Test
   public void methodNative() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodNative()V");
@@ -140,7 +139,7 @@
   @Test
   @Ignore
   public void methodVarags() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodVarags([I)V");
@@ -151,7 +150,7 @@
 
   @Test
   public void constructorPrivate() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "<init>()V");
@@ -162,7 +161,7 @@
 
   @Test
   public void constructorPublic() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "<init>(I)V");
@@ -173,7 +172,7 @@
 
   @Test
   public void methodAbstract() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodAbstract()V");
@@ -184,7 +183,7 @@
 
   @Test
   public void clinit() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = type.getMethod("<clinit>", JPrimitiveTypeEnum.VOID.getType());
@@ -195,7 +194,7 @@
 
   @Test
   public void methodStrictfp() throws Exception {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup().getType(classSignature);
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup().getType(classSignature);
     Assert.assertNotNull(type);
 
     JMethod method = TestTools.getMethod(type, "methodStrictfp()V");
diff --git a/jack/tests/com/android/jack/frontend/MissingClassTest.java b/jack/tests/com/android/jack/frontend/MissingClassTest.java
new file mode 100644
index 0000000..8aacd6b
--- /dev/null
+++ b/jack/tests/com/android/jack/frontend/MissingClassTest.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.jack.frontend;
+
+import com.android.jack.Options;
+import com.android.jack.TestTools;
+import com.android.jack.category.KnownBugs;
+
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+
+import java.io.File;
+
+public class MissingClassTest {
+
+  @Test
+  @Category(KnownBugs.class)
+  public void test001() throws Exception {
+    File outJackTmpMissing = TestTools.createTempDir("MissingClassTest001-missing", ".jack");
+    File outJackTmpSuper = TestTools.createTempDir("MissingClassTest001-super", ".jack");
+    File outJackTmpTest = TestTools.createTempDir("MissingClassTest001-test", ".jack");
+
+    TestTools.compileSourceToJack(new Options(),
+        new File(TestTools.getJackTestsWithJackFolder("frontend/test001"), "missing"),
+        TestTools.getDefaultBootclasspathString(), outJackTmpMissing, false /* zip */);
+
+    TestTools.compileSourceToJack(new Options(),
+        new File(TestTools.getJackTestsWithJackFolder("frontend/test001"), "sub2"),
+            TestTools.getDefaultBootclasspathString() + File.pathSeparator
+            + outJackTmpMissing.getPath(), outJackTmpSuper, false /* zip */);
+
+    TestTools.compileSourceToJack(new Options(),
+        new File(TestTools.getJackTestsWithJackFolder("frontend/test001"), "test"),
+        TestTools.getDefaultBootclasspathString() + File.pathSeparator + outJackTmpSuper.getPath(),
+        outJackTmpTest, false /* zip */);
+
+  }
+
+}
diff --git a/jack/tests/com/android/jack/frontend/SwitchTest.java b/jack/tests/com/android/jack/frontend/SwitchTest.java
index f5b5f84..fd34953 100644
--- a/jack/tests/com/android/jack/frontend/SwitchTest.java
+++ b/jack/tests/com/android/jack/frontend/SwitchTest.java
@@ -17,13 +17,13 @@
 package com.android.jack.frontend;
 
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JBlock;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JSwitchStatement;
+import com.android.jack.util.filter.SignatureMethodFilter;
 
 import junit.framework.Assert;
 
@@ -53,7 +53,9 @@
   public void testCompileSwitch001() throws Exception {
     final String methodSignature = "switch001(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -71,7 +73,9 @@
   public void testCompileSwitch002() throws Exception {
     final String methodSignature = "switch002(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -98,7 +102,9 @@
   public void testCompileSwitch003() throws Exception {
     final String methodSignature = "switch003(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -113,7 +119,9 @@
   public void testCompileSwitch004() throws Exception {
     final String methodSignature = "switch004(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
diff --git a/jack/tests/com/android/jack/frontend/SynchronizedTest.java b/jack/tests/com/android/jack/frontend/SynchronizedTest.java
index d837001..d112ca9 100644
--- a/jack/tests/com/android/jack/frontend/SynchronizedTest.java
+++ b/jack/tests/com/android/jack/frontend/SynchronizedTest.java
@@ -17,7 +17,6 @@
 package com.android.jack.frontend;
 
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.SourceInfo;
 import com.android.jack.ir.ast.JClass;
@@ -25,7 +24,7 @@
 import com.android.jack.ir.ast.JLock;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JReturnStatement;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JSynchronizedBlock;
@@ -33,6 +32,7 @@
 import com.android.jack.lookup.CommonTypes;
 import com.android.jack.transformations.request.AppendBefore;
 import com.android.jack.transformations.request.TransformationRequest;
+import com.android.jack.util.filter.SignatureMethodFilter;
 
 import junit.framework.Assert;
 
@@ -61,7 +61,9 @@
   public void testSynchronizedBlock() throws Exception {
     final String methodSignature = "sync(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -80,7 +82,9 @@
   public void testSynchronizedMethod() throws Exception {
     final String methodSignature = "syncMethod(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -96,7 +100,9 @@
   public void testLockUnlock() throws Exception {
     final String methodSignature = "syncMethod(I)I";
     Options commandLineArgs = TestTools.buildCommandLineArgs(FILE);
-    commandLineArgs.setFilter(new SignatureMethodFilter(methodSignature));
+    commandLineArgs.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    commandLineArgs.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
 
     JMethod method =
         FrontendTools.parseMethod(CLASS_SIGNATURE, methodSignature, commandLineArgs);
@@ -111,7 +117,7 @@
     SourceInfo srcInfo = firstStmt.getSourceInfo();
 
     TransformationRequest tr = new TransformationRequest(method);
-    JClass javaLangClass = method.getParent(JProgram.class).getPhantomLookup()
+    JClass javaLangClass = method.getParent(JSession.class).getPhantomLookup()
         .getClass(CommonTypes.JAVA_LANG_CLASS);
     tr.append(new AppendBefore(firstStmt, new JLock(srcInfo,
         new JClassLiteral(srcInfo, method.getEnclosingType(), javaLangClass))));
diff --git a/jack/tests/com/android/jack/frontend/TypeModifierTest.java b/jack/tests/com/android/jack/frontend/TypeModifierTest.java
index 94d5a13..2ae0a66 100644
--- a/jack/tests/com/android/jack/frontend/TypeModifierTest.java
+++ b/jack/tests/com/android/jack/frontend/TypeModifierTest.java
@@ -20,8 +20,7 @@
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JModifier;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.util.filter.RejectAllMethods;
+import com.android.jack.ir.ast.JSession;
 
 import junit.framework.Assert;
 
@@ -29,7 +28,7 @@
 import org.junit.Test;
 
 public class TypeModifierTest {
-  private JProgram program;
+  private JSession session;
   private static final String OUTER_CLASS_BINARY_NAME = "com/android/jack/modifier/jack/TypeModifier";
 
   @Before
@@ -38,13 +37,13 @@
 
     Options jackArgs = TestTools.buildCommandLineArgs(
         TestTools.getJackTestFromBinaryName(OUTER_CLASS_BINARY_NAME));
-    jackArgs.setFilter(new RejectAllMethods());
-    program = TestTools.buildProgram(jackArgs);
-    Assert.assertNotNull(program);
+    jackArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
+    session = TestTools.buildSession(jackArgs);
+    Assert.assertNotNull(session);
   }
 
   private JDefinedClassOrInterface lookupInnerClass(String className) {
-    JDefinedClassOrInterface type = (JDefinedClassOrInterface) program.getLookup()
+    JDefinedClassOrInterface type = (JDefinedClassOrInterface) session.getLookup()
         .getType("L" + OUTER_CLASS_BINARY_NAME + "$" + className + ";");
     Assert.assertNotNull(type);
     return type;
diff --git a/jack/tests/com/android/jack/gwt/BinaryLookup.java b/jack/tests/com/android/jack/gwt/BinaryLookup.java
index ab85e6c..37d549e 100644
--- a/jack/tests/com/android/jack/gwt/BinaryLookup.java
+++ b/jack/tests/com/android/jack/gwt/BinaryLookup.java
@@ -24,11 +24,10 @@
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JType;
 import com.android.jack.lookup.CommonTypes;
 import com.android.jack.lookup.JLookup;
-import com.android.jack.util.filter.RejectAllMethods;
 import com.android.sched.util.RunnableHooks;
 
 import junit.framework.Assert;
@@ -41,7 +40,7 @@
 
   private static RunnableHooks hooks;
   private static JLookup lookup;
-  private static JProgram program;
+  private static JSession session;
 
   @BeforeClass
   public static void setUpClass() throws Exception {
@@ -49,10 +48,10 @@
 
     Options fiboArgs = TestTools.buildCommandLineArgs(
         TestTools.getJackTestFromBinaryName("com/android/jack/fibonacci/jack/Fibo"));
-    fiboArgs.setFilter(new RejectAllMethods());
+    fiboArgs.addProperty(Options.METHOD_FILTER.getName(), "reject-all-methods");
     hooks = new RunnableHooks();
-    program = TestTools.buildProgram(fiboArgs, hooks);
-    lookup = program.getLookup();
+    session = TestTools.buildSession(fiboArgs, hooks);
+    lookup = session.getLookup();
   }
 
   @AfterClass
@@ -65,10 +64,11 @@
     JType jls = lookup.getType(CommonTypes.JAVA_LANG_STRING);
 
     Assert.assertTrue(Jack.getLookupFormatter().getName(jls).equals("Ljava/lang/String;"));
-    Assert.assertTrue(program.isJavaLangString(jls));
-    Assert.assertTrue(program.getLookup().getType(CommonTypes.JAVA_LANG_STRING) == jls);
-    Assert.assertTrue(program.getLookup().getType("Ljava/lang/String;") == jls);
-    Assert.assertTrue(program.getLookup().getClass(CommonTypes.JAVA_LANG_STRING) ==
+    Assert.assertTrue(jls ==
+        session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING));
+    Assert.assertTrue(session.getLookup().getType(CommonTypes.JAVA_LANG_STRING) == jls);
+    Assert.assertTrue(session.getLookup().getType("Ljava/lang/String;") == jls);
+    Assert.assertTrue(session.getLookup().getClass(CommonTypes.JAVA_LANG_STRING) ==
         lookup.getClass("Ljava/lang/String;"));
   }
 
@@ -77,8 +77,8 @@
     JType jls = lookup.getType("[[[Ljava/lang/String;");
 
     Assert.assertTrue(Jack.getLookupFormatter().getName(jls).equals("[[[Ljava/lang/String;"));
-    Assert.assertTrue(program.getLookup()
-        .getArrayType(program.getLookup().getType(CommonTypes.JAVA_LANG_STRING), 3) == jls);
+    Assert.assertTrue(session.getLookup()
+        .getArrayType(session.getLookup().getType(CommonTypes.JAVA_LANG_STRING), 3) == jls);
   }
 
   @Test
@@ -199,7 +199,8 @@
     JMethod append = TestTools.getMethod(type, "append(Ljava/lang/String;)Ljava/lang/StringBuilder;");
 
     Assert.assertTrue(append.getName().equals("append"));
-    Assert.assertTrue(program.isJavaLangString(append.getParams().get(0).getType()));
+    Assert.assertTrue(append.getParams().get(0).getType() ==
+        session.getPhantomLookup().getClass(CommonTypes.JAVA_LANG_STRING));
   }
 
   @Test
diff --git a/jack/tests/com/android/jack/ir/ast/MarkerCollectorTest.java b/jack/tests/com/android/jack/ir/ast/MarkerCollectorTest.java
index d98ced3..8041496 100644
--- a/jack/tests/com/android/jack/ir/ast/MarkerCollectorTest.java
+++ b/jack/tests/com/android/jack/ir/ast/MarkerCollectorTest.java
@@ -38,7 +38,7 @@
   private final JParameter param;
 
   public MarkerCollectorTest() {
-    JPackage p = new JPackage("test", new JProgram(), null);
+    JPackage p = new JPackage("test", new JSession(), null);
     JDefinedClass classTest = new JDefinedClass(SourceOrigin.UNKNOWN, "Test", JModifier.PUBLIC, p,
         NopClassOrInterfaceLoader.INSTANCE);
     JMethod method =
diff --git a/jack/tests/com/android/jack/optimizations/ExpressionSimplifierTest.java b/jack/tests/com/android/jack/optimizations/ExpressionSimplifierTest.java
index b4fd726..8fa7eac 100644
--- a/jack/tests/com/android/jack/optimizations/ExpressionSimplifierTest.java
+++ b/jack/tests/com/android/jack/optimizations/ExpressionSimplifierTest.java
@@ -46,7 +46,7 @@
 import com.android.jack.ir.ast.JPrefixNegOperation;
 import com.android.jack.ir.ast.JPrefixNotOperation;
 import com.android.jack.ir.ast.JPrimitiveType.JPrimitiveTypeEnum;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JShortLiteral;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.MethodKind;
@@ -75,7 +75,7 @@
   private final JParameter param;
 
   public ExpressionSimplifierTest() {
-    JPackage p = new JPackage("test", new JProgram(), null);
+    JPackage p = new JPackage("test", new JSession(), null);
     classTest = new JDefinedClass(SourceOrigin.UNKNOWN, "Test", JModifier.PUBLIC, p,
         NopClassOrInterfaceLoader.INSTANCE);
     method =
diff --git a/jack/tests/com/android/jack/optimizations/NotSimplifierTest.java b/jack/tests/com/android/jack/optimizations/NotSimplifierTest.java
index 086e2e0..b222ba2 100644
--- a/jack/tests/com/android/jack/optimizations/NotSimplifierTest.java
+++ b/jack/tests/com/android/jack/optimizations/NotSimplifierTest.java
@@ -16,7 +16,6 @@
 
 package com.android.jack.optimizations;
 
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JBinaryOperation;
 import com.android.jack.ir.ast.JBinaryOperator;
@@ -45,8 +44,8 @@
     String methodSignature = "test001(II)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.EQ).accept(m);
@@ -60,8 +59,8 @@
     String methodSignature = "test002(II)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.LT).accept(m);
@@ -74,8 +73,8 @@
     String methodSignature = "test003(IIII)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.LT).accept(m);
@@ -89,8 +88,8 @@
     String methodSignature = "test004(IIZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.LT).accept(m);
@@ -103,8 +102,8 @@
     String methodSignature = "test005(IIII)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.LT).accept(m);
@@ -118,8 +117,8 @@
     String methodSignature = "test006(II)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.NEQ).accept(m);
@@ -132,8 +131,8 @@
     String methodSignature = "test007(II)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.EQ).accept(m);
@@ -146,8 +145,8 @@
     String methodSignature = "test008(II)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.NEQ).accept(m);
@@ -160,8 +159,8 @@
     String methodSignature = "test009(IIII)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.NEQ).accept(m);
@@ -174,8 +173,8 @@
     String methodSignature = "test010(Z)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     Assert
@@ -190,8 +189,8 @@
     String methodSignature = "test011(ZZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     checkFirstStatement(m, JBinaryOperator.BIT_OR);
@@ -204,8 +203,8 @@
     String methodSignature = "test012(ZZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     checkFirstStatement(m, JBinaryOperator.BIT_AND);
@@ -218,8 +217,8 @@
     String methodSignature = "test013(ZZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     checkFirstStatement(m, JBinaryOperator.BIT_XOR);
@@ -232,8 +231,8 @@
     String methodSignature = "test014(ZZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.BIT_AND).accept(m);
@@ -246,8 +245,8 @@
     String methodSignature = "test015(ZZ)Z";
 
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
+            + classBinaryName + ";", methodSignature);
     Assert.assertNotNull(m);
 
     new CheckAbsenceOfBinaryOp(JBinaryOperator.BIT_OR).accept(m);
diff --git a/jack/tests/com/android/jack/shrob/AbstractTest.java b/jack/tests/com/android/jack/shrob/AbstractTest.java
index 229b7ef..9afc34c 100644
--- a/jack/tests/com/android/jack/shrob/AbstractTest.java
+++ b/jack/tests/com/android/jack/shrob/AbstractTest.java
@@ -233,29 +233,6 @@
   }
 
   @Test
-  public void test3_001() throws Exception {
-    String testName = "shrob/test003";
-    File[] defaultBoot = TestTools.getDefaultBootclasspath();
-    File[] bootclasspath = new File[defaultBoot.length + 1];
-    System.arraycopy(defaultBoot, 0, bootclasspath, 0, defaultBoot.length);
-    bootclasspath[defaultBoot.length] =
-        new File(TestTools.getJackTestFolder(testName).getAbsolutePath(), "test.jar");
-
-    runTest(bootclasspath, null, "003", "001", "");
-  }
-
-  @Test
-  @Category(SlowTests.class)
-  public void test3_001_bis() throws Exception {
-    String testName = "shrob/test003";
-
-    File[] classpath = new File[] {
-        new File(TestTools.getJackTestFolder(testName).getAbsolutePath(), "test.jar")
-    };
-    runTest(defaultBootclasspath, classpath, "003", "001", "");
-  }
-
-  @Test
   public void test4_001() throws Exception {
     runTest(defaultBootclasspath, null, "004", "001", "");
   }
diff --git a/jack/tests/com/android/jack/shrob/FlattenPackageTest.java b/jack/tests/com/android/jack/shrob/FlattenPackageTest.java
index ee38266..e2d36d6 100644
--- a/jack/tests/com/android/jack/shrob/FlattenPackageTest.java
+++ b/jack/tests/com/android/jack/shrob/FlattenPackageTest.java
@@ -18,13 +18,10 @@
 
 import com.android.jack.Options;
 import com.android.jack.TestTools;
-import com.android.jack.category.KnownBugs;
 import com.android.jack.category.SlowTests;
 import com.android.jack.shrob.proguard.GrammarActions;
 import com.android.jack.shrob.spec.Flags;
 
-import org.junit.Ignore;
-import org.junit.Test;
 import org.junit.experimental.categories.Category;
 
 import java.io.File;
@@ -61,20 +58,4 @@
         TestTools.getJackTestsWithJackFolder(testName), flags);
     ListingComparator.compare(refOutputMapping, candidateOutputMapping);
   }
-
-  @Test
-  @Category(KnownBugs.class)
-  @Override
-  @Ignore
-  public void test16_001() throws Exception {
-    runTest(defaultBootclasspath, null, "016", "001", "");
-  }
-
-  @Test
-  @Category(KnownBugs.class)
-  @Override
-  @Ignore
-  public void test16_002() throws Exception {
-    runTest(defaultBootclasspath, null, "016", "002", "");
-  }
 }
diff --git a/jack/tests/com/android/jack/shrob/ObfuscationWithoutMappingTest.java b/jack/tests/com/android/jack/shrob/ObfuscationWithoutMappingTest.java
index 2531ed8..794dc26 100644
--- a/jack/tests/com/android/jack/shrob/ObfuscationWithoutMappingTest.java
+++ b/jack/tests/com/android/jack/shrob/ObfuscationWithoutMappingTest.java
@@ -86,20 +86,6 @@
   @Override
   @Test
   @Category(KnownBugs.class)
-  public void test3_001() throws Exception {
-    super.test3_001();
-  }
-
-  @Override
-  @Test
-  @Category(KnownBugs.class)
-  public void test3_001_bis() throws Exception {
-    super.test3_001_bis();
-  }
-
-  @Override
-  @Test
-  @Category(KnownBugs.class)
   public void test19_001() throws Exception {
     super.test19_001();
   }
diff --git a/jack/tests/com/android/jack/shrob/SeedTest.java b/jack/tests/com/android/jack/shrob/SeedTest.java
index 024c7c8..841fa81 100644
--- a/jack/tests/com/android/jack/shrob/SeedTest.java
+++ b/jack/tests/com/android/jack/shrob/SeedTest.java
@@ -63,20 +63,6 @@
   @Override
   @Test
   @Category(KnownBugs.class)
-  public void test3_001() throws Exception {
-    super.test3_001();
-  }
-
-  @Override
-  @Test
-  @Category(KnownBugs.class)
-  public void test3_001_bis() throws Exception {
-    super.test3_001_bis();
-  }
-
-  @Override
-  @Test
-  @Category(KnownBugs.class)
   public void test19_001() throws Exception {
     super.test19_001();
   }
diff --git a/jack/tests/com/android/jack/shrob/TreeTest.java b/jack/tests/com/android/jack/shrob/TreeTest.java
index b5c843c..2b9f39f 100644
--- a/jack/tests/com/android/jack/shrob/TreeTest.java
+++ b/jack/tests/com/android/jack/shrob/TreeTest.java
@@ -21,7 +21,6 @@
 import com.android.jack.ProguardFlags;
 import com.android.jack.TestTools;
 import com.android.jack.category.SlowTests;
-import com.android.jack.util.filter.SupportedMethods;
 
 import org.junit.BeforeClass;
 import org.junit.Test;
@@ -50,8 +49,8 @@
     Options options = TestTools.buildCommandLineArgs(new File[]{CORE_SOURCELIST, testFolder});
     options.addProguardFlagsFile(new ProguardFlags(testFolder, "proguard.flags001"));
     options.addProguardFlagsFile(dontObfuscateFlagFile);
-    options.setFilter(new SupportedMethods());
+    options.addProperty(Options.METHOD_FILTER.getName(), "supported-methods");
 
-    TestTools.buildProgram(options);
+    TestTools.buildSession(options);
   }
 }
diff --git a/jack/tests/com/android/jack/statistics/BlockStatisticsOnCore.java b/jack/tests/com/android/jack/statistics/BlockStatisticsOnCore.java
index 0d8ef60..740ed91 100644
--- a/jack/tests/com/android/jack/statistics/BlockStatisticsOnCore.java
+++ b/jack/tests/com/android/jack/statistics/BlockStatisticsOnCore.java
@@ -21,11 +21,10 @@
 import com.android.jack.ir.JavaSourceIr;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.scheduling.adapter.JMethodAdaptor;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
+import com.android.jack.scheduling.adapter.JMethodAdaptor;
 import com.android.jack.transformations.parent.ParentSetterChecker;
-import com.android.jack.util.filter.SupportedMethods;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
 import com.android.sched.scheduler.SchedulableManager;
@@ -50,11 +49,11 @@
   public void computeBlockStatOnCore() throws Exception {
     Options compilerArgs = TestTools.buildCommandLineArgs(null, null,
         TestTools.getFromAndroidTree("libcore/luni/src/main/java/"));
-    compilerArgs.setFilter(new SupportedMethods());
-    JProgram program = buildProgram(compilerArgs);
-    Assert.assertNotNull(program);
+    compilerArgs.addProperty(Options.METHOD_FILTER.getName(), "supported-methods");
+    JSession session = buildSession(compilerArgs);
+    Assert.assertNotNull(session);
 
-    BlockCountMarker bcm = program.getMarker(BlockCountMarker.class);
+    BlockCountMarker bcm = session.getMarker(BlockCountMarker.class);
     Assert.assertNotNull(bcm);
     assert bcm != null; // Find Bugs will be happy
 
@@ -70,9 +69,9 @@
   }
 
   @Nonnull
-  private static JProgram buildProgram(@Nonnull Options options) throws Exception {
-    JProgram jprogram = TestTools.buildProgram(options);
-    Assert.assertNotNull(jprogram);
+  private static JSession buildSession(@Nonnull Options options) throws Exception {
+    JSession session = TestTools.buildSession(options);
+    Assert.assertNotNull(session);
 
     Scheduler scheduler = Scheduler.getScheduler();
     SchedulableManager sm = SchedulableManager.getSchedulableManager();
@@ -82,14 +81,14 @@
     sr.addTargetIncludeTagOrMarker(JavaSourceIr.class);
     sr.addInitialTagOrMarker(JavaSourceIr.class);
 
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
-    progPlan.append(ParentSetterChecker.class);
-    SubPlanBuilder<JDefinedClassOrInterface> typePlan = progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
+    planBuilder.append(ParentSetterChecker.class);
+    SubPlanBuilder<JDefinedClassOrInterface> typePlan = planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
     methodPlan.append(BlockStatistics.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
-    return (jprogram);
+    return (session);
   }
 }
diff --git a/jack/tests/com/android/jack/transformations/ast/ImplicitBlockTest.java b/jack/tests/com/android/jack/transformations/ast/ImplicitBlockTest.java
index 6693e80..3ecec25 100644
--- a/jack/tests/com/android/jack/transformations/ast/ImplicitBlockTest.java
+++ b/jack/tests/com/android/jack/transformations/ast/ImplicitBlockTest.java
@@ -18,15 +18,15 @@
 
 
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.JavaSourceIr;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JMethod;
-import com.android.jack.ir.ast.JProgram;
-import com.android.jack.scheduling.adapter.JMethodAdaptor;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
+import com.android.jack.scheduling.adapter.JMethodAdaptor;
 import com.android.jack.transformations.parent.ParentSetterChecker;
+import com.android.jack.util.filter.SignatureMethodFilter;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
 import com.android.sched.scheduler.Scheduler;
@@ -106,9 +106,11 @@
 
   private static JMethod buildMethodWithImplicitBlock(String methodSignature) throws Exception {
     Options options = TestTools.buildCommandLineArgs(FILE);
-    options.setFilter(new SignatureMethodFilter(methodSignature));
-    JProgram jprogram = TestTools.buildJAst(options);
-    Assert.assertNotNull(jprogram);
+    options.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    options.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
+    JSession session = TestTools.buildJAst(options);
+    Assert.assertNotNull(session);
 
     Scheduler scheduler = Scheduler.getScheduler();
     Request sr = scheduler.createScheduleRequest();
@@ -117,17 +119,17 @@
     sr.addTargetIncludeTagOrMarker(JavaSourceIr.class);
     sr.addInitialTagOrMarker(JavaSourceIr.class);
 
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
-    progPlan.append(ParentSetterChecker.class);
-    SubPlanBuilder<JDefinedClassOrInterface> typePlan = progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
+    planBuilder.append(ParentSetterChecker.class);
+    SubPlanBuilder<JDefinedClassOrInterface> typePlan = planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
     methodPlan.append(ImplicitBlocks.class);
     methodPlan.append(ImplicitBlocksChecker.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
     JDefinedClassOrInterface type = (JDefinedClassOrInterface)
-        jprogram.getLookup().getType(CLASS_SIGNATURE);
+        session.getLookup().getType(CLASS_SIGNATURE);
     Assert.assertNotNull(type);
 
     JMethod foundMethod = TestTools.getMethod(type, methodSignature);
diff --git a/jack/tests/com/android/jack/transformations/ast/SynchronizedTest.java b/jack/tests/com/android/jack/transformations/ast/SynchronizedTest.java
index 306e51b..75e1c89 100644
--- a/jack/tests/com/android/jack/transformations/ast/SynchronizedTest.java
+++ b/jack/tests/com/android/jack/transformations/ast/SynchronizedTest.java
@@ -19,14 +19,13 @@
 
 import com.android.jack.Jack;
 import com.android.jack.Options;
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.ast.JBlock;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JLock;
 import com.android.jack.ir.ast.JMethod;
 import com.android.jack.ir.ast.JMethodBody;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.ir.ast.JStatement;
 import com.android.jack.ir.ast.JTryStatement;
 import com.android.jack.ir.ast.JUnlock;
@@ -34,6 +33,7 @@
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
 import com.android.jack.scheduling.adapter.JMethodAdaptor;
 import com.android.jack.transformations.parent.ParentSetterChecker;
+import com.android.jack.util.filter.SignatureMethodFilter;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
 import com.android.sched.scheduler.Scheduler;
@@ -141,9 +141,11 @@
   private static JMethod buildMethodAndRunSynchronizeTransformer(String methodSignature)
       throws Exception {
     Options options = TestTools.buildCommandLineArgs(FILE);
-    options.setFilter(new SignatureMethodFilter(methodSignature));
-    JProgram jprogram = TestTools.buildJAst(options);
-    Assert.assertNotNull(jprogram);
+    options.addProperty(Options.METHOD_FILTER.getName(), "method-with-signature");
+    options.addProperty(SignatureMethodFilter.METHOD_SIGNATURE_FILTER.getName(),
+        methodSignature);
+    JSession session = TestTools.buildJAst(options);
+    Assert.assertNotNull(session);
 
     Scheduler scheduler = Scheduler.getScheduler();
     Request sr = scheduler.createScheduleRequest();
@@ -151,18 +153,18 @@
     sr.addSchedulables(scheduler.getAllSchedulable());
     sr.addInitialTagsOrMarkers(Jack.getJavaSourceInitialTagSet());
 
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
-    progPlan.append(ParentSetterChecker.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
+    planBuilder.append(ParentSetterChecker.class);
     SubPlanBuilder<JDefinedClassOrInterface> typePlan =
-        progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+        planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JMethod> methodPlan = typePlan.appendSubPlan(JMethodAdaptor.class);
     methodPlan.append(ImplicitBlocks.class);
     methodPlan.append(SynchronizeTransformer.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
 
     JDefinedClassOrInterface type = (JDefinedClassOrInterface)
-        jprogram.getLookup().getType(CLASS_SIGNATURE);
+        session.getLookup().getType(CLASS_SIGNATURE);
     Assert.assertNotNull(type);
     // FINDBUGS
     assert type != null;
diff --git a/jack/tests/com/android/jack/transformations/ast/string/DummyAction.java b/jack/tests/com/android/jack/transformations/ast/string/DummyAction.java
index 77abfa4..72962ea 100644
--- a/jack/tests/com/android/jack/transformations/ast/string/DummyAction.java
+++ b/jack/tests/com/android/jack/transformations/ast/string/DummyAction.java
@@ -18,6 +18,7 @@
 
 import com.android.jack.signature.GenericSignatureAction;
 
+import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
@@ -25,7 +26,7 @@
  *
  * It only concatenates the parsed strings.
  */
-public class DummyAction implements GenericSignatureAction {
+public class DummyAction implements GenericSignatureAction<Object> {
 
   @Nonnull
   private StringBuilder strBuf = new StringBuilder();
@@ -41,13 +42,17 @@
   }
 
   @Override
-  public void parsedTypeName(@Nonnull String name) {
+  @CheckForNull
+  public Object parsedTypeName(@Nonnull String name) {
     strBuf.append(name);
+    return null;
   }
 
   @Override
-  public void parsedInnerTypeName(@Nonnull String name) {
+  @CheckForNull
+  public Object parsedInnerTypeName(@CheckForNull Object enclosingTypeName, @Nonnull String name) {
     strBuf.append(name);
+    return null;
   }
 
   @Override
diff --git a/jack/tests/com/android/jack/transformations/ast/string/StringSplittingTest.java b/jack/tests/com/android/jack/transformations/ast/string/StringSplittingTest.java
index 134cff5..e781bac 100644
--- a/jack/tests/com/android/jack/transformations/ast/string/StringSplittingTest.java
+++ b/jack/tests/com/android/jack/transformations/ast/string/StringSplittingTest.java
@@ -32,7 +32,7 @@
   @Test
   public void testTypeStringSplitting() {
     DummyAction parserActions = new DummyAction();
-    GenericSignatureParser parser = new GenericSignatureParser(parserActions);
+    GenericSignatureParser<Object> parser = new GenericSignatureParser<Object>(parserActions);
     String signature = "LOuter.Inner;";
     parser.parseClassSignature(signature);
     Assert.assertEquals(signature, parserActions.getNewSignature());
diff --git a/jack/tests/com/android/jack/transformations/cast/UselessCastRemoverTest.java b/jack/tests/com/android/jack/transformations/cast/UselessCastRemoverTest.java
index f896038..777b1d2 100644
--- a/jack/tests/com/android/jack/transformations/cast/UselessCastRemoverTest.java
+++ b/jack/tests/com/android/jack/transformations/cast/UselessCastRemoverTest.java
@@ -17,7 +17,6 @@
 package com.android.jack.transformations.cast;
 
 
-import com.android.jack.SignatureMethodFilter;
 import com.android.jack.TestTools;
 import com.android.jack.ir.InternalCompilerException;
 import com.android.jack.ir.ast.JCastOperation;
@@ -144,8 +143,9 @@
   private static void buildMethodAndCheckUselessCastRemover(@Nonnull String classBinaryName,
       @Nonnull String methodSignature, boolean castRemoved) throws Exception {
     JMethod m =
-        TestTools.getJMethod(TestTools.getJackTestFromBinaryName(classBinaryName), "L"
-            + classBinaryName + ";", methodSignature, new SignatureMethodFilter(methodSignature));
+        TestTools.getJMethodWithSignatureFilter(
+            TestTools.getJackTestFromBinaryName(classBinaryName), "L" + classBinaryName + ";",
+            methodSignature);
     Assert.assertNotNull(m);
 
     try {
diff --git a/jack/tests/com/android/jack/util/AllTests.java b/jack/tests/com/android/jack/util/AllTests.java
index aa1b12d..3d9c445 100644
--- a/jack/tests/com/android/jack/util/AllTests.java
+++ b/jack/tests/com/android/jack/util/AllTests.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
 package com.android.jack.util;
 
 import org.junit.runner.RunWith;
diff --git a/jack/tests/com/android/sched/Main.java b/jack/tests/com/android/sched/Main.java
index 0e4efa7..72f32d3 100644
--- a/jack/tests/com/android/sched/Main.java
+++ b/jack/tests/com/android/sched/Main.java
@@ -21,7 +21,7 @@
 import com.android.jack.ir.JavaSourceIr;
 import com.android.jack.ir.ast.JDefinedClassOrInterface;
 import com.android.jack.ir.ast.JNode;
-import com.android.jack.ir.ast.JProgram;
+import com.android.jack.ir.ast.JSession;
 import com.android.jack.scheduling.adapter.JDefinedClassOrInterfaceAdaptor;
 import com.android.sched.scheduler.PlanBuilder;
 import com.android.sched.scheduler.Request;
@@ -55,25 +55,25 @@
   static void run(@Nonnull Options options)
       throws Exception {
 
-    // Build the plan, verify it and run it onto the program
+    // Build the plan, verify it and run it onto the session
     Scheduler scheduler = Scheduler.getScheduler();
     Request sr = scheduler.createScheduleRequest();
 
     sr.addSchedulables(scheduler.getAllSchedulable());
     sr.addInitialTagOrMarker(JavaSourceIr.class);
 
-    JProgram jprogram = TestTools.buildProgram(options);
-    Assert.assertNotNull(jprogram);
+    JSession session = TestTools.buildSession(options);
+    Assert.assertNotNull(session);
 
     // Currently, plan is manually built by adding RunnableSchedulable(s) and sub-plans
     // corresponding to visitors.
-    PlanBuilder<JProgram> progPlan = sr.getPlanBuilder(JProgram.class);
-    SubPlanBuilder<JDefinedClassOrInterface> typePlan = progPlan.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
+    PlanBuilder<JSession> planBuilder = sr.getPlanBuilder(JSession.class);
+    SubPlanBuilder<JDefinedClassOrInterface> typePlan = planBuilder.appendSubPlan(JDefinedClassOrInterfaceAdaptor.class);
     SubPlanBuilder<JNode> nodePlan = typePlan.appendSubPlan(JNodeAdapter.class);
     nodePlan.append(JNodeVisitor1.class);
     nodePlan.append(JNodeVisitor2.class);
 
-    progPlan.getPlan().getScheduleInstance().process(jprogram);
+    planBuilder.getPlan().getScheduleInstance().process(session);
   }
 
   @Nonnull
diff --git a/sched/.settings/findbugs-exclude.xml b/sched/.settings/findbugs-exclude.xml
index 404658b..e21c2b2 100644
--- a/sched/.settings/findbugs-exclude.xml
+++ b/sched/.settings/findbugs-exclude.xml
@@ -23,6 +23,11 @@
 </Match>
 <!-- See inlined comment in source file -->
 <Match>
+    <Class name="com.android.sched.util.log.stats.SampleImpl"/>
+    <Bug pattern="IS2_INCONSISTENT_SYNC"/>
+</Match>
+<!-- See inlined comment in source file -->
+<Match>
     <Class name="com.android.sched.util.table.AbstractTable"/>
     <Bug pattern="EI_EXPOSE_REP"/>
 </Match>
diff --git a/sched/.settings/org.eclipse.jdt.core.prefs b/sched/.settings/org.eclipse.jdt.core.prefs
index 82380d3..34af015 100644
--- a/sched/.settings/org.eclipse.jdt.core.prefs
+++ b/sched/.settings/org.eclipse.jdt.core.prefs
@@ -188,7 +188,7 @@
 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false
 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false
 org.eclipse.jdt.core.formatter.comment.format_block_comments=true
-org.eclipse.jdt.core.formatter.comment.format_header=true
+org.eclipse.jdt.core.formatter.comment.format_header=false
 org.eclipse.jdt.core.formatter.comment.format_html=true
 org.eclipse.jdt.core.formatter.comment.format_javadoc_comments=true
 org.eclipse.jdt.core.formatter.comment.format_line_comments=true
diff --git a/sched/src/com/android/sched/SchedProperties.java b/sched/src/com/android/sched/SchedProperties.java
index c9edf55..5594905 100644
--- a/sched/src/com/android/sched/SchedProperties.java
+++ b/sched/src/com/android/sched/SchedProperties.java
@@ -16,6 +16,7 @@
 
 package com.android.sched;
 
+import com.android.sched.item.onlyfor.Default;
 import com.android.sched.item.onlyfor.OnlyForType;
 import com.android.sched.util.codec.ClassSelector;
 import com.android.sched.util.config.HasKeyId;
@@ -32,10 +33,10 @@
   @Nonnull
   public static final BooleanPropertyId FAILED_STOP = BooleanPropertyId.create(
       "sched.failedstop", "Define if the SchedLib stop at the first failed")
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   public static final PropertyId<Class<? extends OnlyForType>> ONLY_FOR = PropertyId.create(
       "sched.onlyfor", "Define which items to take into account",
-      new ClassSelector<OnlyForType>(OnlyForType.class)).addDefaultValue("default");
+      new ClassSelector<OnlyForType>(OnlyForType.class)).addDefaultValue(Default.class);
 }
diff --git a/sched/src/com/android/sched/scheduler/MultiWorkersScheduleInstance.java b/sched/src/com/android/sched/scheduler/MultiWorkersScheduleInstance.java
index de04742..64da80f 100644
--- a/sched/src/com/android/sched/scheduler/MultiWorkersScheduleInstance.java
+++ b/sched/src/com/android/sched/scheduler/MultiWorkersScheduleInstance.java
@@ -65,7 +65,7 @@
       "sched.runner.thread.synchronized",
       "If scheduler manages synchronized schedulable by itself").requiredIf(
       ScheduleInstance.DEFAULT_RUNNER.getClazz().isSubClassOf(MultiWorkersScheduleInstance.class))
-      .addDefaultValue("true");
+      .addDefaultValue(Boolean.TRUE);
 
   @Nonnull
   private static final IntegerPropertyId CHECK_FREQUENCY = IntegerPropertyId.create(
diff --git a/sched/src/com/android/sched/scheduler/genetic/GeneticEventType.java b/sched/src/com/android/sched/scheduler/genetic/GeneticEventType.java
index 049b935..a8777d5 100644
--- a/sched/src/com/android/sched/scheduler/genetic/GeneticEventType.java
+++ b/sched/src/com/android/sched/scheduler/genetic/GeneticEventType.java
@@ -25,24 +25,16 @@
  * Represents a type of event whose performance is tracked
  */
 enum GeneticEventType implements EventType {
-  ENGINE("Genetic engine", "Red"),
-  ANALYZER("Genetic analizing plan", "Red"),
-  BUILDER("Genetic builder builder", "Red"),
-  RANDOM_INIT("Random generator initializer", "Red");
-  @Nonnull
-  private final String cssColor;
+  ENGINE("Genetic engine"),
+  ANALYZER("Genetic analizing plan"),
+  BUILDER("Genetic builder builder"),
+  RANDOM_INIT("Random generator initializer");
+
   @Nonnull
   private final String name;
 
-  GeneticEventType(@Nonnull String name, @Nonnull String cssColor) {
+  GeneticEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/sched/src/com/android/sched/util/Colors.java b/sched/src/com/android/sched/util/Colors.java
deleted file mode 100644
index 69c8372..0000000
--- a/sched/src/com/android/sched/util/Colors.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.sched.util;
-
-import java.awt.Color;
-import java.util.Random;
-
-import javax.annotation.Nonnull;
-
-/**
- * Utility class to manipulate Color.
- */
-public class Colors {
-  /**
-   * Return a valid string describing a color valid for Css.
-   * @param color the color
-   * @return the string describing the color
-   */
-  @Nonnull
-  public static String getCssColor(@Nonnull Color color) {
-    StringBuffer buffer = new StringBuffer(7);
-    buffer.append('#');
-    buffer.append(getHexColorComponent(color.getRed()));
-    buffer.append(getHexColorComponent(color.getGreen()));
-    buffer.append(getHexColorComponent(color.getBlue()));
-
-    return buffer.toString();
-  }
-
-  @Nonnull
-  private static String getHexColorComponent(int colorComponent) {
-    String hex = Integer.toString(colorComponent, 16);
-
-    // Make sure hex value is two digits
-    if (hex.length() == 1) {
-      hex = "0" + hex;
-    }
-
-    return hex;
-  }
-
-  /**
-   * Create a random pastel color.
-   *
-   * @return a color
-   */
-  @Nonnull
-  public static Color getRandomPastel() {
-    Random random = new Random();
-
-    final float hue = random.nextFloat();
-    final float saturation = 0.9f; // 1.0 for brilliant, 0.0 for dull
-    final float luminance = 1.0f;  // 1.0 for brighter, 0.0 for black
-
-    return Color.getHSBColor(hue, saturation, luminance);
-  }
-
-  /**
-   * Create a random pastel color based on a seed.
-   *
-   * @param seed the seed
-   * @return a color
-   */
-  @Nonnull
-  public static Color getRandomPastel(int seed) {
-    final float hue;
-    if (seed != 0) {
-      hue = 1.0F / ((((long) seed) << 32) >>> 32); // Remove the sign
-    } else {
-      hue = 1.0F;
-    }
-
-    final float saturation = 0.9f; // 1.0 for brilliant, 0.0 for dull
-    final float luminance = 1.0f;  // 1.0 for brighter, 0.0 for black
-
-    return Color.getHSBColor(hue, saturation, luminance);
-  }
-
-  private Colors() {}
-}
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/sched/src/com/android/sched/util/ConcurrentIOException.java
similarity index 66%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to sched/src/com/android/sched/util/ConcurrentIOException.java
index 0c967d9..b3ea109 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/sched/src/com/android/sched/util/ConcurrentIOException.java
@@ -14,18 +14,19 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
-
-import java.util.Collection;
+package com.android.sched.util;
 
 import javax.annotation.Nonnull;
 
 /**
- * Virtual directory.
+ * Thrown when an external change to the file system prevents continuing the current processing.
  */
-public interface VDir extends VElement {
+public class ConcurrentIOException extends UnrecoverableException {
 
-  @Nonnull
-  Collection<? extends VElement> list();
+  private static final long serialVersionUID = 1L;
+
+  public ConcurrentIOException(@Nonnull Throwable cause) {
+    super(cause);
+  }
 
 }
diff --git a/sched/src/com/android/sched/util/UnrecoverableException.java b/sched/src/com/android/sched/util/UnrecoverableException.java
new file mode 100644
index 0000000..a3f2dff
--- /dev/null
+++ b/sched/src/com/android/sched/util/UnrecoverableException.java
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.util;
+
+import javax.annotation.Nonnull;
+
+/**
+ * Thrown when a major problem occurred because of an event out of our control.
+ * Handling this error should only be reporting to the user and maybe just retry exactly the same
+ * thing as the one that has thrown.
+ */
+public abstract class UnrecoverableException extends RuntimeException {
+
+  private static final long serialVersionUID = 1L;
+
+  public UnrecoverableException(@Nonnull Throwable cause) {
+    super(cause);
+  }
+
+  @Override
+  public String getMessage() {
+    return getCause().getMessage();
+  }
+}
diff --git a/sched/src/com/android/sched/util/codec/ClassSelector.java b/sched/src/com/android/sched/util/codec/ClassSelector.java
index c8f45c5..f3f8cb9 100644
--- a/sched/src/com/android/sched/util/codec/ClassSelector.java
+++ b/sched/src/com/android/sched/util/codec/ClassSelector.java
@@ -18,6 +18,8 @@
 
 
 
+import com.google.common.base.Joiner;
+
 import com.android.sched.util.config.ConfigurationError;
 
 import javax.annotation.Nonnull;
@@ -44,8 +46,8 @@
   public void checkValue(@Nonnull CodecContext context, @Nonnull Class<? extends T> cls)
       throws CheckingException {
     if (!checkClass(cls)) {
-      throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(cls) + "'");
+      throw new CheckingException("The value must be {" + Joiner.on(',').join(getClasses())
+          + "} but is '" + cls.getCanonicalName() + "'");
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/DefaultFactorySelector.java b/sched/src/com/android/sched/util/codec/DefaultFactorySelector.java
index c357b9d..6a5c110 100644
--- a/sched/src/com/android/sched/util/codec/DefaultFactorySelector.java
+++ b/sched/src/com/android/sched/util/codec/DefaultFactorySelector.java
@@ -17,6 +17,8 @@
 package com.android.sched.util.codec;
 
 
+import com.google.common.base.Joiner;
+
 import com.android.sched.util.config.ConfigurationError;
 import com.android.sched.util.config.DefaultFactory;
 import com.android.sched.util.config.ReflectDefaultCtorFactory;
@@ -56,8 +58,9 @@
   public void checkValue(@Nonnull CodecContext context, @Nonnull DefaultFactory<T> factory)
       throws CheckingException {
     if (!checkClass(factory.getInstanciatedClass())) {
-      throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(factory) + "'");
+      throw new CheckingException("The value must be a DefaultFactory<{"
+          + Joiner.on(',').join(getClasses()) + "}> but is a DefaultFactory<"
+          + factory.getInstanciatedClass().getCanonicalName() + ">");
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/DoubleCodec.java b/sched/src/com/android/sched/util/codec/DoubleCodec.java
index 44ee717..a2be42f 100644
--- a/sched/src/com/android/sched/util/codec/DoubleCodec.java
+++ b/sched/src/com/android/sched/util/codec/DoubleCodec.java
@@ -72,7 +72,7 @@
 
     if (v < min || v > max) {
       throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(d) + "'");
+          "The value must be " + getUsage() + " but is " + d);
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/ImplementationSelector.java b/sched/src/com/android/sched/util/codec/ImplementationSelector.java
index 1f06a15..e242be7 100644
--- a/sched/src/com/android/sched/util/codec/ImplementationSelector.java
+++ b/sched/src/com/android/sched/util/codec/ImplementationSelector.java
@@ -16,6 +16,8 @@
 
 package com.android.sched.util.codec;
 
+import com.google.common.base.Joiner;
+
 import com.android.sched.util.config.ConfigurationError;
 import com.android.sched.util.config.ReflectDefaultCtorFactory;
 
@@ -56,8 +58,9 @@
   public void checkValue(@Nonnull CodecContext context, @Nonnull T data)
       throws CheckingException {
     if (!checkClass((Class<? extends T>) data.getClass())) {
-      throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(data) + "'");
+      throw new CheckingException("The value must be an instance of {"
+          + Joiner.on(',').join(getClasses()) + "} but is an instance of '"
+          + data.getClass().getCanonicalName() + "'");
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/KeyValueCodec.java b/sched/src/com/android/sched/util/codec/KeyValueCodec.java
index ec9db66..4f16b47 100644
--- a/sched/src/com/android/sched/util/codec/KeyValueCodec.java
+++ b/sched/src/com/android/sched/util/codec/KeyValueCodec.java
@@ -20,6 +20,8 @@
 
 import java.util.Arrays;
 import java.util.Comparator;
+import java.util.HashSet;
+import java.util.Set;
 
 import javax.annotation.Nonnull;
 
@@ -109,8 +111,28 @@
       }
     }
 
-    throw new CheckingException(
-        "The value must be " + getUsage() + " but is '" + formatValue(value) + "'");
+    Set<T> set = new HashSet<T>();
+    for (Entry<T> entry : entries) {
+      set.add(entry.value);
+    }
+
+    StringBuilder sb = new StringBuilder();
+    boolean first = true;
+    for (T data : set) {
+      if (first) {
+        first = false;
+      } else {
+        sb.append(", ");
+      }
+
+      sb.append(data);
+      sb.append(" (");
+      sb.append(data.getClass().getCanonicalName());
+      sb.append(')');
+    }
+
+    throw new CheckingException("The value must be {" + sb.toString() + "} but is '" + value + " ("
+        + value.getClass().getCanonicalName() + ")'");
   }
 
   @Override
diff --git a/sched/src/com/android/sched/util/codec/LongCodec.java b/sched/src/com/android/sched/util/codec/LongCodec.java
index 4c4153c..cf9b8da 100644
--- a/sched/src/com/android/sched/util/codec/LongCodec.java
+++ b/sched/src/com/android/sched/util/codec/LongCodec.java
@@ -76,7 +76,7 @@
 
     if (v < min || v > max) {
       throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(l) + "'");
+          "The value must be " + getUsage() + " but is " + l);
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/ReflectFactorySelector.java b/sched/src/com/android/sched/util/codec/ReflectFactorySelector.java
index 43819f7..3ea1073 100644
--- a/sched/src/com/android/sched/util/codec/ReflectFactorySelector.java
+++ b/sched/src/com/android/sched/util/codec/ReflectFactorySelector.java
@@ -16,6 +16,8 @@
 
 package com.android.sched.util.codec;
 
+import com.google.common.base.Joiner;
+
 import com.android.sched.util.config.ConfigurationError;
 import com.android.sched.util.config.ReflectFactory;
 
@@ -78,8 +80,9 @@
   public void checkValue(@Nonnull CodecContext context, @Nonnull ReflectFactory<T> factory)
       throws CheckingException {
     if (!checkClass(factory.getInstanciatedClass())) {
-      throw new CheckingException(
-          "The value must be " + getUsage() + " but is '" + formatValue(factory) + "'");
+      throw new CheckingException("The value must be a ReflectFactory<{"
+          + Joiner.on(',').join(getClasses()) + "}> but is a ReflectFactory<"
+          + factory.getInstanciatedClass().getCanonicalName() + ">");
     }
   }
 
diff --git a/sched/src/com/android/sched/util/codec/Selector.java b/sched/src/com/android/sched/util/codec/Selector.java
index 799f106..3e4d90e 100644
--- a/sched/src/com/android/sched/util/codec/Selector.java
+++ b/sched/src/com/android/sched/util/codec/Selector.java
@@ -27,6 +27,7 @@
 import java.util.Collections;
 import java.util.Comparator;
 import java.util.HashMap;
+import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.Map.Entry;
@@ -85,6 +86,7 @@
   public String getName(@Nonnull Class<? extends T> type) {
     ensureScan();
     assert propertyValues != null;
+
     for (Entry<String, Class<? extends T>> entry : propertyValues.entrySet()) {
       if (entry.getValue() == type) {
         return entry.getKey();
@@ -127,6 +129,17 @@
     return list;
   }
 
+  @Nonnull
+  public Set<Class<? extends T>> getClasses() {
+    ensureScan();
+    assert propertyValues != null;
+
+    Set<Class<? extends T>> set = new HashSet<Class<? extends T>>();
+    set.addAll(propertyValues.values());
+
+    return set;
+  }
+
   private synchronized void ensureScan() {
     if (propertyValues == null) {
       propertyValues = new HashMap<String, Class<? extends T>>();
diff --git a/sched/src/com/android/sched/util/config/AsapConfigBuilder.java b/sched/src/com/android/sched/util/config/AsapConfigBuilder.java
index 0b8bdf2..597d44e 100644
--- a/sched/src/com/android/sched/util/config/AsapConfigBuilder.java
+++ b/sched/src/com/android/sched/util/config/AsapConfigBuilder.java
@@ -38,6 +38,7 @@
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.HashMap;
+import java.util.List;
 import java.util.Map;
 import java.util.Map.Entry;
 import java.util.Set;
@@ -69,11 +70,11 @@
       new HashMap<KeyId<?, ?>, FieldLocation>();
 
   @Nonnull
-  private final Map<PropertyId<?>, String> stringValuesById =
-      new HashMap<PropertyId<?>, String>();
+  private final Map<PropertyId<?>, PropertyId<?>.Value> valuesById =
+      new HashMap<PropertyId<?>, PropertyId<?>.Value>();
 
   @Nonnull
-  private final Map<ObjectId<?>, Object> instanceValuesById =
+  private final Map<ObjectId<?>, Object> instances =
       new HashMap<ObjectId<?>, Object>();
 
   @Nonnull
@@ -182,13 +183,7 @@
   }
 
   @Nonnull
-  public AsapConfigBuilder set(@Nonnull String name, @Nonnull String value)
-      throws UnknownPropertyNameException, PropertyIdException {
-    return set(name, value, defaultLocations.peek());
-  }
-
-  @Nonnull
-  public AsapConfigBuilder set(
+  public AsapConfigBuilder setString(
       @Nonnull String name, @Nonnull String value, @Nonnull Location location)
       throws UnknownPropertyNameException, PropertyIdException {
     KeyId<?, ?> keyId = keyIdsByName.get(name);
@@ -197,7 +192,7 @@
     }
 
     try {
-      set((PropertyId<?>) keyId, value, location);
+      setString((PropertyId<?>) keyId, value, location);
     } catch (UnknownPropertyIdException e) {
       throw new AssertionError();
     }
@@ -206,13 +201,36 @@
   }
 
   @Nonnull
-  public AsapConfigBuilder set(@Nonnull PropertyId<?> propertyId, @Nonnull String value)
-      throws PropertyIdException {
-    return set(propertyId, value, defaultLocations.peek());
+  public <T> AsapConfigBuilder set(
+      @Nonnull String name, @Nonnull T value, @Nonnull Location location)
+      throws UnknownPropertyNameException, PropertyIdException {
+    KeyId<?, ?> keyId = keyIdsByName.get(name);
+    if (keyId == null || !(keyId instanceof PropertyId)) {
+      throw new UnknownPropertyNameException(name);
+    }
+
+    @SuppressWarnings("unchecked")
+    PropertyId<T> propertyId = (PropertyId<T>) keyId;
+
+    if (context.isDebug()) {
+      try {
+        propertyId.getCodec().checkValue(context, value);
+      } catch (Exception e) {
+        throw new ConfigurationError("Property '" + name + "': " + e.getMessage());
+      }
+    }
+
+    try {
+      set(propertyId, value, location);
+    } catch (UnknownPropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
   }
 
   @Nonnull
-  public AsapConfigBuilder set(
+  public AsapConfigBuilder setString(
       @Nonnull PropertyId<?> propertyId, @Nonnull String value, @Nonnull Location location)
       throws PropertyIdException {
     if (!keyIdsByName.values().contains(propertyId)) {
@@ -227,21 +245,39 @@
       }
     }
 
-    stringValuesById.put(propertyId, value);
+    valuesById.put(propertyId, propertyId.new Value(value));
+    locationsByKeyId.put(propertyId, location);
+
+    return this;
+  }
+
+
+  @Nonnull
+  public <T> AsapConfigBuilder set(
+      @Nonnull PropertyId<T> propertyId, @Nonnull T value, @Nonnull Location location)
+      throws PropertyIdException {
+    if (!keyIdsByName.values().contains(propertyId)) {
+      throw new UnknownPropertyIdException(propertyId);
+    }
+
+    if (context.isDebug()) {
+      try {
+        propertyId.getCodec().checkValue(context, value);
+      } catch (Exception e) {
+        throw new ConfigurationError("Property '" + propertyId.getName() + "': " + e.getMessage());
+      }
+    }
+
+    valuesById.put(propertyId, propertyId.new Value(value));
     locationsByKeyId.put(propertyId, location);
 
     return this;
   }
 
   @Nonnull
-  public <T> AsapConfigBuilder set(@Nonnull ObjectId<T> objectId, @Nonnull T value) {
-    return set(objectId, value, defaultLocations.peek());
-  }
-
-  @Nonnull
   public <T> AsapConfigBuilder set(
       @Nonnull ObjectId<T> objectId, @Nonnull T value, @Nonnull Location location) {
-    instanceValuesById.put(objectId, value);
+    instances.put(objectId, value);
     locationsByKeyId.put(objectId, location);
 
     return this;
@@ -276,7 +312,7 @@
    * @throws ConfigurationException
    */
   @Nonnull
-  public Config build() throws ConfigurationException {
+  public <X> Config build() throws ConfigurationException {
     ChainedExceptionBuilder<ConfigurationException> exceptions =
         new ChainedExceptionBuilder<ConfigurationException>();
 
@@ -286,12 +322,14 @@
       logger.setLevel(Level.INFO);
     }
 
-    @Nonnull Map<PropertyId<?>, String> values = new HashMap<PropertyId<?>, String>();
+    @Nonnull
+    Map<PropertyId<?>, PropertyId<?>.Value> values =
+        new HashMap<PropertyId<?>, PropertyId<?>.Value>();
     processValues(values);
     processDefaultValues(values);
 
     ConfigChecker checker =
-        new ConfigChecker(context, values, instanceValuesById, locationsByKeyId);
+        new ConfigChecker(context, values, instances, locationsByKeyId);
 
     for (KeyId<?, ?> keyId : keyIdsByName.values()) {
       boolean needChecks = false;
@@ -343,15 +381,15 @@
 
     if (context.isDebug()) {
       return new ConfigDebug(
-          context, checker.getStrings(), checker.getInstances(), checker.getDropCauses());
+          context, checker.getValues(), checker.getInstances(), checker.getDropCauses());
     } else {
-      return new ConfigImpl(context, checker.getStrings(), checker.getInstances());
+      return new ConfigImpl(context, checker.getValues(), checker.getInstances());
     }
   }
 
   @Nonnull
   public Collection<PropertyId<?>> getPropertyIds() {
-    ArrayList<PropertyId<?>> result = new ArrayList<PropertyId<?>>(keyIdsByName.size());
+    List<PropertyId<?>> result = new ArrayList<PropertyId<?>>(keyIdsByName.size());
 
     for (KeyId<?, ?> keyId : keyIdsByName.values()) {
       if (keyId.isPublic() && keyId instanceof PropertyId<?>) {
@@ -363,15 +401,21 @@
   }
 
   @CheckForNull
-  public String getDefaultValue(@Nonnull PropertyId<?> propertyId) {
-    return propertyId.getDefaultValue(context);
+  public <T> String getDefaultValue(@Nonnull PropertyId<T> propertyId) {
+    PropertyId<T>.Value value = propertyId.getDefaultValue(context);
+
+    if (value != null) {
+      return value.getString();
+    } else {
+      return null;
+    }
   }
 
-  private void processValues(@Nonnull Map<PropertyId<?>, String> values) {
-    values.putAll(stringValuesById);
+  private void processValues(@Nonnull Map<PropertyId<?>, PropertyId<?>.Value> values) {
+    values.putAll(valuesById);
   }
 
-  private void processDefaultValues(@Nonnull Map<PropertyId<?>, String> values) {
+  private void processDefaultValues(@Nonnull Map<PropertyId<?>, PropertyId<?>.Value> values) {
     for (KeyId<?, ?> keyId : keyIdsByName.values()) {
       if (keyId instanceof PropertyId) {
         PropertyId<?> propertyId = (PropertyId<?>) keyId;
@@ -427,7 +471,7 @@
 
               try {
                 assert propertyId != null;
-                set(propertyId, value, new EnvironmentLocation(envKey));
+                setString(propertyId, value, new EnvironmentLocation(envKey));
               } catch (ConfigurationException e) {
                 exceptions.appendException(e);
               }
@@ -450,6 +494,10 @@
     return this;
   }
 
+  //
+  // Default location
+  //
+
   public void pushDefaultLocation(@Nonnull Location location) {
     defaultLocations.push(location);
   }
@@ -458,4 +506,221 @@
     assert defaultLocations.size() > 1;
     defaultLocations.pop();
   }
+
+  @Nonnull
+  public <T> AsapConfigBuilder set(@Nonnull ObjectId<T> objectId, @Nonnull T value) {
+    return set(objectId, value, defaultLocations.peek());
+  }
+
+  @Nonnull
+  public <T> AsapConfigBuilder set(@Nonnull String name, @Nonnull T value)
+      throws UnknownPropertyNameException, PropertyIdException {
+    return set(name, value, defaultLocations.peek());
+  }
+
+  @Nonnull
+  public <T> AsapConfigBuilder set(@Nonnull PropertyId<T> propertyId, @Nonnull T value)
+      throws PropertyIdException {
+    return set(propertyId, value, defaultLocations.peek());
+  }
+
+  @Nonnull
+  public AsapConfigBuilder setString(@Nonnull PropertyId<?> propertyId, @Nonnull String value)
+      throws PropertyIdException {
+    return setString(propertyId, value, defaultLocations.peek());
+  }
+
+  @Nonnull
+  public AsapConfigBuilder setString(@Nonnull String name, @Nonnull String value)
+      throws UnknownPropertyNameException, PropertyIdException {
+    return setString(name, value, defaultLocations.peek());
+  }
+
+  //
+  // Commodity helper
+  //
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Boolean> propertyId, boolean value) {
+    try {
+      set(propertyId, Boolean.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Boolean> propertyId, boolean value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Boolean.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Byte> propertyId, byte value) {
+    try {
+      set(propertyId, Byte.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Byte> propertyId, byte value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Byte.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Short> propertyId, short value) {
+    try {
+      set(propertyId, Short.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Short> propertyId, short value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Short.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Character> propertyId, char value) {
+    try {
+      set(propertyId, Character.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Character> propertyId, char value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Character.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Integer> propertyId, int value) {
+    try {
+      set(propertyId, Integer.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Integer> propertyId, int value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Integer.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Long> propertyId, long value) {
+    try {
+      set(propertyId, Long.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Long> propertyId, long value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Long.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Float> propertyId, float value) {
+    try {
+      set(propertyId, Float.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Float> propertyId, float value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Float.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Double> propertyId, double value) {
+    try {
+      set(propertyId, Double.valueOf(value));
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public AsapConfigBuilder set(@Nonnull PropertyId<Double> propertyId, double value,
+      @Nonnull Location location) {
+    try {
+      set(propertyId, Double.valueOf(value), location);
+    } catch (PropertyIdException e) {
+      throw new AssertionError();
+    }
+
+    return this;
+  }
 }
diff --git a/sched/src/com/android/sched/util/config/Config.java b/sched/src/com/android/sched/util/config/Config.java
index 40faa5c..2bbf884 100644
--- a/sched/src/com/android/sched/util/config/Config.java
+++ b/sched/src/com/android/sched/util/config/Config.java
@@ -17,18 +17,22 @@
 package com.android.sched.util.config;
 
 import com.android.sched.util.config.id.KeyId;
+import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.PropertyId;
 
 import java.util.Collection;
 
 import javax.annotation.Nonnull;
 
-
 /**
- * The class that deals with configuration properties in 'get' mode.
+ * The interface that deals with configuration properties in 'get' mode.
  */
 public interface Config {
   @Nonnull
+  public <T> T get(@Nonnull PropertyId<T> propertyId);
+  @Nonnull
+  public <T> T get(@Nonnull ObjectId<T> objectId);
+  @Nonnull
   public <T, S> T get(@Nonnull KeyId<T, S> keyId);
   @Nonnull
   public <T> String getAsString(@Nonnull PropertyId<T> propertyId);
diff --git a/sched/src/com/android/sched/util/config/ConfigChecker.java b/sched/src/com/android/sched/util/config/ConfigChecker.java
index 4f151c8..781d77a 100644
--- a/sched/src/com/android/sched/util/config/ConfigChecker.java
+++ b/sched/src/com/android/sched/util/config/ConfigChecker.java
@@ -18,10 +18,10 @@
 
 import com.android.sched.util.codec.CodecContext;
 import com.android.sched.util.codec.ParsingException;
-import com.android.sched.util.codec.StringCodec;
 import com.android.sched.util.config.id.KeyId;
 import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.PropertyId;
+import com.android.sched.util.config.id.PropertyId.Value;
 
 import java.util.HashMap;
 import java.util.Map;
@@ -35,14 +35,15 @@
   @Nonnull
   private final CodecContext context;
   @Nonnull
-  private final Map<PropertyId<?>, String> stringValuesById = new HashMap<PropertyId<?>, String>();
+  private final Map<PropertyId<?>, PropertyId<?>.Value> values =
+      new HashMap<PropertyId<?>, PropertyId<?>.Value>();
   @Nonnull
-  private final Map<KeyId<?, ?>, Object> instanceValuesById = new HashMap<KeyId<?, ?>, Object>();
+  private final Map<KeyId<?, ?>, Object> instances = new HashMap<KeyId<?, ?>, Object>();
   @Nonnull
-  private final Map<KeyId<?, ?>, Location> locationsById =
+  private final Map<KeyId<?, ?>, Location> locations =
       new HashMap<KeyId<?, ?>, Location>();
   @Nonnull
-  private final Map<KeyId<?, ?>, String> droppedById = new HashMap<KeyId<?, ?>, String>();
+  private final Map<KeyId<?, ?>, String> dropped = new HashMap<KeyId<?, ?>, String>();
 
   /**
    * @param context Context for parsers
@@ -50,57 +51,50 @@
    * @param instanceValues All the property values as objects.
    */
   ConfigChecker(@Nonnull CodecContext context,
-      @Nonnull Map<PropertyId<?>, String> stringValues,
+      @Nonnull Map<PropertyId<?>, PropertyId<?>.Value> stringValues,
       @Nonnull Map<ObjectId<?>, Object> instanceValues,
       @Nonnull Map<KeyId<?, ?>, Location> locationsById) {
     this.context = context;
-    this.stringValuesById.putAll(stringValues);
-    this.instanceValuesById.putAll(instanceValues);
-    this.locationsById.putAll(locationsById);
+    this.values.putAll(stringValues);
+    this.instances.putAll(instanceValues);
+    this.locations.putAll(locationsById);
   }
 
   @Nonnull
-  public synchronized <T> T parse(@Nonnull PropertyId<T> propertyId) throws PropertyIdException
-       {
-    @SuppressWarnings("unchecked")
-    T instance = (T) instanceValuesById.get(propertyId);
+  public synchronized <T> T parse(@Nonnull PropertyId<T> propertyId) throws PropertyIdException {
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    PropertyId<T>.Value value = (PropertyId.Value) values.get(propertyId);
 
-    if (instance == null) {
-      String value = getRawValue(propertyId);
-      try {
-        StringCodec<T> parser = propertyId.getCodec();
-
-        instance = parser.checkString(context, value);
-        if (instance == null) {
-          instance = parser.parseString(context, value);
-        }
-
-        instanceValuesById.put(propertyId, instance);
-        stringValuesById.remove(propertyId);
-      } catch (ParsingException e) {
-        throw new PropertyIdException(propertyId, getLocation(propertyId), e);
-      }
+    if (value == null) {
+      throw new MissingPropertyException(propertyId);
     }
 
-    return instance;
+    try {
+      value.check(context);
+      return value.getObject(context);
+    } catch (ParsingException e) {
+      throw new PropertyIdException(propertyId, getLocation(propertyId), e);
+    }
   }
 
   public synchronized <T, S> void check(@Nonnull KeyId<T, S> keyId) throws PropertyIdException {
-    if (instanceValuesById.get(keyId) == null) {
+    if (instances.get(keyId) == null) {
       if (keyId instanceof PropertyId) {
         @SuppressWarnings("unchecked")
         PropertyId<T> propertyId = (PropertyId<T>) keyId;
-        String value = getRawValue(propertyId);
+
+        @SuppressWarnings({"unchecked", "rawtypes"})
+        PropertyId<T>.Value value = (PropertyId.Value) values.get(propertyId);
+
+        if (value == null) {
+          throw new MissingPropertyException(propertyId);
+        }
+
         try {
-          T instance = propertyId.getCodec().checkString(context, value);
-          if (instance != null) {
-            instanceValuesById.put(propertyId, instance);
-            stringValuesById.remove(keyId);
-          }
+          value.check(context);
         } catch (ParsingException e) {
           throw new PropertyIdException(propertyId, getLocation(propertyId), e);
         }
-
       } else {
         assert keyId instanceof ObjectId;
 
@@ -114,41 +108,42 @@
   @Nonnull
   public <T> String getRawValue(@Nonnull PropertyId<T> propertyId)
       throws MissingPropertyException {
-    String value = stringValuesById.get(propertyId);
+    @SuppressWarnings({"rawtypes", "unchecked"})
+    PropertyId<T>.Value value = (Value) values.get(propertyId);
 
     if (value == null) {
       throw new MissingPropertyException(propertyId);
     }
 
-    return value;
+    return value.getString();
   }
 
   @Nonnull
   public Map<KeyId<?, ?>, Object> getInstances() {
-    return instanceValuesById;
+    return instances;
   }
 
   @Nonnull
-  public Map<PropertyId<?>, String> getStrings() {
-    return stringValuesById;
+  public Map<PropertyId<?>, PropertyId<?>.Value> getValues() {
+    return values;
   }
 
   @Nonnull
   public Map<KeyId<?, ?>, String> getDropCauses() {
-    return droppedById;
+    return dropped;
   }
 
   @Nonnull
   public Location getLocation(@Nonnull KeyId<?, ?> keyId) {
-    assert locationsById.get(keyId) != null;
+    assert locations.get(keyId) != null;
 
-    return locationsById.get(keyId);
+    return locations.get(keyId);
   }
 
   public void remove(@Nonnull KeyId<?, ?> keyId, @Nonnull String cause) {
-    stringValuesById.remove(keyId);
-    instanceValuesById.remove(keyId);
-    locationsById.remove(keyId);
-    droppedById.put(keyId, cause);
+    values.remove(keyId);
+    instances.remove(keyId);
+    locations.remove(keyId);
+    dropped.put(keyId, cause);
   }
 }
diff --git a/sched/src/com/android/sched/util/config/ConfigDebug.java b/sched/src/com/android/sched/util/config/ConfigDebug.java
index f7b5a94..db926d1 100644
--- a/sched/src/com/android/sched/util/config/ConfigDebug.java
+++ b/sched/src/com/android/sched/util/config/ConfigDebug.java
@@ -18,6 +18,7 @@
 
 import com.android.sched.util.codec.CodecContext;
 import com.android.sched.util.config.id.KeyId;
+import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.PropertyId;
 import com.android.sched.util.log.LoggerFactory;
 
@@ -47,16 +48,29 @@
       }
   };
 
-  ConfigDebug(@Nonnull CodecContext context, @Nonnull Map<PropertyId<?>, String> stringValues,
-      @Nonnull Map<KeyId<?, ?>, Object> instanceValues,
+  ConfigDebug(@Nonnull CodecContext context,
+      @Nonnull Map<PropertyId<?>, PropertyId<?>.Value> values,
+      @Nonnull Map<KeyId<?, ?>, Object> instances,
       @Nonnull Map<KeyId<?, ?>, String> dropCauses) {
-    super(context, stringValues, instanceValues);
+    super(context, values, instances);
 
     this.dropCauses = new HashMap<KeyId<?, ?>, String>(dropCauses);
   }
 
   @Override
   @Nonnull
+  public synchronized <T> T get(@Nonnull PropertyId<T> propertyId) {
+    return get((KeyId<T, ?>) propertyId);
+  }
+
+  @Override
+  @Nonnull
+  public synchronized <T> T get(@Nonnull ObjectId<T> objectId) {
+    return get((KeyId<T, ?>) objectId);
+  }
+
+  @Override
+  @Nonnull
   public <T, S> T get(@Nonnull KeyId<T, S> keyId) {
     Stack<KeyId<?, ?>> localKeyIds = keyIds.get();
 
diff --git a/sched/src/com/android/sched/util/config/ConfigImpl.java b/sched/src/com/android/sched/util/config/ConfigImpl.java
index 00a1bce..d3d6ee9 100644
--- a/sched/src/com/android/sched/util/config/ConfigImpl.java
+++ b/sched/src/com/android/sched/util/config/ConfigImpl.java
@@ -26,71 +26,110 @@
 import java.util.HashMap;
 import java.util.Map;
 
+import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
  * Implementation of a fully built {@code Config}.
  */
-class ConfigImpl implements Config {
+class ConfigImpl implements Config, InternalConfig {
   @Nonnull
   private final CodecContext context;
   @Nonnull
-  private final Map<PropertyId<?>, String> stringValuesById = new HashMap<PropertyId<?>, String>();
+  private final Map<PropertyId<?>, PropertyId<?>.Value> valuesById =
+      new HashMap<PropertyId<?>, PropertyId<?>.Value>();
   @Nonnull
-  private final Map<KeyId<?, ?>, Object> instanceValuesById = new HashMap<KeyId<?, ?>, Object>();
+  private final Map<KeyId<?, ?>, Object> instancesById = new HashMap<KeyId<?, ?>, Object>();
 
   /**
    * @param context Context for parsers
-   * @param stringValues All the property values as {@code String} objects.
-   * @param instanceValues All the property values as objects.
+   * @param values All the property values as {@code String} objects.
+   * @param instances All the property values as objects.
    */
-  ConfigImpl(@Nonnull CodecContext context, @Nonnull Map<PropertyId<?>, String> stringValues,
-      @Nonnull Map<KeyId<?, ?>, Object> instanceValues) {
+  ConfigImpl(@Nonnull CodecContext context, @Nonnull Map<PropertyId<?>, PropertyId<?>.Value> values,
+      @Nonnull Map<KeyId<?, ?>, Object> instances) {
     this.context = context;
-    this.stringValuesById.putAll(stringValues);
-    this.instanceValuesById.putAll(instanceValues);
+    this.valuesById.putAll(values);
+    this.instancesById.putAll(instances);
   }
 
   @Override
   @Nonnull
-  public synchronized <T, S> T get(@Nonnull KeyId<T, S> keyId) {
+  public <T> T get(@Nonnull PropertyId<T> propertyId) {
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    PropertyId<T>.Value value = (PropertyId.Value) valuesById.get(propertyId);
+
+    if (value == null) {
+      throw new ConfigurationError("Property '" + propertyId.getName()
+          + "' is unknown (see annotation @" + HasKeyId.class.getSimpleName()
+          + " or requiredIf expression)");
+    }
+
+    return value.getObject(context);
+  }
+
+  @Override
+  @CheckForNull
+  public <T> T getObjectIfAny(@Nonnull PropertyId<T> propertyId) {
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    PropertyId<T>.Value value = (PropertyId.Value) valuesById.get(propertyId);
+
+    if (value == null) {
+      throw new ConfigurationError("Property '" + propertyId.getName()
+          + "' is unknown (see annotation @" + HasKeyId.class.getSimpleName()
+          + " or requiredIf expression)");
+    }
+
+    return value.getObjectIfAny();
+  }
+
+  @Override
+  @Nonnull
+  public <T> String getAsString(@Nonnull PropertyId<T> propertyId) {
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    PropertyId<T>.Value value = (PropertyId.Value) valuesById.get(propertyId);
+
+    if (value == null) {
+      throw new ConfigurationError("Property '" + propertyId.getName()
+          + "' is unknown (see annotation @" + HasKeyId.class.getSimpleName()
+          + " or requiredIf expression)");
+    }
+
+    return value.getString();
+  }
+
+  @Override
+  @Nonnull
+  public synchronized <T> T get(@Nonnull ObjectId<T> objectId) {
     @SuppressWarnings("unchecked")
-    T instance = (T) instanceValuesById.get(keyId);
+    T instance = (T) instancesById.get(objectId);
 
     if (instance == null) {
-      if (keyId instanceof PropertyId) {
-        @SuppressWarnings("unchecked")
-        PropertyId<T> propertyId = (PropertyId<T>) keyId;
-
-        String value = stringValuesById.get(propertyId);
-        if (value == null) {
-          throw new ConfigurationError("Property '" + propertyId.getName()
-              + "' is unknown (see annotation @" + HasKeyId.class.getSimpleName()
-              + " or requiredIf expression)");
-        }
-
-        instance = propertyId.getCodec().parseString(context, value);
-        instanceValuesById.put(propertyId, instance);
-        stringValuesById.remove(propertyId);
-      } else {
-        @SuppressWarnings("unchecked")
-        ObjectId<T> objectId = (ObjectId<T>) keyId;
-
-        instance = objectId.createObject();
-        instanceValuesById.put(objectId, instance);
-      }
+      instance = objectId.createObject();
+      instancesById.put(objectId, instance);
     }
 
     return instance;
   }
 
+  @SuppressWarnings("unchecked")
+  @Override
+  @Nonnull
+  public <T, S> T get(@Nonnull KeyId<T, S> keyId) {
+    if (keyId instanceof PropertyId) {
+      return get((PropertyId<T>) keyId);
+    } else {
+      return get((ObjectId<T>) keyId);
+    }
+  }
+
   @Override
   @Nonnull
   public Collection<PropertyId<?>> getPropertyIds() {
     ArrayList<PropertyId<?>> result =
-        new ArrayList<PropertyId<?>>(instanceValuesById.size() + stringValuesById.size());
+        new ArrayList<PropertyId<?>>(instancesById.size() + valuesById.size());
 
-    for (KeyId<?, ?> keyId : stringValuesById.keySet()) {
+    for (KeyId<?, ?> keyId : valuesById.keySet()) {
       if (keyId.isPublic()) {
         if (keyId instanceof PropertyId) {
           result.add((PropertyId<?>) keyId);
@@ -98,7 +137,7 @@
       }
     }
 
-    for (KeyId<?, ?> keyId : instanceValuesById.keySet()) {
+    for (KeyId<?, ?> keyId : instancesById.keySet()) {
       if (keyId.isPublic()) {
         if (keyId instanceof PropertyId) {
           result.add((PropertyId<?>) keyId);
@@ -108,25 +147,4 @@
 
     return result;
   }
-
-  @Override
-  @Nonnull
-  public <T> String getAsString(@Nonnull PropertyId<T> propertyId) {
-    String result;
-
-    result = stringValuesById.get(propertyId);
-    if (result == null) {
-      @SuppressWarnings("unchecked")
-      T instance = (T) instanceValuesById.get(propertyId);
-      if (instance == null) {
-        throw new ConfigurationError("Property '" + propertyId.getName()
-            + "' is unknown (see annotation @" + HasKeyId.class.getSimpleName()
-            + " or requiredIf expression)");
-      }
-
-      result = propertyId.getCodec().formatValue(instance);
-    }
-
-    return result;
-  }
 }
diff --git a/sched/src/com/android/sched/util/config/ConfigurationError.java b/sched/src/com/android/sched/util/config/ConfigurationError.java
index 9ca2b2b..fef0795 100644
--- a/sched/src/com/android/sched/util/config/ConfigurationError.java
+++ b/sched/src/com/android/sched/util/config/ConfigurationError.java
@@ -16,6 +16,7 @@
 
 package com.android.sched.util.config;
 
+import com.android.sched.util.codec.CheckingException;
 import com.android.sched.util.codec.ParsingException;
 
 import javax.annotation.Nonnull;
@@ -43,4 +44,8 @@
   public ConfigurationError(@Nonnull ParsingException e) {
     super(e.getMessage(), e);
   }
+
+  public ConfigurationError(@Nonnull CheckingException e) {
+    super(e.getMessage(), e);
+  }
 }
diff --git a/sched/src/com/android/sched/util/config/GatherConfigBuilder.java b/sched/src/com/android/sched/util/config/GatherConfigBuilder.java
index b923541..133ef88 100644
--- a/sched/src/com/android/sched/util/config/GatherConfigBuilder.java
+++ b/sched/src/com/android/sched/util/config/GatherConfigBuilder.java
@@ -54,7 +54,21 @@
   }
 
   @Nonnull
-  public GatherConfigBuilder set(@Nonnull String name, @Nonnull String value) {
+  public GatherConfigBuilder setString(@Nonnull String name, @Nonnull String value) {
+    try {
+      builder.setString(name, value);
+    } catch (PropertyIdException e) {
+      exceptions.appendException(e);
+    } catch (UnknownPropertyNameException e) {
+      exceptions.appendException(e);
+    }
+
+    return this;
+  }
+
+
+  @Nonnull
+  public <T> GatherConfigBuilder set(@Nonnull String name, @Nonnull T value) {
     try {
       builder.set(name, value);
     } catch (PropertyIdException e) {
@@ -67,9 +81,24 @@
   }
 
   @Nonnull
-  public GatherConfigBuilder set(
+  public GatherConfigBuilder setString(
       @Nonnull String name, @Nonnull String value, @Nonnull Location location) {
     try {
+      builder.setString(name, value, location);
+    } catch (UnknownPropertyNameException e) {
+      exceptions.appendException(e);
+    } catch (PropertyIdException e) {
+      exceptions.appendException(e);
+    }
+
+    return this;
+  }
+
+
+  @Nonnull
+  public <T> GatherConfigBuilder set(
+      @Nonnull String name, @Nonnull T value, @Nonnull Location location) {
+    try {
       builder.set(name, value, location);
     } catch (UnknownPropertyNameException e) {
       exceptions.appendException(e);
@@ -81,7 +110,20 @@
   }
 
   @Nonnull
-  public GatherConfigBuilder set(@Nonnull PropertyId<?> propertyId, @Nonnull String value) {
+  public GatherConfigBuilder setString(@Nonnull PropertyId<?> propertyId, @Nonnull String value) {
+    try {
+      builder.setString(propertyId, value);
+    } catch (UnknownPropertyIdException e) {
+      exceptions.appendException(e);
+    } catch (PropertyIdException e) {
+      exceptions.appendException(e);
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public <T> GatherConfigBuilder set(@Nonnull PropertyId<T> propertyId, @Nonnull T value) {
     try {
       builder.set(propertyId, value);
     } catch (UnknownPropertyIdException e) {
@@ -94,9 +136,23 @@
   }
 
   @Nonnull
-  public GatherConfigBuilder set(
+  public GatherConfigBuilder setString(
       @Nonnull PropertyId<?> propertyId, @Nonnull String value, @Nonnull Location location) {
     try {
+      builder.setString(propertyId, value, location);
+    } catch (UnknownPropertyIdException e) {
+      exceptions.appendException(e);
+    } catch (PropertyIdException e) {
+      exceptions.appendException(e);
+    }
+
+    return this;
+  }
+
+  @Nonnull
+  public <T> GatherConfigBuilder set(
+      @Nonnull PropertyId<T> propertyId, @Nonnull T value, @Nonnull Location location) {
+    try {
       builder.set(propertyId, value, location);
     } catch (UnknownPropertyIdException e) {
       exceptions.appendException(e);
@@ -151,12 +207,18 @@
    */
   @Nonnull
   public Config build() throws ConfigurationException {
+    Config config;
+
     try {
-      return builder.build();
+      config = builder.build();
     } catch (ConfigurationException e) {
       exceptions.appendException(e);
       throw exceptions.getException();
     }
+
+    exceptions.throwIfNecessary();
+
+    return config;
   }
 
   @Nonnull
@@ -180,6 +242,10 @@
     return this;
   }
 
+  //
+  // Default location
+  //
+
   public void pushDefaultLocation(@Nonnull Location location) {
     builder.pushDefaultLocation(location);
   }
@@ -187,4 +253,128 @@
   public void popDefaultLocation() {
     builder.popDefaultLocation();
   }
+
+  //
+  // Commodity helper
+  //
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Boolean> propertyId, boolean value) {
+    set(propertyId, Boolean.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Boolean> propertyId, boolean value,
+      @Nonnull Location location) {
+    set(propertyId, Boolean.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Byte> propertyId, byte value) {
+    set(propertyId, Byte.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Byte> propertyId, byte value,
+      @Nonnull Location location) {
+    set(propertyId, Byte.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Short> propertyId, short value) {
+    set(propertyId, Short.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Short> propertyId, short value,
+      @Nonnull Location location) {
+    set(propertyId, Short.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Character> propertyId, char value) {
+    set(propertyId, Character.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Character> propertyId, char value,
+      @Nonnull Location location) {
+    set(propertyId, Character.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Integer> propertyId, int value) {
+    set(propertyId, Integer.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Integer> propertyId, int value,
+      @Nonnull Location location) {
+    set(propertyId, Integer.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Long> propertyId, long value) {
+    set(propertyId, Long.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Long> propertyId, long value,
+      @Nonnull Location location) {
+    set(propertyId, Long.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Float> propertyId, float value) {
+    set(propertyId, Float.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Float> propertyId, float value,
+      @Nonnull Location location) {
+    set(propertyId, Float.valueOf(value), location);
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Double> propertyId, double value) {
+    set(propertyId, Double.valueOf(value));
+
+    return this;
+  }
+
+  @Nonnull
+  public GatherConfigBuilder set(@Nonnull PropertyId<Double> propertyId, double value,
+      @Nonnull Location location) {
+    set(propertyId, Double.valueOf(value), location);
+
+    return this;
+  }
 }
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/sched/src/com/android/sched/util/config/InternalConfig.java
similarity index 62%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to sched/src/com/android/sched/util/config/InternalConfig.java
index 0c967d9..0f96a98 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/sched/src/com/android/sched/util/config/InternalConfig.java
@@ -14,18 +14,18 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.util.config;
 
-import java.util.Collection;
+import com.android.sched.util.config.id.PropertyId;
 
+import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
- * Virtual directory.
+ * The interface that deals with configuration properties in private 'get' mode. This interface is
+ * for private use only (config framework itself).
  */
-public interface VDir extends VElement {
-
-  @Nonnull
-  Collection<? extends VElement> list();
-
+public interface InternalConfig {
+  @CheckForNull
+  public <T> T getObjectIfAny(@Nonnull PropertyId<T> propertyId);
 }
diff --git a/sched/src/com/android/sched/util/config/ThreadConfig.java b/sched/src/com/android/sched/util/config/ThreadConfig.java
index df8cfa5..da532fd 100644
--- a/sched/src/com/android/sched/util/config/ThreadConfig.java
+++ b/sched/src/com/android/sched/util/config/ThreadConfig.java
@@ -16,7 +16,14 @@
 
 package com.android.sched.util.config;
 
-import com.android.sched.util.config.id.KeyId;
+import com.android.sched.util.config.id.ObjectId;
+import com.android.sched.util.config.id.PropertyId;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
+import com.android.sched.util.log.stats.Counter;
+import com.android.sched.util.log.stats.CounterImpl;
+import com.android.sched.util.log.stats.StatisticId;
+import com.android.sched.util.log.tracer.TracerEventType;
 
 import javax.annotation.Nonnull;
 
@@ -25,6 +32,11 @@
  */
 public class ThreadConfig {
   @Nonnull
+  public static final StatisticId<Counter> TLS_READ = new StatisticId<Counter>(
+      "sched.config.tls.read", "Reading TLS to get current config",
+      CounterImpl.class, Counter.class);
+
+  @Nonnull
   private static final Config unitializedConfig = new UninitializedConfig();
 
   @Nonnull
@@ -37,8 +49,27 @@
       };
 
   @Nonnull
-  public static <T, S> T get(@Nonnull KeyId<T, S> keyId) {
-    return threadLocalConfig.get().get(keyId);
+  public static <T> T get(@Nonnull PropertyId<T> propertyId) {
+    Config config = threadLocalConfig.get();
+    updateStatistic(config);
+
+    return config.get(propertyId);
+  }
+
+  @Nonnull
+  public static <T> T get(@Nonnull ObjectId<T> objectId) {
+    Config config = threadLocalConfig.get();
+    updateStatistic(config);
+
+    return config.get(objectId);
+  }
+
+  private static void updateStatistic(@Nonnull Config config) {
+    Tracer tracer = ((InternalConfig) config).<Tracer> getObjectIfAny(TracerFactory.TRACER);
+
+    if (tracer != null && tracer.getCurrentEventType() != TracerEventType.NOEVENT) {
+      tracer.getStatistic(TLS_READ).incValue();
+    }
   }
 
   @Nonnull
diff --git a/sched/src/com/android/sched/util/config/UninitializedConfig.java b/sched/src/com/android/sched/util/config/UninitializedConfig.java
index f87e628..b6c8e7f 100644
--- a/sched/src/com/android/sched/util/config/UninitializedConfig.java
+++ b/sched/src/com/android/sched/util/config/UninitializedConfig.java
@@ -17,16 +17,29 @@
 package com.android.sched.util.config;
 
 import com.android.sched.util.config.id.KeyId;
+import com.android.sched.util.config.id.ObjectId;
 import com.android.sched.util.config.id.PropertyId;
 
 import java.util.Collection;
 
+import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
 /**
  * This object represents a {@link Config} which has not been created by the builder.
  */
-class UninitializedConfig implements Config {
+class UninitializedConfig implements Config, InternalConfig {
+  @Override
+  @Nonnull
+  public <T> T get(@Nonnull PropertyId<T> propertyId) {
+    throw new ConfigurationError("Configuration has not been initialized");
+  }
+
+  @Override
+  @Nonnull
+  public <T> T get(@Nonnull ObjectId<T> objectId) {
+    throw new ConfigurationError("Configuration has not been initialized");
+  }
 
   @Override
   @Nonnull
@@ -45,4 +58,10 @@
   public Collection<PropertyId<?>> getPropertyIds() {
     throw new ConfigurationError("Configuration has not been initialized");
   }
+
+  @Override
+  @CheckForNull
+  public <T> T getObjectIfAny(@Nonnull PropertyId<T> propertyId) {
+    throw new ConfigurationError("Configuration has not been initialized");
+  }
 }
diff --git a/sched/src/com/android/sched/util/config/VariableDoesNotMatchConfigurationException.java b/sched/src/com/android/sched/util/config/VariableDoesNotMatchConfigurationException.java
index 06c711c..788e852 100644
--- a/sched/src/com/android/sched/util/config/VariableDoesNotMatchConfigurationException.java
+++ b/sched/src/com/android/sched/util/config/VariableDoesNotMatchConfigurationException.java
@@ -25,7 +25,7 @@
   private static final long serialVersionUID = 1L;
 
   public VariableDoesNotMatchConfigurationException(@Nonnull String variable) {
-    super(variable, "Environment variable '" + variable + " does not match any properties");
+    super(variable, "Environment variable '" + variable + "' does not match any properties");
   }
 
   public VariableDoesNotMatchConfigurationException(
diff --git a/sched/src/com/android/sched/util/config/VariableMatchesSeveralConfigurationException.java b/sched/src/com/android/sched/util/config/VariableMatchesSeveralConfigurationException.java
index f6eaab6..1e00409 100644
--- a/sched/src/com/android/sched/util/config/VariableMatchesSeveralConfigurationException.java
+++ b/sched/src/com/android/sched/util/config/VariableMatchesSeveralConfigurationException.java
@@ -31,7 +31,7 @@
 
   public VariableMatchesSeveralConfigurationException(
       @Nonnull String variable, @Nonnull PropertyId<?> propertyId) {
-    super(variable, "Environment variable '" + variable + " matches several properties: '"
+    super(variable, "Environment variable '" + variable + "' matches several properties: '"
         + propertyId.getName() + "'");
     this.propertyId = propertyId;
   }
diff --git a/sched/src/com/android/sched/util/config/ZipLocation.java b/sched/src/com/android/sched/util/config/ZipLocation.java
index 3a6d9be..af78749 100644
--- a/sched/src/com/android/sched/util/config/ZipLocation.java
+++ b/sched/src/com/android/sched/util/config/ZipLocation.java
@@ -30,11 +30,11 @@
   private final Location archive;
 
   @Nonnull
-  private final String pathInArchive;
+  private final String entryName;
 
   public ZipLocation(@Nonnull Location archive, @Nonnull ZipEntry entry) {
     this.archive = archive;
-    this.pathInArchive = '/' + entry.getName();
+    this.entryName = entry.getName();
   }
 
   @Override
@@ -46,7 +46,7 @@
       sb.append(archive.getDescription()).append(", ");
     }
 
-    return sb.append("entry '").append(pathInArchive).append('\'').toString();
+    return sb.append("entry '/").append(entryName).append('\'').toString();
   }
 
   @Nonnull
@@ -54,22 +54,20 @@
     return archive;
   }
 
-  /**
-   * @return the pathInArchive
-   */
-  public String getPathInArchive() {
-    return pathInArchive;
+  @Nonnull
+  public String getEntryName() {
+    return entryName;
   }
 
   @Override
   public final boolean equals(Object obj) {
     return obj instanceof ZipLocation
         && ((ZipLocation) obj).archive.equals(archive)
-        && ((ZipLocation) obj).getPathInArchive().equals(pathInArchive);
+        && ((ZipLocation) obj).entryName.equals(entryName);
   }
 
   @Override
   public final int hashCode() {
-    return archive.hashCode() ^ pathInArchive.hashCode();
+    return archive.hashCode() ^ entryName.hashCode();
   }
 }
diff --git a/sched/src/com/android/sched/util/config/id/BooleanPropertyId.java b/sched/src/com/android/sched/util/config/id/BooleanPropertyId.java
index ebe2399..a97bd45 100644
--- a/sched/src/com/android/sched/util/config/id/BooleanPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/BooleanPropertyId.java
@@ -52,6 +52,21 @@
 
   @Override
   @Nonnull
+  public BooleanPropertyId addDefaultValue (@Nonnull Boolean defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Nonnull
+  public BooleanPropertyId addDefaultValue (boolean defaultValue) {
+    super.addDefaultValue(Boolean.valueOf(defaultValue));
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public BooleanPropertyId requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
diff --git a/sched/src/com/android/sched/util/config/id/DoublePropertyId.java b/sched/src/com/android/sched/util/config/id/DoublePropertyId.java
index 786c9b2..111fd5e 100644
--- a/sched/src/com/android/sched/util/config/id/DoublePropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/DoublePropertyId.java
@@ -51,6 +51,21 @@
 
   @Override
   @Nonnull
+  public DoublePropertyId addDefaultValue (@Nonnull Double defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Nonnull
+  public DoublePropertyId addDefaultValue (@Nonnull double defaultValue) {
+    super.addDefaultValue(Double.valueOf(defaultValue));
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public DoublePropertyId requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
diff --git a/sched/src/com/android/sched/util/config/id/EnumPropertyId.java b/sched/src/com/android/sched/util/config/id/EnumPropertyId.java
index 493f1e5..c209e3c 100644
--- a/sched/src/com/android/sched/util/config/id/EnumPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/EnumPropertyId.java
@@ -51,6 +51,14 @@
 
   @Override
   @Nonnull
+  public EnumPropertyId<T> addDefaultValue (@Nonnull T defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public EnumPropertyId<T> requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
diff --git a/sched/src/com/android/sched/util/config/id/IntegerPropertyId.java b/sched/src/com/android/sched/util/config/id/IntegerPropertyId.java
index 4b584cd..ce03c10 100644
--- a/sched/src/com/android/sched/util/config/id/IntegerPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/IntegerPropertyId.java
@@ -44,6 +44,20 @@
     return this;
   }
 
+  @Nonnull
+  public IntegerPropertyId addDefaultValue (@Nonnull Integer defaultValue) {
+    super.addDefaultValue(Long.valueOf(defaultValue.longValue()));
+
+    return this;
+  }
+
+  @Nonnull
+  public IntegerPropertyId addDefaultValue (@Nonnull int defaultValue) {
+    super.addDefaultValue(Long.valueOf(defaultValue));
+
+    return this;
+  }
+
   @Override
   @Nonnull
   public IntegerPropertyId requiredIf(@Nonnull BooleanExpression expression) {
diff --git a/sched/src/com/android/sched/util/config/id/KeyId.java b/sched/src/com/android/sched/util/config/id/KeyId.java
index 40b157c..3576fab 100644
--- a/sched/src/com/android/sched/util/config/id/KeyId.java
+++ b/sched/src/com/android/sched/util/config/id/KeyId.java
@@ -21,9 +21,6 @@
 import com.android.sched.util.config.expression.BooleanExpression;
 import com.android.sched.util.config.expression.PropertyNotRequiredException;
 
-import java.util.ArrayList;
-import java.util.List;
-
 import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
@@ -38,12 +35,6 @@
   @Nonnull
   private final String name;
 
-  @CheckForNull
-  private BooleanExpression requiredIf;
-
-  @Nonnull
-  private final List<S> defaultValues = new ArrayList<S>(2);
-
   public KeyId(@Nonnull String name) {
     this.name = name;
   }
@@ -55,17 +46,8 @@
 
   public abstract boolean isPublic();
 
-  @Nonnull
-  public KeyId<T, S> addDefaultValue(@Nonnull S defaultValue) {
-    defaultValues.add(defaultValue);
-
-    return this;
-  }
-
-  @Nonnull
-  public List<S> getDefaultValues() {
-    return defaultValues;
-  }
+  @CheckForNull
+  private BooleanExpression requiredIf;
 
   @Nonnull
   public KeyId<T, S> requiredIf(@Nonnull BooleanExpression expression) {
diff --git a/sched/src/com/android/sched/util/config/id/ListPropertyId.java b/sched/src/com/android/sched/util/config/id/ListPropertyId.java
index 7f7c999..075fa00 100644
--- a/sched/src/com/android/sched/util/config/id/ListPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/ListPropertyId.java
@@ -55,6 +55,15 @@
     return this;
   }
 
+
+  @Override
+  @Nonnull
+  public ListPropertyId<T> addDefaultValue (@Nonnull List<T> defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
   @Override
   @Nonnull
   public ListPropertyId<T> requiredIf(@Nonnull BooleanExpression expression) {
diff --git a/sched/src/com/android/sched/util/config/id/LongPropertyId.java b/sched/src/com/android/sched/util/config/id/LongPropertyId.java
index cb1e377..7f95102 100644
--- a/sched/src/com/android/sched/util/config/id/LongPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/LongPropertyId.java
@@ -51,6 +51,21 @@
 
   @Override
   @Nonnull
+  public LongPropertyId addDefaultValue (@Nonnull Long defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Nonnull
+  public LongPropertyId addDefaultValue (@Nonnull long defaultValue) {
+    super.addDefaultValue(Long.valueOf(defaultValue));
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public LongPropertyId requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
diff --git a/sched/src/com/android/sched/util/config/id/ProbabilityPropertyId.java b/sched/src/com/android/sched/util/config/id/ProbabilityPropertyId.java
index 1e173e1..f83165b 100644
--- a/sched/src/com/android/sched/util/config/id/ProbabilityPropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/ProbabilityPropertyId.java
@@ -45,6 +45,22 @@
 
   @Override
   @Nonnull
+  public ProbabilityPropertyId addDefaultValue (@Nonnull Double defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
+  public ProbabilityPropertyId addDefaultValue (@Nonnull double defaultValue) {
+    super.addDefaultValue(defaultValue);
+
+    return this;
+  }
+
+  @Override
+  @Nonnull
   public ProbabilityPropertyId requiredIf(@Nonnull BooleanExpression expression) {
     super.requiredIf(expression);
 
@@ -70,7 +86,7 @@
   }
 
   private boolean checkRange(double value) {
-    return value >= 0 && value <= 1;
+    return value >= 0.0 && value <= 1.0;
   }
 
   /**
diff --git a/sched/src/com/android/sched/util/config/id/PropertyId.java b/sched/src/com/android/sched/util/config/id/PropertyId.java
index 7e9fa28..280bf08 100644
--- a/sched/src/com/android/sched/util/config/id/PropertyId.java
+++ b/sched/src/com/android/sched/util/config/id/PropertyId.java
@@ -23,6 +23,9 @@
 import com.android.sched.util.config.ConfigurationError;
 import com.android.sched.util.config.expression.BooleanExpression;
 
+import java.util.ArrayList;
+import java.util.List;
+
 import javax.annotation.CheckForNull;
 import javax.annotation.Nonnull;
 
@@ -31,48 +34,55 @@
  * @param <T> Type of the configuration property.
  */
 public class PropertyId<T> extends KeyId<T, String> {
-
   @Nonnull
   private final String description;
 
   @Nonnull
-  private final StringCodec<T> parser;
+  private final StringCodec<T> codec;
 
+  @Nonnull
+  private final List<Value> defaultValues = new ArrayList<Value>(1);
   @CheckForNull
-  private String  defaultValue = null;
-  private boolean defaultValueAvailable = false;
+  private Value    defaultValue = null;
+  private boolean  defaultValueAvailable = false;
 
   private boolean isPublic = true;
 
   public static <T> PropertyId<T> create(
-      @Nonnull String name, @Nonnull String description, @Nonnull StringCodec<T> parser) {
-    return new PropertyId<T>(name, description, parser);
+      @Nonnull String name, @Nonnull String description, @Nonnull StringCodec<T> codec) {
+    return new PropertyId<T>(name, description, codec);
   }
 
-  protected PropertyId(
-      @Nonnull String name, @Nonnull String description, @Nonnull StringCodec<T> parser) {
+  protected PropertyId(@Nonnull String name, @Nonnull String description,
+      @Nonnull StringCodec<T> codec) {
     super(name);
 
     this.description = description;
-    this.parser = parser;
+    this.codec = codec;
   }
 
-  @Override
   @Nonnull
   public PropertyId<T> addDefaultValue(@Nonnull String defaultValue) {
-    super.addDefaultValue(defaultValue);
+    defaultValues.add(new Value(defaultValue));
+
+    return this;
+  }
+
+  @Nonnull
+  public PropertyId<T> addDefaultValue(@Nonnull T defaultValue) {
+    defaultValues.add(new Value(defaultValue));
 
     return this;
   }
 
   @CheckForNull
-  public String getDefaultValue(@Nonnull CodecContext context) {
+  public Value getDefaultValue(@Nonnull CodecContext context) {
     if (!defaultValueAvailable) {
       ParsingException lastException = null;
 
-      for (String value : getDefaultValues()) {
+      for (Value value : getDefaultValues()) {
         try {
-          parser.checkString(context, value);
+          value.check(context);
           defaultValue = value;
           break;
         } catch (ParsingException e) {
@@ -91,6 +101,11 @@
   }
 
   @Nonnull
+  public List<Value> getDefaultValues() {
+    return defaultValues;
+  }
+
+  @Nonnull
   public String getDescription() {
     return description;
   }
@@ -100,6 +115,7 @@
     return isPublic;
   }
 
+  @Nonnull
   public PropertyId<T> makePrivate() {
     isPublic = false;
     return this;
@@ -107,7 +123,7 @@
 
   @Nonnull
   public StringCodec<T> getCodec() {
-    return parser;
+    return codec;
   }
 
   @Override
@@ -118,4 +134,148 @@
     return this;
   }
 
+  public class Value {
+    @Nonnull
+    private IValue<T> value;
+
+    public Value (@Nonnull T value) {
+      this.value = new IValueObject<T>(value);
+    }
+
+    public Value (@Nonnull String value) {
+      this.value = new IValueString(value);
+    }
+
+    public synchronized void check(@Nonnull CodecContext context) throws ParsingException {
+      value = value.check(context);
+    }
+
+    @Nonnull
+    public String getString() {
+      return value.getString();
+    }
+
+    @Nonnull
+    public synchronized T getObject(@Nonnull CodecContext context) {
+      value = value.getValueObject(context);
+
+      return ((IValueObject<T>) value).getObject();
+    }
+
+
+    @CheckForNull
+    public synchronized T getObjectIfAny() {
+      if (value instanceof IValueObject) {
+        return ((IValueObject<T>) value).getObject();
+      } else {
+        return null;
+      }
+    }
+  }
+
+  //
+  // Private IValue hierarchy
+  //
+
+  private static interface IValue<T> {
+    @Nonnull
+    public IValue<T> check(@Nonnull CodecContext context) throws ParsingException;
+
+    @Nonnull
+    public PropertyId<?>.IValueObject<T> getValueObject(@Nonnull CodecContext context);
+
+    @Nonnull
+    public String getString();
+  }
+
+  private class IValueString implements IValue<T> {
+    @Nonnull
+    private final String value;
+
+    public IValueString (@Nonnull String value) {
+      this.value = value;
+    }
+
+    @Override
+    public String getString() {
+      return value;
+    }
+
+    @Override
+    @Nonnull
+    public IValue<T> check(@Nonnull CodecContext context) throws ParsingException {
+      T val = PropertyId.this.codec.checkString(context, value);
+
+      if (val != null) {
+        return new IValueObject<T>(val);
+      } else {
+        return new IValueCheckedString(value);
+      }
+    }
+
+    @Override
+    @Nonnull
+    public PropertyId<T>.IValueObject<T> getValueObject(@Nonnull CodecContext context) {
+      throw new AssertionError();
+    }
+  }
+
+  private class IValueCheckedString implements IValue<T> {
+    @Nonnull
+    private final String value;
+
+    private IValueCheckedString (@Nonnull String value) {
+      this.value = value;
+    }
+
+    @Override
+    public String getString() {
+      return value;
+    }
+
+    @Override
+    @Nonnull
+    public IValue<T> check(@Nonnull CodecContext context) {
+      return this;
+    }
+
+    @Override
+    @Nonnull
+    public PropertyId<?>.IValueObject<T> getValueObject(@Nonnull CodecContext context) {
+      return new IValueObject<T>(PropertyId.this.codec.parseString(context, value));
+    }
+  }
+
+  private class IValueObject<T> implements IValue<T> {
+    @Nonnull
+    private final T value;
+
+    public IValueObject (@Nonnull T value) {
+      this.value = value;
+    }
+
+    @SuppressWarnings("unchecked")
+    @Override
+    @Nonnull
+    public String getString() {
+      return ((PropertyId<T>) (PropertyId.this)).codec.formatValue(value);
+    }
+
+    @Override
+    @Nonnull
+    public IValue<T> check(@Nonnull CodecContext context) {
+      return this;
+    }
+
+    @Override
+    @Nonnull
+    public PropertyId<?>.IValueObject<T> getValueObject(@Nonnull CodecContext context) {
+      return this;
+    }
+
+    @Nonnull
+    public T getObject() {
+      return value;
+    }
+  }
 }
diff --git a/sched/src/com/android/sched/util/log/EventType.java b/sched/src/com/android/sched/util/log/EventType.java
index 040d99a..418ccc3 100644
--- a/sched/src/com/android/sched/util/log/EventType.java
+++ b/sched/src/com/android/sched/util/log/EventType.java
@@ -20,6 +20,5 @@
  * Represents a event type of an event.
  */
 public interface EventType {
-  public String getColor();
   public String getName();
 }
\ No newline at end of file
diff --git a/sched/src/com/android/sched/util/log/SchedEventType.java b/sched/src/com/android/sched/util/log/SchedEventType.java
index dd2352b..0344d6e 100644
--- a/sched/src/com/android/sched/util/log/SchedEventType.java
+++ b/sched/src/com/android/sched/util/log/SchedEventType.java
@@ -23,24 +23,15 @@
  * Represents a type of event whose performance is tracked
  */
 public enum SchedEventType implements EventType {
-  REFLECTIONS("Reflections", "Yellow"), //
-  INSTANCIER("Schedulable instancier", "Blue"), //
-  PLANBUILDER("Plan builder", "Red");
+  REFLECTIONS("Reflections"),
+  INSTANCIER("Schedulable instancier"),
+  PLANBUILDER("Plan builder");
 
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
-  SchedEventType(@Nonnull String name, @Nonnull String cssColor) {
+  SchedEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/sched/src/com/android/sched/util/log/StatisticOnlyTracer.java b/sched/src/com/android/sched/util/log/StatisticOnlyTracer.java
index da5323b..81095e5 100644
--- a/sched/src/com/android/sched/util/log/StatisticOnlyTracer.java
+++ b/sched/src/com/android/sched/util/log/StatisticOnlyTracer.java
@@ -36,11 +36,13 @@
 import com.android.sched.util.table.SimpleTable;
 import com.android.sched.util.table.Table;
 
+import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.Date;
 import java.util.HashMap;
 import java.util.HashSet;
+import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
 import java.util.Map.Entry;
@@ -48,6 +50,7 @@
 import java.util.WeakHashMap;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.atomic.AtomicInteger;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
 import java.util.logging.Level;
 import java.util.logging.Logger;
 
@@ -147,7 +150,7 @@
     @Override
     @Nonnull
     public String toString() {
-      return "Dummy";
+      return "Singleton";
     }
 
     @Override
@@ -221,7 +224,7 @@
   @Override
   @Nonnull
   public EventType getCurrentEventType() {
-    return TracerEventType.NOEVENT;
+    return TracerEventType.SINGLETON;
   }
 
   @Override
@@ -246,77 +249,116 @@
       objects = new HashMap<
           Class<? extends ObjectWatcher<?>>, WeakHashMap<Object, ObjectWatcher<Object>>>();
 
+  // Map a class C to a list of watcher classes that watch instances of type C
   @Nonnull
-  private final Map<Class<?>, Class<? extends ObjectWatcher<?>>> watchers =
-      new HashMap<Class<?>, Class<? extends ObjectWatcher<?>>>();
+  private final Map<Class<?>, List<Class<? extends ObjectWatcher<?>>>> watchers =
+      new HashMap<Class<?>, List<Class<? extends ObjectWatcher<?>>>>();
 
+  // Set of classes not watched (speedup non watched classes)
   @Nonnull
   private final Set<Class<?>> notWatched = new HashSet<Class<?>>();
   @Nonnull
-  private final Object watcherLock = new Object();
+  private final ReentrantReadWriteLock watcherLock = new ReentrantReadWriteLock();
 
   @Override
-  public synchronized <T> void registerWatcher(@Nonnull Class<T> objectClass,
+  public synchronized <T> void registerWatcher(@Nonnull Class<T> rootWatchedClass,
       @Nonnull Class<? extends ObjectWatcher<? extends T>> watcherClass) {
     WeakHashMap<Object, ObjectWatcher<Object>> map =
         new WeakHashMap<Object, ObjectWatcher<Object>>();
 
-    synchronized (watcherLock) {
+    watcherLock.writeLock().lock();
+    try {
       objects.put(watcherClass, map);
-      watchers.put(objectClass, watcherClass);
 
-      for (Class<?> cls : notWatched) {
-        if (objectClass.isAssignableFrom(cls)) {
+      List<Class<? extends ObjectWatcher<?>>> list = watchers.get(rootWatchedClass);
+      if (list == null) {
+        list = new ArrayList<Class<? extends ObjectWatcher<?>>>(1);
+        watchers.put(rootWatchedClass, list);
+      }
+
+      list.add(watcherClass);
+
+      Iterator<Class<?>> iterNotWatched = notWatched.iterator();
+      while (iterNotWatched.hasNext()) {
+        Class<?> watchedClass = iterNotWatched.next();
+        if (rootWatchedClass.isAssignableFrom(watchedClass)) {
           logger.log(Level.INFO, "Watcher ''{0}'' missed some instances of type ''{1}''",
-              new Object[] {watcherClass.getName(), cls.getName()});
+              new Object[] {watcherClass.getName(), watchedClass.getName()});
 
-          watchers.put(cls, watcherClass);
-          notWatched.remove(objectClass);
+          list = watchers.get(watchedClass);
+          if (list == null) {
+            list = new ArrayList<Class<? extends ObjectWatcher<?>>>(1);
+            watchers.put(watchedClass, list);
+          }
+
+          list.add(watcherClass);
+          iterNotWatched.remove();
         }
       }
+    } finally {
+      watcherLock.writeLock().unlock();
     }
   }
 
   @Override
   public void registerObject(@Nonnull Object object, @Nonnegative long size, int count) {
-    Class<? extends ObjectWatcher<?>> watcherClass = null;
+    enable.set(Boolean.FALSE);
+    Class<?> objectClass = object.getClass();
+    List<Class<? extends ObjectWatcher<?>>> list = null;
 
-    synchronized (watcherLock) {
-      if (notWatched.contains(object.getClass())) {
+    watcherLock.readLock().lock();
+    try {
+      // If this object is not watched explicitly, go away
+      if (notWatched.contains(objectClass)) {
         return;
       }
 
-      watcherClass = watchers.get(object.getClass());
-      if (watcherClass == null) {
-        for (Entry<Class<?>, Class<? extends ObjectWatcher<?>>> entry : watchers.entrySet()) {
-          if (entry.getKey().isAssignableFrom(object.getClass())) {
-            watcherClass = entry.getValue();
-            break;
+      list = watchers.get(objectClass);
+    } finally {
+      watcherLock.readLock().unlock();
+    }
+
+    if (list == null) {
+      watcherLock.writeLock().lock();
+      try {
+        list = watchers.get(objectClass);
+        if (list == null) {
+          list = new ArrayList<Class<? extends ObjectWatcher<?>>>(1);
+
+          for (Entry<Class<?>, List<Class<? extends ObjectWatcher<?>>>> entry :
+              watchers.entrySet()) {
+            if (entry.getKey().isAssignableFrom(objectClass)) {
+              list.addAll(entry.getValue());
+            }
           }
         }
 
-        if (watcherClass != null) {
-          watchers.put(object.getClass(), watcherClass);
+        if (!list.isEmpty()) {
+          watchers.put(objectClass, list);
         } else {
-          notWatched.add(object.getClass());
-          return;
+          notWatched.add(objectClass);
         }
+      } finally {
+        watcherLock.writeLock().unlock();
       }
     }
 
-    try {
-      @SuppressWarnings("unchecked")
-      ObjectWatcher<Object> watcher = (ObjectWatcher<Object>) watcherClass.newInstance();
-      WeakHashMap<Object, ObjectWatcher<Object>> weak = objects.get(watcherClass);
-      assert weak != null; // If watchers contains object.getClass, then objects contains it also,
-                           // see registerWatcher
-      if (watcher.notifyInstantiation(object, size, count, getCurrentEventType())) {
-        weak.put(object, watcher);
+    for (Class<? extends ObjectWatcher<?>> watcherClass : list) {
+      try {
+        @SuppressWarnings("unchecked")
+        ObjectWatcher<Object> watcher = (ObjectWatcher<Object>) watcherClass.newInstance();
+
+        if (watcher.notifyInstantiation(object, size, count, getCurrentEventType())) {
+          WeakHashMap<Object, ObjectWatcher<Object>> weak = objects.get(watcherClass);
+          assert weak != null; // If watchers contains object.getClass, then objects contains it
+                               // also, see registerWatcher
+          weak.put(object, watcher);
+        }
+      } catch (InstantiationException e) {
+        logger.log(Level.WARNING, "Can not instantiate Watcher", e);
+      } catch (IllegalAccessException e) {
+        logger.log(Level.WARNING, "Can not instantiate Watcher", e);
       }
-    } catch (InstantiationException e) {
-      logger.log(Level.WARNING, "Can not instantiate Watcher", e);
-    } catch (IllegalAccessException e) {
-      logger.log(Level.WARNING, "Can not instantiate Watcher", e);
     }
   }
 }
diff --git a/sched/src/com/android/sched/util/log/stats/Alloc.java b/sched/src/com/android/sched/util/log/stats/Alloc.java
index 2bf2989..ae1b50b 100644
--- a/sched/src/com/android/sched/util/log/stats/Alloc.java
+++ b/sched/src/com/android/sched/util/log/stats/Alloc.java
@@ -46,53 +46,10 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Count";
-      case 1:
-        return "Size";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      case 1:
-        return "number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public String getDescription() {
     return "Allocation";
   }
 
-
   @Nonnull
   private static final String[] HEADER = new String[] {
     "Count",
diff --git a/sched/src/com/android/sched/util/log/stats/AllocImpl.java b/sched/src/com/android/sched/util/log/stats/AllocImpl.java
index bbed19c..df2b01a 100644
--- a/sched/src/com/android/sched/util/log/stats/AllocImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/AllocImpl.java
@@ -18,7 +18,6 @@
 
 import com.google.common.collect.Iterators;
 
-import com.android.sched.util.log.tracer.probe.MemoryBytesProbe;
 import com.android.sched.util.table.DataHeader;
 import com.android.sched.util.table.DataRow;
 
@@ -63,34 +62,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public synchronized Object getValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.valueOf(number);
-      case 1:
-        return Long.valueOf(size);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public synchronized String getHumanReadableValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.toString(number);
-      case 1:
-        return MemoryBytesProbe.formatBytes(size);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public synchronized Iterator<Object> iterator() {
     return Iterators.<Object> forArray(
         Long.valueOf(number),
diff --git a/sched/src/com/android/sched/util/log/stats/ArrayAlloc.java b/sched/src/com/android/sched/util/log/stats/ArrayAlloc.java
index 5b29bbf..d086b49 100644
--- a/sched/src/com/android/sched/util/log/stats/ArrayAlloc.java
+++ b/sched/src/com/android/sched/util/log/stats/ArrayAlloc.java
@@ -18,9 +18,9 @@
 
 import com.google.common.collect.ObjectArrays;
 
+import com.android.sched.util.codec.ByteFormatter;
 import com.android.sched.util.codec.Formatter;
 import com.android.sched.util.codec.LongCodec;
-import com.android.sched.util.codec.ByteFormatter;
 
 import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
@@ -49,64 +49,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Array count";
-      case 1:
-        return "Total size";
-      case 2:
-        return "Total elements";
-      case 3:
-        return "Min elements";
-      case 4:
-        return "Average elements";
-      case 5:
-        return "max elements";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      case 1:
-        return "number";
-      case 2:
-        return "number";
-      case 3:
-        return "number";
-      case 4:
-        return "number";
-      case 5:
-        return "number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public String getDescription() {
     return "Array allocation";
   }
diff --git a/sched/src/com/android/sched/util/log/stats/ArrayAllocImpl.java b/sched/src/com/android/sched/util/log/stats/ArrayAllocImpl.java
index ff59b55..f5b5c5e 100644
--- a/sched/src/com/android/sched/util/log/stats/ArrayAllocImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/ArrayAllocImpl.java
@@ -18,7 +18,6 @@
 
 import com.google.common.collect.Iterators;
 
-import com.android.sched.util.log.tracer.probe.MemoryBytesProbe;
 import com.android.sched.util.table.DataRow;
 
 import java.util.Iterator;
@@ -69,34 +68,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public synchronized Object getValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.valueOf(number);
-      case 1:
-        return Long.valueOf(size);
-      default:
-        return element.getValue(columnIdx - 1);
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public synchronized String getHumanReadableValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.toString(number);
-      case 1:
-        return MemoryBytesProbe.formatBytes(size);
-      default:
-        return element.getHumanReadableValue(columnIdx - 1);
-    }
-  }
-
-  @Override
-  @Nonnull
   public synchronized Iterator<Object> iterator() {
     return Iterators.concat(
         Iterators.forArray(Long.valueOf(number), Long.valueOf(size)), element.iterator());
diff --git a/sched/src/com/android/sched/util/log/stats/Counter.java b/sched/src/com/android/sched/util/log/stats/Counter.java
index 8001004..fb6b630 100644
--- a/sched/src/com/android/sched/util/log/stats/Counter.java
+++ b/sched/src/com/android/sched/util/log/stats/Counter.java
@@ -24,7 +24,7 @@
 
 
 /**
- * Represents a counter statistic when statistic is not enabled..
+ * Represents a counter statistic when statistic is not enabled.
  */
 public class Counter extends Statistic {
   protected Counter(@Nonnull StatisticId<? extends Statistic> id) {
@@ -60,45 +60,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public String getDescription() {
     return "Counter";
   }
diff --git a/sched/src/com/android/sched/util/log/stats/CounterImpl.java b/sched/src/com/android/sched/util/log/stats/CounterImpl.java
index 32aca6c..3aeca0a 100644
--- a/sched/src/com/android/sched/util/log/stats/CounterImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/CounterImpl.java
@@ -22,7 +22,6 @@
 
 import java.util.Iterator;
 
-import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
 
 
@@ -82,24 +81,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    assert columnIdx == 0;
-
-    return Long.valueOf(value);
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    assert columnIdx == 0;
-
-    return Long.valueOf(value).toString();
-  }
-
-  @Override
-  @Nonnull
   public synchronized Iterator<Object> iterator() {
     return Iterators.<Object> forArray(Long.valueOf(value));
   }
diff --git a/sched/src/com/android/sched/util/log/stats/ExtendedSample.java b/sched/src/com/android/sched/util/log/stats/ExtendedSample.java
new file mode 100644
index 0000000..5ade77f
--- /dev/null
+++ b/sched/src/com/android/sched/util/log/stats/ExtendedSample.java
@@ -0,0 +1,131 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.util.log.stats;
+
+import com.android.sched.util.codec.DoubleCodec;
+import com.android.sched.util.codec.Formatter;
+import com.android.sched.util.codec.LongCodec;
+
+import javax.annotation.Nonnegative;
+import javax.annotation.Nonnull;
+
+/**
+ * Extended statistic computation on a set of values when statistic is not enabled. Have Median,
+ * First quartile, Third quartile.
+ */
+public class ExtendedSample extends Statistic {
+  protected ExtendedSample(@Nonnull StatisticId<? extends Statistic> id) {
+    super(id);
+  }
+
+  public void add(double value) {
+  }
+
+  @Nonnegative
+  public int getCount() {
+    return 0;
+  }
+
+  public double getTotal() {
+    return 0;
+  }
+
+  public double getMin() {
+    return Double.NaN;
+  }
+
+  public double getAverage() {
+    return Double.NaN;
+  }
+
+  public double getMax() {
+    return Double.NaN;
+  }
+
+  public double getFirstQuartile() {
+    return Double.NaN;
+  }
+
+  public double getMedian() {
+    return Double.NaN;
+  }
+
+  public double getThirdQuartile() {
+    return Double.NaN;
+  }
+
+  @Override
+  public void merge(@Nonnull Statistic statistic) {
+    throw new UnsupportedOperationException();
+  }
+
+  @Override
+  @Nonnull
+  public String getDescription() {
+    return "Sample";
+  }
+
+
+  @Nonnull
+  private static final String[] HEADER = new String[] {
+    "Count",
+    "Total",
+    "Min",
+    "Average",
+    "First Quartile",
+    "Median",
+    "Third Quartile",
+    "Max"
+  };
+
+  @Override
+  @Nonnull
+  public String[] getHeader() {
+    return HEADER.clone();
+  }
+
+  @Nonnull
+  public static String[] getStaticHeader() {
+    return HEADER.clone();
+  }
+
+  @Nonnull
+  public static Formatter<? extends Object>[] getStaticFormatters() {
+    return new Formatter<?>[] {
+        new LongCodec(),
+        new DoubleCodec(),
+        new DoubleCodec(),
+        new DoubleCodec(),
+        new DoubleCodec(),
+        new DoubleCodec(),
+        new DoubleCodec(),
+        new DoubleCodec()
+    };
+  }
+
+  @Override
+  @Nonnull
+  public Formatter<? extends Object>[] getFormatters() {
+    return getStaticFormatters();
+  }
+
+  @Override
+  @Nonnegative
+  public int getColumnCount() {
+    return HEADER.length;
+  }
+}
diff --git a/sched/src/com/android/sched/util/log/stats/ExtendedSampleImpl.java b/sched/src/com/android/sched/util/log/stats/ExtendedSampleImpl.java
new file mode 100644
index 0000000..c0e77c4
--- /dev/null
+++ b/sched/src/com/android/sched/util/log/stats/ExtendedSampleImpl.java
@@ -0,0 +1,187 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.util.log.stats;
+
+import com.google.common.collect.Iterators;
+
+import com.android.sched.util.table.DataHeader;
+import com.android.sched.util.table.DataRow;
+
+import java.util.Arrays;
+import java.util.Iterator;
+
+import javax.annotation.Nonnegative;
+import javax.annotation.Nonnull;
+
+/**
+ * Extended statistic computation on a set of values. Have Median, First quartile, Third quartile.
+ */
+public class ExtendedSampleImpl extends ExtendedSample implements DataRow, DataHeader {
+  private static final int INITIAL_CAPACITY = 16;
+  private static final int INCREMENT        = 0;
+
+  @Nonnull
+  protected double[] samples  = new double[INITIAL_CAPACITY];
+  @Nonnegative
+  protected int      count    = 0;
+  private   double   total;
+  private   boolean  isSorted = true;
+
+  @Nonnegative
+  private final int increment;
+
+  public ExtendedSampleImpl(@Nonnull StatisticId<? extends Statistic> id) {
+    super(id);
+
+    this.increment = INCREMENT;
+  }
+
+  @Override
+  public synchronized void add(double value) {
+    ensureCapacity(count);
+
+    samples[count++] = value;
+    total += value;
+    isSorted = false;
+  }
+
+  @Override
+  @Nonnegative
+  public int getCount() {
+    return count;
+  }
+
+  @Override
+  public double getTotal() {
+    return total;
+  }
+
+  @Override
+  public synchronized double getMin() {
+    ensureSorted();
+    return samples[0];
+  }
+
+  @Override
+  public synchronized double getAverage() {
+    return total / count;
+  }
+
+  @Override
+  public synchronized double getMax() {
+    ensureSorted();
+    return samples[count];
+  }
+
+  @Override
+  public synchronized double getFirstQuartile() {
+    return getNth(1, 4);
+  }
+
+  @Override
+  public synchronized double getMedian() {
+    return getNth(1, 2);
+  }
+
+  @Override
+  public synchronized double getThirdQuartile() {
+    return getNth(3, 4);
+  }
+
+  @Override
+  public synchronized void merge(@Nonnull Statistic statistic) {
+    ExtendedSampleImpl samples = (ExtendedSampleImpl) statistic;
+
+    synchronized (samples) {
+      ensureCapacity(count + samples.count);
+
+      System.arraycopy(samples.samples, 0, this.samples, count, samples.count);
+      count += samples.count;
+      total += samples.total;
+      isSorted = false;
+    }
+  }
+
+  private void ensureSorted() {
+    if (!isSorted) {
+      Arrays.sort(samples, 0, count);
+      isSorted = true;
+    }
+  }
+
+  private void ensureCapacity (@Nonnegative int index) {
+    if (index >= samples.length) {
+      int newLength;
+
+      if (increment <= 0) {
+        newLength = samples.length * 2 + 1;
+      } else {
+        newLength = samples.length + increment;
+      }
+
+      double[] newArray = new double[newLength];
+      System.arraycopy(samples, 0, newArray, 0, count);
+
+      samples = newArray;
+    }
+  }
+
+  private double getNth(int n, int d) {
+    ensureSorted();
+
+    if (count == 0) {
+      return Double.NaN;
+    }
+
+    if (count == 1) {
+      return samples[0];
+    }
+
+    double pos   = (double) (n * (count + 1)) / (double) d;
+
+    if (pos < 1.0) {
+      return samples[0];
+    }
+
+    double floor = Math.floor(pos);
+    double diff  = pos - floor;
+    double vLow  = samples[(int) pos - 1];
+
+    if (diff == 0) {
+      return vLow;
+    } else {
+      double vHigh = samples[(int) pos];
+      return vLow + diff * (vHigh - vLow);
+    }
+  }
+
+  @Override
+  @Nonnull
+  public synchronized Iterator<Object> iterator() {
+    ensureSorted();
+
+    return Iterators.<Object>forArray(
+           Long.valueOf(getCount()),
+           Double.valueOf(getTotal()),
+           Double.valueOf(getMin()),
+           Double.valueOf(getAverage()),
+           Double.valueOf(getFirstQuartile()),
+           Double.valueOf(getMedian()),
+           Double.valueOf(getThirdQuartile()),
+           Double.valueOf(getMax()));
+  }
+}
diff --git a/sched/src/com/android/sched/util/log/stats/ObjectAlloc.java b/sched/src/com/android/sched/util/log/stats/ObjectAlloc.java
index ed57ae4..eb547a2 100644
--- a/sched/src/com/android/sched/util/log/stats/ObjectAlloc.java
+++ b/sched/src/com/android/sched/util/log/stats/ObjectAlloc.java
@@ -46,52 +46,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Object count";
-      case 1:
-        return "Object size";
-      case 2:
-        return "Total size";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      case 1:
-        return "number";
-      case 2:
-        return "number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public String getDescription() {
     return "Object allocation";
   }
diff --git a/sched/src/com/android/sched/util/log/stats/ObjectAllocImpl.java b/sched/src/com/android/sched/util/log/stats/ObjectAllocImpl.java
index 3f511d4..eb0f887 100644
--- a/sched/src/com/android/sched/util/log/stats/ObjectAllocImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/ObjectAllocImpl.java
@@ -18,7 +18,6 @@
 
 import com.google.common.collect.Iterators;
 
-import com.android.sched.util.log.tracer.probe.MemoryBytesProbe;
 import com.android.sched.util.table.DataHeader;
 import com.android.sched.util.table.DataRow;
 
@@ -71,38 +70,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public synchronized Object getValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.valueOf(number);
-      case 1:
-        return Long.valueOf(size);
-      case 2:
-        return Long.valueOf(size * number);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public synchronized String getHumanReadableValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.toString(number);
-      case 1:
-        return MemoryBytesProbe.formatBytes(size);
-      case 2:
-        return MemoryBytesProbe.formatBytes(size * number);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public synchronized Iterator<Object> iterator() {
     return Iterators.<Object> forArray(
         Long.valueOf(number),
diff --git a/sched/src/com/android/sched/util/log/stats/Percent.java b/sched/src/com/android/sched/util/log/stats/Percent.java
index 86096c7..f36cd47 100644
--- a/sched/src/com/android/sched/util/log/stats/Percent.java
+++ b/sched/src/com/android/sched/util/log/stats/Percent.java
@@ -40,6 +40,15 @@
   public void add(boolean value) {
   }
 
+  public void removeTrue() {
+  }
+
+  public void removeFalse() {
+  }
+
+  public void remove(boolean value) {
+  }
+
   public double getPercent() {
     return Double.NaN;
   }
@@ -50,52 +59,6 @@
 
   @Override
   @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Percent";
-      case 1:
-        return "Number";
-      case 2:
-        return "Total";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      case 1:
-        return "number";
-      case 2:
-        return "number";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
   public String getDescription() {
     return "Percent";
   }
diff --git a/sched/src/com/android/sched/util/log/stats/PercentImpl.java b/sched/src/com/android/sched/util/log/stats/PercentImpl.java
index 7f02617..99f3916 100644
--- a/sched/src/com/android/sched/util/log/stats/PercentImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/PercentImpl.java
@@ -20,10 +20,8 @@
 
 import com.android.sched.util.table.DataRow;
 
-import java.text.NumberFormat;
 import java.util.Iterator;
 
-import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
 
 
@@ -59,7 +57,31 @@
   }
 
   @Override
+  public synchronized void removeTrue() {
+    this.numTrue--;
+    this.total--;
+  }
+
+  @Override
+  public synchronized void removeFalse() {
+    this.total--;
+  }
+
+  @Override
+  public synchronized void remove(boolean value) {
+    if (value) {
+      removeTrue();
+    } else {
+      removeFalse();
+    }
+  }
+
+  @Override
   public synchronized double getPercent() {
+    if (numTrue < 0 || total < 0) {
+      return Double.NaN;
+    }
+
     return (double ) numTrue / (double) total;
   }
 
@@ -73,54 +95,6 @@
     }
   }
 
-  @Override
-  @Nonnull
-  @Deprecated
-  public synchronized Object getValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Double.valueOf((double ) numTrue / (double) total);
-      case 1:
-        return Long.valueOf(numTrue);
-      case 2:
-        return Long.valueOf(total);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Override
-  @Nonnull
-  @Deprecated
-  public synchronized String getHumanReadableValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        if (total == 0) {
-          return notANumber;
-        } else {
-          return formatter.format((double) numTrue / (double) total);
-        }
-      case 1:
-        return Long.toString(numTrue);
-      case 2:
-        return Long.toString(total);
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Nonnull
-  @Deprecated
-  private static NumberFormat formatter = NumberFormat.getPercentInstance();
-  @Nonnull
-  @Deprecated
-  private static String       notANumber;
-
-  static {
-    formatter.setMinimumFractionDigits(2);
-    notANumber = formatter.format(0).replace('0', '-');
-  }
-
   @Nonnull
   @Override
   public synchronized Iterator<Object> iterator() {
diff --git a/sched/src/com/android/sched/util/log/stats/Sample.java b/sched/src/com/android/sched/util/log/stats/Sample.java
index 027074b..115fb03 100644
--- a/sched/src/com/android/sched/util/log/stats/Sample.java
+++ b/sched/src/com/android/sched/util/log/stats/Sample.java
@@ -26,7 +26,7 @@
 import javax.annotation.Nonnull;
 
 /**
- * Simple statistic computation on a set of values.
+ * Simple statistic computation on a set of values when statistic is not enabled.
  */
 public class Sample extends Statistic {
   protected Sample(@Nonnull StatisticId<? extends Statistic> id) {
@@ -41,66 +41,36 @@
     throw new AssertionError();
   }
 
-  @Override
-  @Nonnull
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
+  @Nonnegative
+  public int getCount() {
+    return 0;
   }
 
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    throw new AssertionError();
+  public double getTotal() {
+    return 0;
   }
 
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getDescription(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "Count";
-      case 1:
-        return "Total";
-      case 2:
-        return "Min";
-      case 3:
-        return "Average";
-      case 4:
-        return "Max";
-      case 5:
-        return "Min Marker";
-      case 6:
-        return "Max Marker";
-      default:
-        throw new AssertionError();
-    }
+  public double getMin() {
+    return Double.NaN;
   }
 
-  @Override
-  @Nonnull
-  @Deprecated
-  public String getType(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return "number";
-      case 1:
-        return "number";
-      case 2:
-        return "number";
-      case 3:
-        return "number";
-      case 4:
-        return "number";
-      case 5:
-        return "string";
-      case 6:
-        return "string";
-      default:
-        throw new AssertionError();
-    }
+  public double getAverage() {
+    return Double.NaN;
+  }
+
+  public double getMax() {
+    return Double.NaN;
+  }
+
+  @CheckForNull
+  public Object getMinObject() {
+    return null;
+
+  }
+
+  @CheckForNull
+  public Object getMaxObject() {
+    return null;
   }
 
   @Override
@@ -110,7 +80,7 @@
   }
 
 
-  @Nonnegative
+  @Nonnull
   private static final String[] HEADER = new String[] {
     "Count",
     "Total",
diff --git a/sched/src/com/android/sched/util/log/stats/SampleImpl.java b/sched/src/com/android/sched/util/log/stats/SampleImpl.java
index 3a51c1a..50d609b 100644
--- a/sched/src/com/android/sched/util/log/stats/SampleImpl.java
+++ b/sched/src/com/android/sched/util/log/stats/SampleImpl.java
@@ -31,7 +31,8 @@
  * Simple statistic computation on a set of values.
  */
 public class SampleImpl extends Sample implements DataRow, DataHeader {
-  private long   count;
+  @Nonnegative
+  private int    count;
 
   private double min = Double.POSITIVE_INFINITY;
   @CheckForNull
@@ -64,6 +65,46 @@
     count++;
   }
 
+
+  @Override
+  @Nonnegative
+  public int getCount() {
+    return count;
+  }
+
+  @Override
+  public double getTotal() {
+    return total;
+  }
+
+  @Override
+  public double getMin() {
+    return min;
+  }
+
+  @Override
+  public synchronized double getAverage() {
+    return total / count;
+  }
+
+  @Override
+  public double getMax() {
+    return max;
+  }
+
+  @Override
+  @CheckForNull
+  public Object getMinObject() {
+    return minObject;
+
+  }
+
+  @Override
+  @CheckForNull
+  public Object getMaxObject() {
+    return maxObject;
+  }
+
   @Override
   public synchronized void merge(@Nonnull Statistic statistic) {
     SampleImpl samples = (SampleImpl) statistic;
@@ -82,94 +123,14 @@
 
   @Nonnull
   @Override
-  @Deprecated
-  public Object getValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.valueOf(count);
-      case 1:
-        return Double.valueOf(total);
-      case 2:
-        if (min == Double.POSITIVE_INFINITY) {
-          return Double.valueOf(Double.MAX_VALUE);
-        } else {
-          return Double.valueOf(min);
-        }
-      case 3:
-        if (count == 0) {
-          return Long.valueOf(0);
-        } else {
-          return Double.valueOf(total / count);
-        }
-      case 4:
-        if (max == Double.NEGATIVE_INFINITY) {
-          return Double.valueOf(Double.MIN_VALUE);
-        } else {
-          return Double.valueOf(max);
-        }
-      case 5:
-        return "";
-      case 6:
-        return "";
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Nonnull
-  @Override
-  @Deprecated
-  public String getHumanReadableValue(@Nonnegative int columnIdx) {
-    switch (columnIdx) {
-      case 0:
-        return Long.toString(count);
-      case 1:
-        return Double.toString(total);
-      case 2:
-        if (min == Double.POSITIVE_INFINITY) {
-          return "--";
-        } else {
-          return Double.toString(min);
-        }
-      case 3:
-        if (count == 0) {
-          return "--";
-        } else {
-          return Double.toString(total / count);
-        }
-      case 4:
-        if (max == Double.NEGATIVE_INFINITY) {
-          return "--";
-        } else {
-            return Double.toString(max);
-        }
-      case 5:
-        if (minObject == null) {
-          return "--";
-        } else {
-          return minObject.toString();
-        }
-      case 6:
-        if (maxObject == null) {
-          return "--";
-        } else {
-          return maxObject.toString();
-        }
-      default:
-        throw new AssertionError();
-    }
-  }
-
-  @Nonnull
-  @Override
-  public Iterator<Object> iterator() {
+  public synchronized Iterator<Object> iterator() {
     return Iterators.forArray(
-        Long.valueOf(count),
-        Double.valueOf(total),
-        Double.valueOf(min),
-        Double.valueOf(total / count),
-        Double.valueOf(max),
-        minObject,
-        maxObject);
+        Integer.valueOf(getCount()),
+        Double.valueOf(getTotal()),
+        Double.valueOf(getMin()),
+        Double.valueOf(getAverage()),
+        Double.valueOf(getMax()),
+        getMinObject(),
+        getMaxObject());
   }
 }
diff --git a/sched/src/com/android/sched/util/log/stats/Statistic.java b/sched/src/com/android/sched/util/log/stats/Statistic.java
index 569d85c..93d2535 100644
--- a/sched/src/com/android/sched/util/log/stats/Statistic.java
+++ b/sched/src/com/android/sched/util/log/stats/Statistic.java
@@ -16,7 +16,12 @@
 
 package com.android.sched.util.log.stats;
 
+import com.google.common.collect.Iterators;
+
+import com.android.sched.util.codec.Formatter;
+import com.android.sched.util.codec.ToStringFormatter;
 import com.android.sched.util.table.DataHeader;
+import com.android.sched.util.table.DataRow;
 
 import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
@@ -40,22 +45,6 @@
   }
 
   @Nonnull
-  @Deprecated
-  public abstract Object getValue(@Nonnegative int columnIdx);
-
-  @Nonnull
-  @Deprecated
-  public abstract String getHumanReadableValue(@Nonnegative int columnIdx);
-
-  @Nonnull
-  @Deprecated
-  public abstract String getDescription(@Nonnegative int columnIdx);
-
-  @Nonnull
-  @Deprecated
-  public abstract String getType(@Nonnegative int columnIdx);
-
-  @Nonnull
   public abstract String getDescription();
 
   @Override
@@ -63,4 +52,43 @@
   public String toString() {
     return id.getName();
   }
+
+  //
+  // Adapter for deprecated API
+  //
+
+  @Nonnull
+  @Deprecated
+  public final String getDescription(int columnIdx) {
+    return getHeader()[columnIdx];
+  }
+
+  @Nonnull
+  @Deprecated
+  public final String getType(int columnIdx) {
+    if (getFormatters()[columnIdx] instanceof ToStringFormatter) {
+      return "string";
+    } else {
+      return "number";
+    }
+  }
+
+  @Nonnull
+  @Deprecated
+  public final Object getValue(@Nonnegative int columnIdx) {
+    if (this instanceof DataRow) {
+      DataRow data = (DataRow) this;
+
+      return Iterators.get(data.iterator(), columnIdx);
+    }
+
+    throw new AssertionError();
+  }
+
+  @SuppressWarnings("unchecked")
+  @Nonnull
+  @Deprecated
+  public final String getHumanReadableValue(@Nonnegative int columnIdx) {
+    return ((Formatter<Object>) (getFormatters()[columnIdx])).formatValue(getValue(columnIdx));
+  }
 }
diff --git a/sched/src/com/android/sched/util/log/stats/StatisticId.java b/sched/src/com/android/sched/util/log/stats/StatisticId.java
index c6f0fe5..597a5a3 100644
--- a/sched/src/com/android/sched/util/log/stats/StatisticId.java
+++ b/sched/src/com/android/sched/util/log/stats/StatisticId.java
@@ -18,12 +18,8 @@
 
 import com.android.sched.util.config.ReflectFactory;
 
-import java.util.ArrayList;
 import java.util.Collection;
-import java.util.Collections;
-import java.util.HashSet;
 import java.util.Map;
-import java.util.Set;
 import java.util.concurrent.ConcurrentHashMap;
 
 import javax.annotation.Nonnull;
@@ -35,9 +31,6 @@
  */
 public class StatisticId<T extends Statistic> {
   @Nonnull
-  private static Set<StatisticId<? extends Statistic>> ids =
-      Collections.synchronizedSet(new HashSet<StatisticId<? extends Statistic>>());
-  @Nonnull
   private static Map<Class<? extends Statistic>, Statistic> dummies =
       new ConcurrentHashMap<Class<? extends Statistic>, Statistic>();
   @Nonnull
@@ -70,8 +63,6 @@
       dummies.put(dummyClass, newDummyInstance());
       regulars.put(dummyClass, regularClass);
     }
-
-    ids.add(this);
   }
 
   @Nonnull
@@ -96,12 +87,6 @@
 
   @Nonnull
   @Deprecated
-  public static synchronized Collection<StatisticId<? extends Statistic>> getIds() {
-    return new ArrayList<StatisticId<? extends Statistic>>(ids);
-  }
-
-  @Nonnull
-  @Deprecated
   public static synchronized Collection<? extends Statistic> getDummies() {
     return dummies.values();
   }
diff --git a/sched/src/com/android/sched/util/log/tracer/DynamicEventType.java b/sched/src/com/android/sched/util/log/tracer/DynamicEventType.java
index 2f2ca1b..c9f43ca 100644
--- a/sched/src/com/android/sched/util/log/tracer/DynamicEventType.java
+++ b/sched/src/com/android/sched/util/log/tracer/DynamicEventType.java
@@ -16,7 +16,6 @@
 
 package com.android.sched.util.log.tracer;
 
-import com.android.sched.util.Colors;
 import com.android.sched.util.log.EventType;
 
 import javax.annotation.Nonnull;
@@ -26,19 +25,10 @@
  */
 class DynamicEventType implements EventType {
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
    DynamicEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = Colors.getCssColor(Colors.getRandomPastel(name.hashCode()));
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/sched/src/com/android/sched/util/log/tracer/TracerEventType.java b/sched/src/com/android/sched/util/log/tracer/TracerEventType.java
index 59d825d..3558a45 100644
--- a/sched/src/com/android/sched/util/log/tracer/TracerEventType.java
+++ b/sched/src/com/android/sched/util/log/tracer/TracerEventType.java
@@ -24,24 +24,16 @@
  * Represents a type of event whose performance is tracked.
  */
 public enum TracerEventType implements EventType {
-  OVERHEAD("Tracer overhead", "Plum"),
-  NOEVENT("No Event", "Black"),
-  NOTYPE("Not a Type", "Black");
+  OVERHEAD("Tracer overhead"),
+  NOEVENT("No Event"),
+  SINGLETON("Singleton event"),
+  NOTYPE("Not a Type");
 
   @Nonnull
-  private final String cssColor;
-  @Nonnull
   private final String name;
 
-  TracerEventType(@Nonnull String name, @Nonnull String cssColor) {
+  TracerEventType(@Nonnull String name) {
     this.name = name;
-    this.cssColor = cssColor;
-  }
-
-  @Override
-  @Nonnull
-  public String getColor() {
-    return cssColor;
   }
 
   @Override
diff --git a/sched/src/com/android/sched/util/log/tracer/watcher/AllocationWatcher.java b/sched/src/com/android/sched/util/log/tracer/watcher/AllocationWatcher.java
index 09a8e18..78fd9b8 100644
--- a/sched/src/com/android/sched/util/log/tracer/watcher/AllocationWatcher.java
+++ b/sched/src/com/android/sched/util/log/tracer/watcher/AllocationWatcher.java
@@ -22,23 +22,17 @@
 import com.android.sched.util.log.TracerFactory;
 import com.android.sched.util.log.stats.Alloc;
 import com.android.sched.util.log.stats.AllocImpl;
-import com.android.sched.util.log.stats.ArrayAlloc;
-import com.android.sched.util.log.stats.ArrayAllocImpl;
-import com.android.sched.util.log.stats.ObjectAlloc;
-import com.android.sched.util.log.stats.ObjectAllocImpl;
 import com.android.sched.util.log.stats.Statistic;
 import com.android.sched.util.log.stats.StatisticId;
 
 import java.util.Iterator;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
 
 import javax.annotation.CheckForNull;
 import javax.annotation.Nonnegative;
 import javax.annotation.Nonnull;
 
 /**
- * Class to watch {@link Object} creation.
+ * Class to watch {@link Object} creation and make a global statistic about allocation.
  */
 public class AllocationWatcher implements ObjectWatcher<Object> {
   static class Statistics implements ObjectWatcher.Statistics {
@@ -54,14 +48,6 @@
       "Total object and array allocations",
       AllocImpl.class, Alloc.class);
 
-  @Nonnull
-  private static final Map<Class<?>, StatisticId<ObjectAlloc>> objectStats =
-      new ConcurrentHashMap<Class<?>, StatisticId<ObjectAlloc>>();
-
-  @Nonnull
-  private static final Map<Class<?>, StatisticId<ArrayAlloc>> arrayStats =
-      new ConcurrentHashMap<Class<?>, StatisticId<ArrayAlloc>>();
-
   @Override
   public boolean notifyInstantiation(
       @Nonnull Object object, @Nonnegative long size, int count, @Nonnull EventType notUsed) {
@@ -77,46 +63,19 @@
   }
 
   private void notifyObject(@Nonnull Class<?> type, @Nonnegative long size) {
-    synchronized (AllocationWatcher.class) {
-      StatisticId<ObjectAlloc> id = objectStats.get(type);
-      if (id == null) {
-        String name = type.getName();
-
-        id = new StatisticId<ObjectAlloc>("jack.allocation.object." + name,
-            "Object allocation of type " + type.getName(), ObjectAllocImpl.class,
-            ObjectAlloc.class);
-        objectStats.put(type, id);
-      }
-
-      try {
-        Tracer tracer = TracerFactory.getTracer();
-        tracer.getStatistic(id).recordObjectAllocation(size);
-        tracer.getStatistic(ALLOCATIONS).recordAllocation(size);
-      } catch (RuntimeException e) {
-        e.printStackTrace();
-      }
+    try {
+      TracerFactory.getTracer().getStatistic(ALLOCATIONS).recordAllocation(size);
+    } catch (RuntimeException e) {
+      // Do best effort here
     }
   }
 
   private synchronized void notifyArray(@Nonnull Class<?> type, @Nonnegative long size,
       @Nonnegative int count) {
-    synchronized (AllocationWatcher.class) {
-      StatisticId<ArrayAlloc> id = arrayStats.get(type);
-      if (id == null) {
-        String name = type.getName();
-
-        id = new StatisticId<ArrayAlloc>("jack.allocation.array." + name,
-            "Array allocation of type " + type.getName(), ArrayAllocImpl.class, ArrayAlloc.class);
-        arrayStats.put(type, id);
-      }
-
-      try {
-        Tracer tracer = TracerFactory.getTracer();
-        tracer.getStatistic(id).recordObjectAllocation(count, size);
-        tracer.getStatistic(ALLOCATIONS).recordAllocation(size);
-      } catch (RuntimeException e) {
-        e.printStackTrace();
-      }
+    try {
+      TracerFactory.getTracer().getStatistic(ALLOCATIONS).recordAllocation(size);
+    } catch (RuntimeException e) {
+      // Do best effort here
     }
   }
 
diff --git a/sched/src/com/android/sched/util/log/tracer/watcher/DetailedAllocationWatcher.java b/sched/src/com/android/sched/util/log/tracer/watcher/DetailedAllocationWatcher.java
new file mode 100644
index 0000000..f8a97e3
--- /dev/null
+++ b/sched/src/com/android/sched/util/log/tracer/watcher/DetailedAllocationWatcher.java
@@ -0,0 +1,132 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.util.log.tracer.watcher;
+
+import com.android.sched.util.codec.ImplementationName;
+import com.android.sched.util.log.EventType;
+import com.android.sched.util.log.Tracer;
+import com.android.sched.util.log.TracerFactory;
+import com.android.sched.util.log.stats.ArrayAlloc;
+import com.android.sched.util.log.stats.ArrayAllocImpl;
+import com.android.sched.util.log.stats.ObjectAlloc;
+import com.android.sched.util.log.stats.ObjectAllocImpl;
+import com.android.sched.util.log.stats.Statistic;
+import com.android.sched.util.log.stats.StatisticId;
+
+import java.util.Iterator;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+import javax.annotation.CheckForNull;
+import javax.annotation.Nonnegative;
+import javax.annotation.Nonnull;
+
+/**
+ * Class to watch {@link Object} creation and make detailed statistics about allocation.
+ */
+public class DetailedAllocationWatcher implements ObjectWatcher<Object> {
+  static class Statistics implements ObjectWatcher.Statistics {
+    @Override
+    public Iterator<Statistic> iterator() {
+      throw new AssertionError();
+    }
+  }
+
+  @Nonnull
+  private static final Map<Class<?>, StatisticId<ObjectAlloc>> objectStats =
+      new ConcurrentHashMap<Class<?>, StatisticId<ObjectAlloc>>();
+
+  @Nonnull
+  private static final Map<Class<?>, StatisticId<ArrayAlloc>> arrayStats =
+      new ConcurrentHashMap<Class<?>, StatisticId<ArrayAlloc>>();
+
+  @Override
+  public boolean notifyInstantiation(
+      @Nonnull Object object, @Nonnegative long size, int count, @Nonnull EventType notUsed) {
+    Class<?> type = object.getClass();
+
+    if (count == -1) {
+      notifyObject(type, size);
+    } else {
+      notifyArray(type, size, count);
+    }
+
+    return false;
+  }
+
+  private void notifyObject(@Nonnull Class<?> type, @Nonnegative long size) {
+    StatisticId<ObjectAlloc> id;
+
+    synchronized (DetailedAllocationWatcher.class) {
+      id = objectStats.get(type);
+      if (id == null) {
+        String name = type.getName();
+
+        id = new StatisticId<ObjectAlloc>("jack.allocation.object." + name,
+            "Object allocation of type " + name, ObjectAllocImpl.class,
+            ObjectAlloc.class);
+        objectStats.put(type, id);
+      }
+    }
+
+    try {
+      TracerFactory.getTracer().getStatistic(id).recordObjectAllocation(size);
+    } catch (RuntimeException e) {
+      // Do best effort here
+    }
+  }
+
+  private synchronized void notifyArray(@Nonnull Class<?> type, @Nonnegative long size,
+      @Nonnegative int count) {
+    StatisticId<ArrayAlloc> id;
+
+    synchronized (DetailedAllocationWatcher.class) {
+      id = arrayStats.get(type);
+      if (id == null) {
+        String name = type.getName();
+
+        id = new StatisticId<ArrayAlloc>("jack.allocation.array." + name,
+            "Array allocation of type " + name, ArrayAllocImpl.class, ArrayAlloc.class);
+        arrayStats.put(type, id);
+      }
+    }
+
+    try {
+      TracerFactory.getTracer().getStatistic(id).recordObjectAllocation(count, size);
+    } catch (RuntimeException e) {
+      // Do best effort here
+    }
+  }
+
+  @Override
+  @Nonnull
+  public ObjectWatcher.Statistics addSample(@Nonnull Object node,
+      @CheckForNull ObjectWatcher.Statistics raw, @Nonnull EventType type) {
+    throw new AssertionError();
+  }
+
+  /**
+   * Install a {@link DetailedAllocationWatcher}
+   */
+  @ImplementationName(iface = WatcherInstaller.class, name = "detailed-object-alloc")
+  public static class DetailedAllocationWatcherInstaller implements WatcherInstaller {
+    @Override
+    public void install(@Nonnull Tracer tracer) {
+      tracer.registerWatcher(Object.class, DetailedAllocationWatcher.class);
+    }
+  }
+}
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/sched/src/com/android/sched/vfs/AbstractVElement.java
similarity index 74%
copy from jack/src/com/android/jack/vfs/VDir.java
copy to sched/src/com/android/sched/vfs/AbstractVElement.java
index 0c967d9..939f8bc 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/sched/src/com/android/sched/vfs/AbstractVElement.java
@@ -14,18 +14,18 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
-
-import java.util.Collection;
+package com.android.sched.vfs;
 
 import javax.annotation.Nonnull;
 
 /**
- * Virtual directory.
+ * Base class for implementing VElement.
  */
-public interface VDir extends VElement {
+public abstract class AbstractVElement implements VElement {
 
   @Nonnull
-  Collection<? extends VElement> list();
-
+  @Override
+  public String toString() {
+    return getLocation().getDescription();
+  }
 }
diff --git a/jack/src/com/android/jack/vfs/VDir.java b/sched/src/com/android/sched/vfs/InputVDir.java
similarity index 90%
rename from jack/src/com/android/jack/vfs/VDir.java
rename to sched/src/com/android/sched/vfs/InputVDir.java
index 0c967d9..f57636d 100644
--- a/jack/src/com/android/jack/vfs/VDir.java
+++ b/sched/src/com/android/sched/vfs/InputVDir.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs;
 
 import java.util.Collection;
 
@@ -23,7 +23,7 @@
 /**
  * Virtual directory.
  */
-public interface VDir extends VElement {
+public interface InputVDir extends VElement {
 
   @Nonnull
   Collection<? extends VElement> list();
diff --git a/jack/src/com/android/jack/vfs/VFile.java b/sched/src/com/android/sched/vfs/InputVFile.java
similarity index 90%
rename from jack/src/com/android/jack/vfs/VFile.java
rename to sched/src/com/android/sched/vfs/InputVFile.java
index a948b2d..3d7d2cd 100644
--- a/jack/src/com/android/jack/vfs/VFile.java
+++ b/sched/src/com/android/sched/vfs/InputVFile.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs;
 
 import java.io.IOException;
 import java.io.InputStream;
@@ -24,7 +24,7 @@
 /**
  * Virtual file.
  */
-public interface VFile extends VElement {
+public interface InputVFile extends VElement {
 
   @Nonnull
   InputStream openRead() throws IOException;
diff --git a/jack/src/com/android/jack/vfs/VFile.java b/sched/src/com/android/sched/vfs/OutputVDir.java
similarity index 78%
copy from jack/src/com/android/jack/vfs/VFile.java
copy to sched/src/com/android/sched/vfs/OutputVDir.java
index a948b2d..622c553 100644
--- a/jack/src/com/android/jack/vfs/VFile.java
+++ b/sched/src/com/android/sched/vfs/OutputVDir.java
@@ -14,19 +14,18 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs;
 
 import java.io.IOException;
-import java.io.InputStream;
 
 import javax.annotation.Nonnull;
 
 /**
- * Virtual file.
+ * Virtual directory to write to.
  */
-public interface VFile extends VElement {
+public interface OutputVDir extends VElement {
 
   @Nonnull
-  InputStream openRead() throws IOException;
+  OutputVFile createOutputVFile(@Nonnull String filePath) throws IOException;
 
 }
diff --git a/jack/src/com/android/jack/vfs/VFile.java b/sched/src/com/android/sched/vfs/OutputVFile.java
similarity index 78%
copy from jack/src/com/android/jack/vfs/VFile.java
copy to sched/src/com/android/sched/vfs/OutputVFile.java
index a948b2d..32154b5 100644
--- a/jack/src/com/android/jack/vfs/VFile.java
+++ b/sched/src/com/android/sched/vfs/OutputVFile.java
@@ -14,19 +14,19 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs;
 
 import java.io.IOException;
-import java.io.InputStream;
+import java.io.OutputStream;
 
 import javax.annotation.Nonnull;
 
 /**
- * Virtual file.
+ * Virtual file to write to.
  */
-public interface VFile extends VElement {
+public interface OutputVFile extends VElement {
 
   @Nonnull
-  InputStream openRead() throws IOException;
+  OutputStream openWrite() throws IOException;
 
 }
diff --git a/jack/src/com/android/jack/vfs/VElement.java b/sched/src/com/android/sched/vfs/VElement.java
similarity index 96%
rename from jack/src/com/android/jack/vfs/VElement.java
rename to sched/src/com/android/sched/vfs/VElement.java
index d4420a6..748b9bd 100644
--- a/jack/src/com/android/jack/vfs/VElement.java
+++ b/sched/src/com/android/sched/vfs/VElement.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs;
 
 import com.android.sched.util.config.Location;
 
diff --git a/jack/src/com/android/jack/vfs/direct/DirectDir.java b/sched/src/com/android/sched/vfs/direct/InputDirectDir.java
similarity index 75%
rename from jack/src/com/android/jack/vfs/direct/DirectDir.java
rename to sched/src/com/android/sched/vfs/direct/InputDirectDir.java
index 4144729..4e88043 100644
--- a/jack/src/com/android/jack/vfs/direct/DirectDir.java
+++ b/sched/src/com/android/sched/vfs/direct/InputDirectDir.java
@@ -14,14 +14,15 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs.direct;
+package com.android.sched.vfs.direct;
 
-import com.android.jack.JackIOException;
-import com.android.jack.vfs.VDir;
-import com.android.jack.vfs.VElement;
+import com.android.sched.util.ConcurrentIOException;
 import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.file.NotFileOrDirectoryException;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.InputVDir;
+import com.android.sched.vfs.VElement;
 
 import java.io.File;
 import java.util.ArrayList;
@@ -34,14 +35,14 @@
 /**
  * Directory in the file system.
  */
-public class DirectDir implements VDir {
+public class InputDirectDir extends AbstractVElement implements InputVDir {
 
   @Nonnull
   private final File dir;
   @CheckForNull
   private ArrayList<VElement> list;
 
-  public DirectDir(@Nonnull File dir) throws NotFileOrDirectoryException {
+  public InputDirectDir(@Nonnull File dir) throws NotFileOrDirectoryException {
     if (!dir.isDirectory()) {
       throw new NotFileOrDirectoryException(dir.getAbsolutePath(), false);
     }
@@ -60,7 +61,7 @@
     if (list == null) {
       File[] subs = dir.listFiles();
       if (subs == null) {
-        throw new JackIOException("Failed to list content of '" + dir.getAbsolutePath() + "'");
+        throw new ConcurrentIOException(new ListDirException(dir));
       }
       if (subs.length == 0) {
         return Collections.emptyList();
@@ -70,14 +71,12 @@
       for (File sub : subs) {
         try {
           if (sub.isFile()) {
-            list.add(new DirectFile(sub));
+            list.add(new InputDirectFile(sub));
           } else {
-            list.add(new DirectDir(sub));
+            list.add(new InputDirectDir(sub));
           }
         } catch (NotFileOrDirectoryException e) {
-          AssertionError ae = new AssertionError();
-          ae.initCause(e);
-          throw ae;
+          throw new ConcurrentIOException(e);
         }
       }
     }
@@ -86,12 +85,6 @@
     return list;
   }
 
-  @Nonnull
-  @Override
-  public String toString() {
-    return dir.getPath();
-  }
-
   @Override
   @Nonnull
   public Location getLocation() {
diff --git a/jack/src/com/android/jack/vfs/direct/DirectFile.java b/sched/src/com/android/sched/vfs/direct/InputDirectFile.java
similarity index 83%
rename from jack/src/com/android/jack/vfs/direct/DirectFile.java
rename to sched/src/com/android/sched/vfs/direct/InputDirectFile.java
index 8464183..45ae9ab 100644
--- a/jack/src/com/android/jack/vfs/direct/DirectFile.java
+++ b/sched/src/com/android/sched/vfs/direct/InputDirectFile.java
@@ -14,12 +14,13 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs.direct;
+package com.android.sched.vfs.direct;
 
-import com.android.jack.vfs.VFile;
 import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.file.NotFileOrDirectoryException;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.InputVFile;
 
 import java.io.File;
 import java.io.FileInputStream;
@@ -31,12 +32,12 @@
 /**
  * A {@code VFile} directly backed but a {@code java.io.File}.
  */
-public class DirectFile implements VFile {
+public class InputDirectFile extends AbstractVElement implements InputVFile {
 
   @Nonnull
   private final File file;
 
-  public DirectFile(@Nonnull File file) throws NotFileOrDirectoryException {
+  public InputDirectFile(@Nonnull File file) throws NotFileOrDirectoryException {
     if (!file.isFile()) {
       throw new NotFileOrDirectoryException(file.getAbsolutePath(), true);
     }
@@ -55,12 +56,6 @@
     return file.getName();
   }
 
-  @Nonnull
-  @Override
-  public String toString() {
-    return file.getPath();
-  }
-
   @Override
   @Nonnull
   public Location getLocation() {
diff --git a/jack/src/com/android/jack/vfs/VFile.java b/sched/src/com/android/sched/vfs/direct/ListDirException.java
similarity index 61%
copy from jack/src/com/android/jack/vfs/VFile.java
copy to sched/src/com/android/sched/vfs/direct/ListDirException.java
index a948b2d..802c9d4 100644
--- a/jack/src/com/android/jack/vfs/VFile.java
+++ b/sched/src/com/android/sched/vfs/direct/ListDirException.java
@@ -14,19 +14,28 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs;
+package com.android.sched.vfs.direct;
 
+import java.io.File;
 import java.io.IOException;
-import java.io.InputStream;
 
 import javax.annotation.Nonnull;
 
 /**
- * Virtual file.
+ * Thrown when listing a directory content failed.
  */
-public interface VFile extends VElement {
+public class ListDirException extends IOException {
 
+  private static final long serialVersionUID = 1L;
   @Nonnull
-  InputStream openRead() throws IOException;
+  private final File dir;
 
+  public ListDirException(@Nonnull File dir) {
+    this.dir = dir;
+  }
+
+  @Override
+  public String getMessage() {
+    return "Failed to list directory content '" + dir.getPath() + "'";
+  }
 }
diff --git a/sched/src/com/android/sched/vfs/direct/OutputDirectDir.java b/sched/src/com/android/sched/vfs/direct/OutputDirectDir.java
new file mode 100644
index 0000000..58968b1
--- /dev/null
+++ b/sched/src/com/android/sched/vfs/direct/OutputDirectDir.java
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.vfs.direct;
+
+import com.android.sched.util.config.FileLocation;
+import com.android.sched.util.config.Location;
+import com.android.sched.util.file.CannotCreateFileException;
+import com.android.sched.util.file.Directory;
+import com.android.sched.util.file.FileAlreadyExistsException;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.OutputVDir;
+import com.android.sched.vfs.OutputVFile;
+
+import java.io.File;
+
+import javax.annotation.Nonnull;
+
+/**
+ * An {@link OutputVDir} using a real directory.
+ */
+public class OutputDirectDir extends AbstractVElement implements OutputVDir {
+
+  @Nonnull
+  private final File dir;
+
+  public OutputDirectDir(@Nonnull Directory dir) {
+    this.dir = dir.getFile();
+  }
+
+  @Nonnull
+  @Override
+  public String getName() {
+    return dir.getName();
+  }
+
+  @Override
+  @Nonnull
+  public Location getLocation() {
+    return new FileLocation(dir);
+  }
+
+  @Override
+  @Nonnull
+  public OutputVFile createOutputVFile(@Nonnull String filePath) throws CannotCreateFileException,
+      FileAlreadyExistsException {
+    File file = new File(dir, filePath);
+    if (!file.getParentFile().mkdirs() && !file.getParentFile().isDirectory()) {
+      throw new CannotCreateFileException(file.getParentFile().getAbsolutePath(),
+          /* isFile */ false);
+    }
+    return new OutputDirectFile(file);
+  }
+}
diff --git a/sched/src/com/android/sched/vfs/direct/OutputDirectFile.java b/sched/src/com/android/sched/vfs/direct/OutputDirectFile.java
new file mode 100644
index 0000000..58b36e9
--- /dev/null
+++ b/sched/src/com/android/sched/vfs/direct/OutputDirectFile.java
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.vfs.direct;
+
+import com.android.sched.util.config.FileLocation;
+import com.android.sched.util.config.Location;
+import com.android.sched.util.file.FileAlreadyExistsException;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.OutputVFile;
+
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.OutputStream;
+
+import javax.annotation.Nonnull;
+
+/**
+ * An {@link OutputVFile} directly backed by a {@link File} directory.
+ */
+class OutputDirectFile extends AbstractVElement implements OutputVFile {
+
+  private static boolean checkIfFileAlreadyExists = false;
+
+  @Nonnull
+  private final File file;
+
+  public OutputDirectFile(@Nonnull File file) throws FileAlreadyExistsException {
+    if (checkIfFileAlreadyExists && file.exists()) {
+      throw new FileAlreadyExistsException(file.getAbsolutePath(), !file.isDirectory());
+    }
+    this.file = file;
+  }
+
+  @Nonnull
+  @Override
+  public OutputStream openWrite() throws FileNotFoundException {
+    return new FileOutputStream(file);
+  }
+
+  @Nonnull
+  @Override
+  public String getName() {
+    return file.getPath();
+  }
+
+  @Override
+  @Nonnull
+  public Location getLocation() {
+    return new FileLocation(file);
+  }
+}
diff --git a/jack/src/com/android/jack/vfs/zip/ZipArchive.java b/sched/src/com/android/sched/vfs/zip/InputZipArchive.java
similarity index 80%
rename from jack/src/com/android/jack/vfs/zip/ZipArchive.java
rename to sched/src/com/android/sched/vfs/zip/InputZipArchive.java
index ff8ba6e..fec4e36 100644
--- a/jack/src/com/android/jack/vfs/zip/ZipArchive.java
+++ b/sched/src/com/android/sched/vfs/zip/InputZipArchive.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs.zip;
+package com.android.sched.vfs.zip;
 
 import java.io.Closeable;
 import java.io.File;
@@ -28,7 +28,7 @@
 /**
  * Virtual directory for viewing the content of a zip file.
  */
-public class ZipArchive extends ZipDir implements Closeable {
+public class InputZipArchive extends InputZipVDir implements Closeable {
 
   @Nonnull
   public static final String IN_ZIP_SEPARATOR = "/";
@@ -36,7 +36,7 @@
   @Nonnull
   private final ZipFile zip;
 
-  public ZipArchive(@Nonnull File zipFile) throws IOException {
+  public InputZipArchive(@Nonnull File zipFile) throws IOException {
     super("", zipFile, new ZipEntry(""));
 
     zip = new ZipFile(zipFile);
@@ -47,20 +47,20 @@
         String entryName = entry.getName();
         String[] names = entryName.split(IN_ZIP_SEPARATOR);
         @SuppressWarnings("resource")
-        ZipDir dir = this;
+        InputZipVDir dir = this;
         StringBuilder inZipPath = new StringBuilder();
         for (int i = 0; i < names.length - 1; i++) {
           String simpleName = names[i];
           inZipPath.append(IN_ZIP_SEPARATOR).append(simpleName);
-          ZipDir nextDir = (ZipDir) dir.subs.get(simpleName);
+          InputZipVDir nextDir = (InputZipVDir) dir.subs.get(simpleName);
           if (nextDir == null) {
-            nextDir = new ZipDir(simpleName, zipFile, new ZipEntry(inZipPath.toString()));
+            nextDir = new InputZipVDir(simpleName, zipFile, new ZipEntry(inZipPath.toString()));
             dir.subs.put(simpleName, nextDir);
           }
           dir = nextDir;
         }
         String simpleName = names[names.length - 1];
-        dir.subs.put(simpleName, new ZipVFile(simpleName, zip, entry));
+        dir.subs.put(simpleName, new InputZipVFile(simpleName, zip, entry));
       }
     }
   }
diff --git a/jack/src/com/android/jack/vfs/zip/ZipDir.java b/sched/src/com/android/sched/vfs/zip/InputZipVDir.java
similarity index 81%
rename from jack/src/com/android/jack/vfs/zip/ZipDir.java
rename to sched/src/com/android/sched/vfs/zip/InputZipVDir.java
index 801f207..7ad1cc5 100644
--- a/jack/src/com/android/jack/vfs/zip/ZipDir.java
+++ b/sched/src/com/android/sched/vfs/zip/InputZipVDir.java
@@ -14,13 +14,14 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs.zip;
+package com.android.sched.vfs.zip;
 
-import com.android.jack.vfs.VDir;
-import com.android.jack.vfs.VElement;
 import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.config.ZipLocation;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.InputVDir;
+import com.android.sched.vfs.VElement;
 
 import java.io.File;
 import java.util.Collection;
@@ -29,7 +30,7 @@
 
 import javax.annotation.Nonnull;
 
-class ZipDir implements VDir {
+class InputZipVDir extends AbstractVElement implements InputVDir {
 
   @Nonnull
   protected final HashMap<String, VElement> subs = new HashMap<String, VElement>();
@@ -39,7 +40,7 @@
   @Nonnull
   private final Location location;
 
-  ZipDir(@Nonnull String name, @Nonnull File zip, @Nonnull ZipEntry entry) {
+  InputZipVDir(@Nonnull String name, @Nonnull File zip, @Nonnull ZipEntry entry) {
     this.name = name;
     this.location = new ZipLocation(new FileLocation(zip), entry);
   }
@@ -56,12 +57,6 @@
     return subs.values();
   }
 
-  @Nonnull
-  @Override
-  public String toString() {
-    return location.getDescription();
-  }
-
   @Override
   @Nonnull
   public Location getLocation() {
diff --git a/jack/src/com/android/jack/vfs/zip/ZipVFile.java b/sched/src/com/android/sched/vfs/zip/InputZipVFile.java
similarity index 83%
rename from jack/src/com/android/jack/vfs/zip/ZipVFile.java
rename to sched/src/com/android/sched/vfs/zip/InputZipVFile.java
index f2f1c62..090dc2f 100644
--- a/jack/src/com/android/jack/vfs/zip/ZipVFile.java
+++ b/sched/src/com/android/sched/vfs/zip/InputZipVFile.java
@@ -14,12 +14,13 @@
  * limitations under the License.
  */
 
-package com.android.jack.vfs.zip;
+package com.android.sched.vfs.zip;
 
-import com.android.jack.vfs.VFile;
 import com.android.sched.util.config.FileLocation;
 import com.android.sched.util.config.Location;
 import com.android.sched.util.config.ZipLocation;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.InputVFile;
 
 import java.io.File;
 import java.io.IOException;
@@ -29,7 +30,7 @@
 
 import javax.annotation.Nonnull;
 
-class ZipVFile implements VFile {
+class InputZipVFile extends AbstractVElement implements InputVFile {
 
   @Nonnull
   private final String name;
@@ -38,7 +39,7 @@
   @Nonnull
   private final ZipEntry entry;
 
-  ZipVFile(@Nonnull String name, @Nonnull ZipFile zip, @Nonnull ZipEntry entry) {
+  InputZipVFile(@Nonnull String name, @Nonnull ZipFile zip, @Nonnull ZipEntry entry) {
     this.name = name;
     this.zip = zip;
     this.entry = entry;
@@ -56,12 +57,6 @@
     return zip.getInputStream(entry);
   }
 
-  @Nonnull
-  @Override
-  public String toString() {
-    return name;
-  }
-
   @Override
   @Nonnull
   public Location getLocation() {
diff --git a/sched/src/com/android/sched/vfs/zip/OutputZipRootVDir.java b/sched/src/com/android/sched/vfs/zip/OutputZipRootVDir.java
new file mode 100644
index 0000000..b1b6ae1
--- /dev/null
+++ b/sched/src/com/android/sched/vfs/zip/OutputZipRootVDir.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.vfs.zip;
+
+import com.android.sched.util.config.FileLocation;
+import com.android.sched.util.config.Location;
+import com.android.sched.util.config.ZipLocation;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.OutputVDir;
+import com.android.sched.vfs.OutputVFile;
+import com.android.sched.vfs.VElement;
+
+import java.io.Closeable;
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipOutputStream;
+
+import javax.annotation.Nonnull;
+
+/**
+ * A root {@link OutputVDir} backed by a zip archive.
+ */
+public class OutputZipRootVDir extends AbstractVElement implements OutputVDir, Closeable {
+
+  @Nonnull
+  protected final HashMap<String, VElement> subs = new HashMap<String, VElement>();
+  @Nonnull
+  private final Location location;
+  @Nonnull
+  protected final ZipOutputStream zos;
+  @Nonnull
+  private final File zipFile;
+
+  public OutputZipRootVDir(@Nonnull File zipFile) throws FileNotFoundException {
+    this.zipFile = zipFile;
+    location = new ZipLocation(new FileLocation(zipFile), new ZipEntry(""));
+    zos = new ZipOutputStream(new FileOutputStream(zipFile));
+  }
+
+  @Nonnull
+  @Override
+  public String getName() {
+    return zipFile.getName();
+  }
+
+  @Override
+  @Nonnull
+  public Location getLocation() {
+    return location;
+  }
+
+  @Override
+  @Nonnull
+  public OutputVFile createOutputVFile(@Nonnull String filePath) {
+    return new OutputZipVFile(zos, new ZipEntry(filePath), zipFile);
+  }
+
+  @Override
+  public void close() throws IOException {
+    zos.close();
+  }
+}
diff --git a/sched/src/com/android/sched/vfs/zip/OutputZipVFile.java b/sched/src/com/android/sched/vfs/zip/OutputZipVFile.java
new file mode 100644
index 0000000..afee54d
--- /dev/null
+++ b/sched/src/com/android/sched/vfs/zip/OutputZipVFile.java
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.sched.vfs.zip;
+
+import com.android.sched.util.config.FileLocation;
+import com.android.sched.util.config.Location;
+import com.android.sched.util.config.ZipLocation;
+import com.android.sched.util.stream.UncloseableOutputStream;
+import com.android.sched.vfs.AbstractVElement;
+import com.android.sched.vfs.OutputVFile;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipOutputStream;
+
+import javax.annotation.Nonnull;
+
+class OutputZipVFile extends AbstractVElement implements OutputVFile {
+
+  @Nonnull
+  private final ZipOutputStream zos;
+  @Nonnull
+  private final ZipEntry entry;
+  @Nonnull
+  private final Location location;
+
+  OutputZipVFile(@Nonnull ZipOutputStream zos, @Nonnull ZipEntry entry, @Nonnull File zipFile) {
+    this.zos = zos;
+    this.entry = entry;
+    location = new ZipLocation(new FileLocation(zipFile), entry);
+  }
+
+  @Nonnull
+  @Override
+  public String getName() {
+    return entry.getName();
+  }
+
+  @Nonnull
+  @Override
+  public OutputStream openWrite() throws IOException {
+    zos.putNextEntry(entry);
+    return new UncloseableOutputStream(zos);
+  }
+
+  @Override
+  @Nonnull
+  public Location getLocation() {
+    return location;
+  }
+
+}