Reformat Java bindings.
This commit is contained in:
@@ -86,7 +86,7 @@ template = {
|
||||
's390x.h' : 'S390x',
|
||||
'tricore.h' : 'TriCore',
|
||||
'unicorn.h': 'Unicorn',
|
||||
'comment_open': '//',
|
||||
'comment_open': ' //',
|
||||
'comment_close': '',
|
||||
},
|
||||
'dotnet': {
|
||||
|
||||
399
bindings/java/eclipse-formatter.xml
Normal file
399
bindings/java/eclipse-formatter.xml
Normal file
@@ -0,0 +1,399 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<profiles version="22">
|
||||
<profile kind="CodeFormatterProfile" name="EclipseFormatter" version="22">
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_for_statment" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indentation.size" value="4"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_enum_constant_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_with_spaces" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_before_code_block" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_switch_case_expressions" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="@formatter:on"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.count_line_length_from_starting_position" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_record_components" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_multiplicative_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameterized_type_references" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_logical_operator" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_annotation_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_enum_constant" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_multiplicative_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_abstract_method" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_enum_constant_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_variable_declarations_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_catch_clause" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiplicative_operator" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_anonymous_type_declaration_on_one_line" value="one_line_if_empty"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_switch_case_expressions" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_shift_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_code_block" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_bitwise_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_parameters" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_loops" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_for_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_switch_case_arrow_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_annotation" value="separate_lines_if_wrapped"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_enum_constant" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.text_block_indentation" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_module_statements" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_names_descriptions" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_if_then_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_assignment_statements_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_permitted_types" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression_chain" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_annotations" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_assertion_message_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_method_declaration" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_fields_grouping_blank_lines" value="2147483647"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_bitwise_operator" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_resources_in_try" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_not_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_type_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_delcaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_empty_lines" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_arguments" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation" value="52"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_package" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_label" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_record_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_bitwise_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_lambda_arrow" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_tag_description" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_record_constructor" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_string_concatenation" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_shift_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_shift_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_do_while_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_record_components" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_for_loop_header" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_additive_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_getter_setter_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_string_concatenation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_lambda_arrow" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_relational_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_import_groups" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_logical_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_invocation" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_record_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_switch_statement" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_default" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="@formatter:off"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="48"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_method_body" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_if_while_statement" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_switch_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_switch_case_with_arrow" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_method_body_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_loop_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_type_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_additive_operator" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_record_constructor" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_relational_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_record_declaration_on_one_line" value="one_line_if_empty"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_lambda_body" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_parameter" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_relational_operator" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_additive_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_string_concatenation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_selector_in_method_invocation_on_expression_first_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_record_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_switch_case_with_arrow_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_switch_case_with_colon" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_after_code_block" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_type" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_local_variable" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_default" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_between_different_tags" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_additive_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_field" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_conditional_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_shift_operator" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_try_clause" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_code_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_record_components" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_bitwise_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_assignment_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_switch_case_with_arrow" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_lambda_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_method" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_record_constructor_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_record_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assertion_message" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_logical_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_record_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_relational_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_last_class_body_declaration" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_while_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_logical_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_statement_group_in_switch" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_lambda_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_permitted_types" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_enum_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="end_of_line"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_multiplicative_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_code_block" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="space"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_string_concatenation" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/>
|
||||
</profile>
|
||||
</profiles>
|
||||
@@ -27,7 +27,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
import unicorn.*;
|
||||
import java.util.*;
|
||||
|
||||
|
||||
public class SampleNetworkAuditing {
|
||||
|
||||
public static long next_id = 3;
|
||||
@@ -51,62 +50,62 @@ public class SampleNetworkAuditing {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
private static class MyInterruptHook implements InterruptHook {
|
||||
// callback for tracing Linux interrupt
|
||||
public void hook(Unicorn uc, int intno, Object user) {
|
||||
// System.err.println(String.format("Interrupt 0x%x, from Unicorn 0x%x", intno, u.hashCode()));
|
||||
// System.err.println(String.format("Interrupt 0x%x, from Unicorn 0x%x", intno, u.hashCode()));
|
||||
|
||||
// only handle Linux syscall
|
||||
if (intno != 0x80) {
|
||||
return;
|
||||
}
|
||||
Long eax = (Long)uc.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
Long ebx = (Long)uc.reg_read(Unicorn.UC_X86_REG_EBX);
|
||||
Long ecx = (Long)uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
Long edx = (Long)uc.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
Long eip = (Long)uc.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
Long eax = (Long) uc.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
Long ebx = (Long) uc.reg_read(Unicorn.UC_X86_REG_EBX);
|
||||
Long ecx = (Long) uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
Long edx = (Long) uc.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
Long eip = (Long) uc.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
|
||||
// System.out.printf(">>> INTERRUPT %d\n", toInt(eax));
|
||||
|
||||
if (eax == 1) { // sys_exit
|
||||
System.out.printf(">>> SYS_EXIT\n");
|
||||
uc.emu_stop();
|
||||
}
|
||||
else if (eax == 3) { // sys_read
|
||||
} else if (eax == 3) { // sys_read
|
||||
long fd = ebx;
|
||||
long buf = ecx;
|
||||
long count = edx;
|
||||
|
||||
String uuid = UUID.randomUUID().toString().substring(0, 32);
|
||||
|
||||
byte[] dummy_content = Arrays.copyOfRange(uuid.getBytes(), 0, (int)Math.min(count, uuid.length()));
|
||||
byte[] dummy_content = Arrays.copyOfRange(uuid.getBytes(), 0,
|
||||
(int) Math.min(count, uuid.length()));
|
||||
uc.mem_write(buf, dummy_content);
|
||||
|
||||
String msg = String.format("read %d bytes from fd(%d) with dummy_content(%s)", count, fd, uuid.substring(0, dummy_content.length));
|
||||
String msg = String.format(
|
||||
"read %d bytes from fd(%d) with dummy_content(%s)", count,
|
||||
fd, uuid.substring(0, dummy_content.length));
|
||||
|
||||
fd_chains.add_log(fd, msg);
|
||||
System.out.printf(">>> %s\n", msg);
|
||||
}
|
||||
else if (eax == 4) { // sys_write
|
||||
} else if (eax == 4) { // sys_write
|
||||
long fd = ebx;
|
||||
long buf = ecx;
|
||||
long count = edx;
|
||||
|
||||
byte[] content = uc.mem_read(buf, count);
|
||||
|
||||
String msg = String.format("write data=%s count=%d to fd(%d)", new String(content), count, fd);
|
||||
String msg = String.format("write data=%s count=%d to fd(%d)",
|
||||
new String(content), count, fd);
|
||||
|
||||
System.out.printf(">>> %s\n", msg);
|
||||
fd_chains.add_log(fd, msg);
|
||||
}
|
||||
else if (eax == 5) { // sys_open
|
||||
} else if (eax == 5) { // sys_open
|
||||
long filename_addr = ebx;
|
||||
long flags = ecx;
|
||||
long mode = edx;
|
||||
@@ -115,124 +114,141 @@ public class SampleNetworkAuditing {
|
||||
Long dummy_fd = get_id();
|
||||
uc.reg_write(Unicorn.UC_X86_REG_EAX, dummy_fd);
|
||||
|
||||
String msg = String.format("open file (filename=%s flags=%d mode=%d) with fd(%d)", filename, flags, mode, dummy_fd);
|
||||
String msg = String.format(
|
||||
"open file (filename=%s flags=%d mode=%d) with fd(%d)",
|
||||
filename, flags, mode, dummy_fd);
|
||||
|
||||
fd_chains.create_chain(dummy_fd);
|
||||
fd_chains.add_log(dummy_fd, msg);
|
||||
System.out.printf(">>> %s\n", msg);
|
||||
}
|
||||
else if (eax == 11) { // sys_execv
|
||||
} else if (eax == 11) { // sys_execv
|
||||
// System.out.printf(">>> ebx=0x%x, ecx=0x%x, edx=0x%x\n", ebx, ecx, edx));
|
||||
String filename = read_string(uc, ebx);
|
||||
|
||||
System.out.printf(">>> SYS_EXECV filename=%s\n", filename);
|
||||
}
|
||||
else if (eax == 63) { // sys_dup2
|
||||
} else if (eax == 63) { // sys_dup2
|
||||
fd_chains.link_fd(ecx, ebx);
|
||||
System.out.printf(">>> SYS_DUP2 oldfd=%d newfd=%d\n", ebx, ecx);
|
||||
}
|
||||
else if (eax == 102) { // sys_socketcall
|
||||
} else if (eax == 102) { // sys_socketcall
|
||||
// ref: http://www.skyfree.org/linux/kernel_network/socket.html
|
||||
Long call = (Long)uc.reg_read(Unicorn.UC_X86_REG_EBX);
|
||||
Long args = (Long)uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
Long call = (Long) uc.reg_read(Unicorn.UC_X86_REG_EBX);
|
||||
Long args = (Long) uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
|
||||
// int sys_socketcall(int call, unsigned long *args)
|
||||
if (call == 1) { // sys_socket
|
||||
// err = sys_socket(a0,a1,a[2])
|
||||
// int sys_socket(int family, int type, int protocol)
|
||||
long family = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long sock_type = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long protocol = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long sock_type =
|
||||
toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long protocol =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
|
||||
Long dummy_fd = get_id();
|
||||
uc.reg_write(Unicorn.UC_X86_REG_EAX, dummy_fd);
|
||||
|
||||
if (family == 2) { // AF_INET
|
||||
String msg = String.format("create socket (%s, %s) with fd(%d)", ADDR_FAMILY.get(family), SOCKET_TYPES.get(sock_type), dummy_fd);
|
||||
String msg =
|
||||
String.format("create socket (%s, %s) with fd(%d)",
|
||||
ADDR_FAMILY.get(family),
|
||||
SOCKET_TYPES.get(sock_type), dummy_fd);
|
||||
fd_chains.create_chain(dummy_fd);
|
||||
fd_chains.add_log(dummy_fd, msg);
|
||||
print_sockcall(msg);
|
||||
} else if (family == 3) { // AF_INET6
|
||||
}
|
||||
else if (family == 3) { // AF_INET6
|
||||
}
|
||||
}
|
||||
else if (call == 2) { // sys_bind
|
||||
} else if (call == 2) { // sys_bind
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long umyaddr = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long addrlen = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long umyaddr =
|
||||
toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long addrlen =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
|
||||
byte[] sock_addr = uc.mem_read(umyaddr, addrlen);
|
||||
|
||||
String msg = String.format("fd(%d) bind to %s", fd, parse_sock_address(sock_addr));
|
||||
String msg = String.format("fd(%d) bind to %s", fd,
|
||||
parse_sock_address(sock_addr));
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
else if (call == 3) { // sys_connect
|
||||
} else if (call == 3) { // sys_connect
|
||||
// err = sys_connect(a0, (struct sockaddr *)a1, a[2])
|
||||
// int sys_connect(int fd, struct sockaddr *uservaddr, int addrlen)
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long uservaddr = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long addrlen = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long uservaddr =
|
||||
toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long addrlen =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
|
||||
byte[] sock_addr = uc.mem_read(uservaddr, addrlen);
|
||||
String msg = String.format("fd(%d) connect to %s", fd, parse_sock_address(sock_addr));
|
||||
String msg = String.format("fd(%d) connect to %s", fd,
|
||||
parse_sock_address(sock_addr));
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
else if (call == 4) { // sys_listen
|
||||
} else if (call == 4) { // sys_listen
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long backlog = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long backlog =
|
||||
toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
|
||||
String msg = String.format("fd(%d) listened with backlog=%d", fd, backlog);
|
||||
String msg = String.format(
|
||||
"fd(%d) listened with backlog=%d", fd, backlog);
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
else if (call == 5) { // sys_accept
|
||||
} else if (call == 5) { // sys_accept
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long upeer_sockaddr = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long upeer_addrlen = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long upeer_sockaddr =
|
||||
toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long upeer_addrlen =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
|
||||
// System.out.printf(">>> upeer_sockaddr=0x%x, upeer_addrlen=%d\n" % (upeer_sockaddr, upeer_addrlen))
|
||||
|
||||
if (upeer_sockaddr == 0x0) {
|
||||
print_sockcall(String.format("fd(%d) accept client", fd));
|
||||
}
|
||||
else {
|
||||
print_sockcall(
|
||||
String.format("fd(%d) accept client", fd));
|
||||
} else {
|
||||
long upeer_len = toInt(uc.mem_read(upeer_addrlen, 4));
|
||||
|
||||
byte[] sock_addr = uc.mem_read(upeer_sockaddr, upeer_len);
|
||||
byte[] sock_addr =
|
||||
uc.mem_read(upeer_sockaddr, upeer_len);
|
||||
|
||||
String msg = String.format("fd(%d) accept client with upeer=%s", fd, parse_sock_address(sock_addr));
|
||||
String msg =
|
||||
String.format("fd(%d) accept client with upeer=%s",
|
||||
fd, parse_sock_address(sock_addr));
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
}
|
||||
else if (call == 9) { // sys_send
|
||||
} else if (call == 9) { // sys_send
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long buff = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long length = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long flags = toInt(uc.mem_read(args + SIZE_REG * 3, SIZE_REG));
|
||||
long length =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long flags =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 3, SIZE_REG));
|
||||
|
||||
byte[] buf = uc.mem_read(buff, length);
|
||||
String msg = String.format("fd(%d) send data=%s", fd, new String(buf));
|
||||
String msg = String.format("fd(%d) send data=%s", fd,
|
||||
new String(buf));
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
else if (call == 11) { // sys_receive
|
||||
} else if (call == 11) { // sys_receive
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long ubuf = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
long size = toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long flags = toInt(uc.mem_read(args + SIZE_REG * 3, SIZE_REG));
|
||||
long size =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 2, SIZE_REG));
|
||||
long flags =
|
||||
toInt(uc.mem_read(args + SIZE_REG * 3, SIZE_REG));
|
||||
|
||||
String msg = String.format("fd(%d) is gonna receive data with size=%d flags=%d", fd, size, flags);
|
||||
String msg = String.format(
|
||||
"fd(%d) is gonna receive data with size=%d flags=%d",
|
||||
fd, size, flags);
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
else if (call == 13) { // sys_shutdown
|
||||
} else if (call == 13) { // sys_shutdown
|
||||
long fd = toInt(uc.mem_read(args, SIZE_REG));
|
||||
long how = toInt(uc.mem_read(args + SIZE_REG, SIZE_REG));
|
||||
|
||||
String msg = String.format("fd(%d) is shutted down because of %d", fd, how);
|
||||
String msg = String.format(
|
||||
"fd(%d) is shutted down because of %d", fd, how);
|
||||
fd_chains.add_log(fd, msg);
|
||||
print_sockcall(msg);
|
||||
}
|
||||
@@ -242,6 +258,7 @@ public class SampleNetworkAuditing {
|
||||
|
||||
public static final Hashtable<Long, String> SOCKET_TYPES;
|
||||
public static final Hashtable<Long, String> ADDR_FAMILY;
|
||||
|
||||
static {
|
||||
SOCKET_TYPES = new Hashtable<Long, String>();
|
||||
ADDR_FAMILY = new Hashtable<Long, String>();
|
||||
@@ -266,14 +283,38 @@ public class SampleNetworkAuditing {
|
||||
ADDR_FAMILY.put(12L, "AF_MAX");
|
||||
}
|
||||
|
||||
// http://shell-storm.org/shellcode/files/shellcode-861.php
|
||||
public static final byte[] X86_SEND_ETCPASSWD = {106,102,88,49,-37,67,49,-46,82,106,1,106,2,-119,-31,-51,-128,-119,-58,106,102,88,67,104,127,1,1,1,102,104,48,57,102,83,-119,-31,106,16,81,86,-119,-31,67,-51,-128,-119,-58,106,1,89,-80,63,-51,-128,-21,39,106,5,88,91,49,-55,-51,-128,-119,-61,-80,3,-119,-25,-119,-7,49,-46,-74,-1,-78,-1,-51,-128,-119,-62,106,4,88,-77,1,-51,-128,106,1,88,67,-51,-128,-24,-44,-1,-1,-1,47,101,116,99,47,112,97,115,115,119,100};
|
||||
// http://shell-storm.org/shellcode/files/shellcode-882.php
|
||||
public static final byte[] X86_BIND_TCP = {106,102,88,106,1,91,49,-10,86,83,106,2,-119,-31,-51,-128,95,-105,-109,-80,102,86,102,104,5,57,102,83,-119,-31,106,16,81,87,-119,-31,-51,-128,-80,102,-77,4,86,87,-119,-31,-51,-128,-80,102,67,86,86,87,-119,-31,-51,-128,89,89,-79,2,-109,-80,63,-51,-128,73,121,-7,-80,11,104,47,47,115,104,104,47,98,105,110,-119,-29,65,-119,-54,-51,-128};
|
||||
// http://shell-storm.org/shellcode/files/shellcode-883.php
|
||||
public static final byte[] X86_REVERSE_TCP = {106,102,88,106,1,91,49,-46,82,83,106,2,-119,-31,-51,-128,-110,-80,102,104,127,1,1,1,102,104,5,57,67,102,83,-119,-31,106,16,81,82,-119,-31,67,-51,-128,106,2,89,-121,-38,-80,63,-51,-128,73,121,-7,-80,11,65,-119,-54,82,104,47,47,115,104,104,47,98,105,110,-119,-29,-51,-128};
|
||||
// http://shell-storm.org/shellcode/files/shellcode-849.php
|
||||
public static final byte[] X86_REVERSE_TCP_2 = {49,-64,49,-37,49,-55,49,-46,-80,102,-77,1,81,106,6,106,1,106,2,-119,-31,-51,-128,-119,-58,-80,102,49,-37,-77,2,104,-64,-88,1,10,102,104,122,105,102,83,-2,-61,-119,-31,106,16,81,86,-119,-31,-51,-128,49,-55,-79,3,-2,-55,-80,63,-51,-128,117,-8,49,-64,82,104,110,47,115,104,104,47,47,98,105,-119,-29,82,83,-119,-31,82,-119,-30,-80,11,-51,-128};
|
||||
// http://shell-storm.org/shellcode/files/shellcode-861.php
|
||||
public static final byte[] X86_SEND_ETCPASSWD = { 106, 102, 88, 49, -37, 67,
|
||||
49, -46, 82, 106, 1, 106, 2, -119, -31, -51, -128, -119, -58, 106, 102,
|
||||
88, 67, 104, 127, 1, 1, 1, 102, 104, 48, 57, 102, 83, -119, -31, 106,
|
||||
16, 81, 86, -119, -31, 67, -51, -128, -119, -58, 106, 1, 89, -80, 63,
|
||||
-51, -128, -21, 39, 106, 5, 88, 91, 49, -55, -51, -128, -119, -61, -80,
|
||||
3, -119, -25, -119, -7, 49, -46, -74, -1, -78, -1, -51, -128, -119, -62,
|
||||
106, 4, 88, -77, 1, -51, -128, 106, 1, 88, 67, -51, -128, -24, -44, -1,
|
||||
-1, -1, 47, 101, 116, 99, 47, 112, 97, 115, 115, 119, 100 };
|
||||
// http://shell-storm.org/shellcode/files/shellcode-882.php
|
||||
public static final byte[] X86_BIND_TCP = { 106, 102, 88, 106, 1, 91, 49,
|
||||
-10, 86, 83, 106, 2, -119, -31, -51, -128, 95, -105, -109, -80, 102, 86,
|
||||
102, 104, 5, 57, 102, 83, -119, -31, 106, 16, 81, 87, -119, -31, -51,
|
||||
-128, -80, 102, -77, 4, 86, 87, -119, -31, -51, -128, -80, 102, 67, 86,
|
||||
86, 87, -119, -31, -51, -128, 89, 89, -79, 2, -109, -80, 63, -51, -128,
|
||||
73, 121, -7, -80, 11, 104, 47, 47, 115, 104, 104, 47, 98, 105, 110,
|
||||
-119, -29, 65, -119, -54, -51, -128 };
|
||||
// http://shell-storm.org/shellcode/files/shellcode-883.php
|
||||
public static final byte[] X86_REVERSE_TCP = { 106, 102, 88, 106, 1, 91, 49,
|
||||
-46, 82, 83, 106, 2, -119, -31, -51, -128, -110, -80, 102, 104, 127, 1,
|
||||
1, 1, 102, 104, 5, 57, 67, 102, 83, -119, -31, 106, 16, 81, 82, -119,
|
||||
-31, 67, -51, -128, 106, 2, 89, -121, -38, -80, 63, -51, -128, 73, 121,
|
||||
-7, -80, 11, 65, -119, -54, 82, 104, 47, 47, 115, 104, 104, 47, 98, 105,
|
||||
110, -119, -29, -51, -128 };
|
||||
// http://shell-storm.org/shellcode/files/shellcode-849.php
|
||||
public static final byte[] X86_REVERSE_TCP_2 = { 49, -64, 49, -37, 49, -55,
|
||||
49, -46, -80, 102, -77, 1, 81, 106, 6, 106, 1, 106, 2, -119, -31, -51,
|
||||
-128, -119, -58, -80, 102, 49, -37, -77, 2, 104, -64, -88, 1, 10, 102,
|
||||
104, 122, 105, 102, 83, -2, -61, -119, -31, 106, 16, 81, 86, -119, -31,
|
||||
-51, -128, 49, -55, -79, 3, -2, -55, -80, 63, -51, -128, 117, -8, 49,
|
||||
-64, 82, 104, 110, 47, 115, 104, 104, 47, 47, 98, 105, -119, -29, 82,
|
||||
83, -119, -31, 82, -119, -30, -80, 11, -51, -128 };
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x1000000;
|
||||
@@ -292,8 +333,10 @@ public class SampleNetworkAuditing {
|
||||
}
|
||||
|
||||
private static class LogChain {
|
||||
public Hashtable<Long, ArrayList<String>> __chains = new Hashtable<Long, ArrayList<String>>();
|
||||
public Hashtable<Long, ArrayList<Long>> __linking_fds = new Hashtable<Long, ArrayList<Long>>();
|
||||
public Hashtable<Long, ArrayList<String>> __chains =
|
||||
new Hashtable<Long, ArrayList<String>>();
|
||||
public Hashtable<Long, ArrayList<Long>> __linking_fds =
|
||||
new Hashtable<Long, ArrayList<Long>>();
|
||||
|
||||
public void clean() {
|
||||
__chains.clear();
|
||||
@@ -303,8 +346,7 @@ public class SampleNetworkAuditing {
|
||||
public void create_chain(long id) {
|
||||
if (!__chains.containsKey(id)) {
|
||||
__chains.put(id, new ArrayList<String>());
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
System.out.printf("LogChain: id %d existed\n", id);
|
||||
}
|
||||
}
|
||||
@@ -314,8 +356,7 @@ public class SampleNetworkAuditing {
|
||||
|
||||
if (fd != -1) {
|
||||
__chains.get(fd).add(msg);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
System.out.printf("LogChain: id %d doesn't exist\n", id);
|
||||
}
|
||||
}
|
||||
@@ -361,7 +402,7 @@ public class SampleNetworkAuditing {
|
||||
StringBuilder ret = new StringBuilder();
|
||||
char c;
|
||||
do {
|
||||
c = (char)(uc.mem_read(addr++, 1)[0] & 0xff);
|
||||
c = (char) (uc.mem_read(addr++, 1)[0] & 0xff);
|
||||
if (c != 0) {
|
||||
ret.append(c);
|
||||
}
|
||||
@@ -374,10 +415,12 @@ public class SampleNetworkAuditing {
|
||||
int sin_family = ((sock_addr[0] & 0xff) + (sock_addr[1] << 8)) & 0xffff;
|
||||
|
||||
if (sin_family == 2) { // AF_INET
|
||||
int sin_port = ((sock_addr[3] & 0xff) + (sock_addr[2] << 8)) & 0xffff;
|
||||
return String.format("%d.%d.%d.%d:%d", sock_addr[4] & 0xff, sock_addr[5] & 0xff, sock_addr[6] & 0xff, sock_addr[7] & 0xff, sin_port);
|
||||
}
|
||||
else if (sin_family == 6) // AF_INET6
|
||||
int sin_port =
|
||||
((sock_addr[3] & 0xff) + (sock_addr[2] << 8)) & 0xffff;
|
||||
return String.format("%d.%d.%d.%d:%d", sock_addr[4] & 0xff,
|
||||
sock_addr[5] & 0xff, sock_addr[6] & 0xff, sock_addr[7] & 0xff,
|
||||
sin_port);
|
||||
} else if (sin_family == 6) // AF_INET6
|
||||
return "";
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -8,8 +8,9 @@ import unicorn.*;
|
||||
public class Sample_arm {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] ARM_CODE = {55,0,(byte)0xa0,(byte)0xe3,3,16,66,(byte)0xe0}; // mov r0, #0x37; sub r1, r2, r3
|
||||
public static final byte[] THUMB_CODE = {(byte)0x83, (byte)0xb0}; // sub sp, #0xc
|
||||
public static final byte[] ARM_CODE =
|
||||
{ 55, 0, (byte) 0xa0, (byte) 0xe3, 3, 16, 66, (byte) 0xe0 }; // mov r0, #0x37; sub r1, r2, r3
|
||||
public static final byte[] THUMB_CODE = { (byte) 0x83, (byte) 0xb0 }; // sub sp, #0xc
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x10000;
|
||||
@@ -24,21 +25,23 @@ public class Sample_arm {
|
||||
}
|
||||
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data)
|
||||
{
|
||||
System.out.print(String.format(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size));
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size));
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
}
|
||||
}
|
||||
|
||||
static void test_arm()
|
||||
{
|
||||
static void test_arm() {
|
||||
|
||||
Long r0 = 0x1234L; // R0 register
|
||||
Long r2 = 0x6789L; // R1 register
|
||||
@@ -74,16 +77,15 @@ public class Sample_arm {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r0 = (Long)u.reg_read(Unicorn.UC_ARM_REG_R0);
|
||||
r1 = (Long)u.reg_read(Unicorn.UC_ARM_REG_R1);
|
||||
r0 = (Long) u.reg_read(Unicorn.UC_ARM_REG_R0);
|
||||
r1 = (Long) u.reg_read(Unicorn.UC_ARM_REG_R1);
|
||||
System.out.print(String.format(">>> R0 = 0x%x\n", r0.intValue()));
|
||||
System.out.print(String.format(">>> R1 = 0x%x\n", r1.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
static void test_thumb()
|
||||
{
|
||||
static void test_thumb() {
|
||||
|
||||
Long sp = 0x1234L; // R0 register
|
||||
|
||||
@@ -114,14 +116,13 @@ public class Sample_arm {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
sp = (Long)u.reg_read(Unicorn.UC_ARM_REG_SP);
|
||||
sp = (Long) u.reg_read(Unicorn.UC_ARM_REG_SP);
|
||||
System.out.print(String.format(">>> SP = 0x%x\n", sp.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_arm();
|
||||
System.out.print("==========================\n");
|
||||
test_thumb();
|
||||
|
||||
@@ -29,7 +29,7 @@ import unicorn.*;
|
||||
public class Sample_arm64 {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] ARM_CODE = {-85,1,15,-117}; // add x11, x13, x15
|
||||
public static final byte[] ARM_CODE = { -85, 1, 15, -117 }; // add x11, x13, x15
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x10000;
|
||||
@@ -46,7 +46,7 @@ public class Sample_arm64 {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -55,19 +55,22 @@ public class Sample_arm64 {
|
||||
// callback for tracing basic blocks
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size));
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
}
|
||||
}
|
||||
|
||||
static void test_arm64()
|
||||
{
|
||||
static void test_arm64() {
|
||||
|
||||
Long x11 = 0x1234L; // X11 register
|
||||
Long x13 = 0x6789L; // X13 register
|
||||
@@ -102,14 +105,13 @@ public class Sample_arm64 {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
x11 = (Long)u.reg_read(Unicorn.UC_ARM64_REG_X11);
|
||||
x11 = (Long) u.reg_read(Unicorn.UC_ARM64_REG_X11);
|
||||
System.out.print(String.format(">>> X11 = 0x%x\n", x11.longValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_arm64();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ import unicorn.*;
|
||||
public class Sample_m68k {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] M68K_CODE = {118,-19}; // movq #-19, %d3
|
||||
public static final byte[] M68K_CODE = { 118, -19 }; // movq #-19, %d3
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x10000;
|
||||
@@ -46,7 +46,7 @@ public class Sample_m68k {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -55,19 +55,22 @@ public class Sample_m68k {
|
||||
// callback for tracing basic blocks
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size));
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
}
|
||||
}
|
||||
|
||||
static void test_m68k()
|
||||
{
|
||||
static void test_m68k() {
|
||||
Long d0 = 0x0000L; // d0 data register
|
||||
Long d1 = 0x0000L; // d1 data register
|
||||
Long d2 = 0x0000L; // d2 data register
|
||||
@@ -92,7 +95,8 @@ public class Sample_m68k {
|
||||
System.out.print("Emulate M68K code\n");
|
||||
|
||||
// Initialize emulator in M68K mode
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_M68K, Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
Unicorn u =
|
||||
new Unicorn(Unicorn.UC_ARCH_M68K, Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
|
||||
// map 2MB memory for this emulation
|
||||
u.mem_map(ADDRESS, 2 * 1024 * 1024, Unicorn.UC_PROT_ALL);
|
||||
@@ -135,43 +139,50 @@ public class Sample_m68k {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
d0 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D0);
|
||||
d1 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D1);
|
||||
d2 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D2);
|
||||
d3 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D3);
|
||||
d4 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D4);
|
||||
d5 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D5);
|
||||
d6 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D6);
|
||||
d7 = (Long)u.reg_read(Unicorn.UC_M68K_REG_D7);
|
||||
d0 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D0);
|
||||
d1 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D1);
|
||||
d2 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D2);
|
||||
d3 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D3);
|
||||
d4 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D4);
|
||||
d5 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D5);
|
||||
d6 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D6);
|
||||
d7 = (Long) u.reg_read(Unicorn.UC_M68K_REG_D7);
|
||||
|
||||
a0 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A0);
|
||||
a1 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A1);
|
||||
a2 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A2);
|
||||
a3 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A3);
|
||||
a4 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A4);
|
||||
a5 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A5);
|
||||
a6 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A6);
|
||||
a7 = (Long)u.reg_read(Unicorn.UC_M68K_REG_A7);
|
||||
a0 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A0);
|
||||
a1 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A1);
|
||||
a2 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A2);
|
||||
a3 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A3);
|
||||
a4 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A4);
|
||||
a5 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A5);
|
||||
a6 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A6);
|
||||
a7 = (Long) u.reg_read(Unicorn.UC_M68K_REG_A7);
|
||||
|
||||
pc = (Long)u.reg_read(Unicorn.UC_M68K_REG_PC);
|
||||
sr = (Long)u.reg_read(Unicorn.UC_M68K_REG_SR);
|
||||
pc = (Long) u.reg_read(Unicorn.UC_M68K_REG_PC);
|
||||
sr = (Long) u.reg_read(Unicorn.UC_M68K_REG_SR);
|
||||
|
||||
System.out.print(String.format(">>> A0 = 0x%x\t\t>>> D0 = 0x%x\n", a0.intValue(), d0.intValue()));
|
||||
System.out.print(String.format(">>> A1 = 0x%x\t\t>>> D1 = 0x%x\n", a1.intValue(), d1.intValue()));
|
||||
System.out.print(String.format(">>> A2 = 0x%x\t\t>>> D2 = 0x%x\n", a2.intValue(), d2.intValue()));
|
||||
System.out.print(String.format(">>> A3 = 0x%x\t\t>>> D3 = 0x%x\n", a3.intValue(), d3.intValue()));
|
||||
System.out.print(String.format(">>> A4 = 0x%x\t\t>>> D4 = 0x%x\n", a4.intValue(), d4.intValue()));
|
||||
System.out.print(String.format(">>> A5 = 0x%x\t\t>>> D5 = 0x%x\n", a5.intValue(), d5.intValue()));
|
||||
System.out.print(String.format(">>> A6 = 0x%x\t\t>>> D6 = 0x%x\n", a6.intValue(), d6.intValue()));
|
||||
System.out.print(String.format(">>> A7 = 0x%x\t\t>>> D7 = 0x%x\n", a7.intValue(), d7.intValue()));
|
||||
System.out.print(String.format(">>> A0 = 0x%x\t\t>>> D0 = 0x%x\n",
|
||||
a0.intValue(), d0.intValue()));
|
||||
System.out.print(String.format(">>> A1 = 0x%x\t\t>>> D1 = 0x%x\n",
|
||||
a1.intValue(), d1.intValue()));
|
||||
System.out.print(String.format(">>> A2 = 0x%x\t\t>>> D2 = 0x%x\n",
|
||||
a2.intValue(), d2.intValue()));
|
||||
System.out.print(String.format(">>> A3 = 0x%x\t\t>>> D3 = 0x%x\n",
|
||||
a3.intValue(), d3.intValue()));
|
||||
System.out.print(String.format(">>> A4 = 0x%x\t\t>>> D4 = 0x%x\n",
|
||||
a4.intValue(), d4.intValue()));
|
||||
System.out.print(String.format(">>> A5 = 0x%x\t\t>>> D5 = 0x%x\n",
|
||||
a5.intValue(), d5.intValue()));
|
||||
System.out.print(String.format(">>> A6 = 0x%x\t\t>>> D6 = 0x%x\n",
|
||||
a6.intValue(), d6.intValue()));
|
||||
System.out.print(String.format(">>> A7 = 0x%x\t\t>>> D7 = 0x%x\n",
|
||||
a7.intValue(), d7.intValue()));
|
||||
System.out.print(String.format(">>> PC = 0x%x\n", pc.intValue()));
|
||||
System.out.print(String.format(">>> SR = 0x%x\n", sr.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_m68k();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,8 +29,8 @@ import unicorn.*;
|
||||
public class Sample_mips {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] MIPS_CODE_EB = {52,33,52,86};
|
||||
public static final byte[] MIPS_CODE_EL = {86,52,33,52};
|
||||
public static final byte[] MIPS_CODE_EB = { 52, 33, 52, 86 };
|
||||
public static final byte[] MIPS_CODE_EL = { 86, 52, 33, 52 };
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x10000;
|
||||
@@ -47,7 +47,7 @@ public class Sample_mips {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -56,26 +56,30 @@ public class Sample_mips {
|
||||
// callback for tracing basic blocks
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size));
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
}
|
||||
}
|
||||
|
||||
static void test_mips_eb()
|
||||
{
|
||||
static void test_mips_eb() {
|
||||
|
||||
Long r1 = 0x6789L; // R1 register
|
||||
|
||||
System.out.print("Emulate MIPS code (big-endian)\n");
|
||||
|
||||
// Initialize emulator in MIPS mode
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_MIPS, Unicorn.UC_MODE_MIPS32 + Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_MIPS,
|
||||
Unicorn.UC_MODE_MIPS32 + Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
|
||||
// map 2MB memory for this emulation
|
||||
u.mem_map(ADDRESS, 2 * 1024 * 1024, Unicorn.UC_PROT_ALL);
|
||||
@@ -99,21 +103,21 @@ public class Sample_mips {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r1 = (Long)u.reg_read(Unicorn.UC_MIPS_REG_1);
|
||||
r1 = (Long) u.reg_read(Unicorn.UC_MIPS_REG_1);
|
||||
System.out.print(String.format(">>> R1 = 0x%x\n", r1.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
static void test_mips_el()
|
||||
{
|
||||
static void test_mips_el() {
|
||||
Long r1 = 0x6789L; // R1 register
|
||||
|
||||
System.out.print("===========================\n");
|
||||
System.out.print("Emulate MIPS code (little-endian)\n");
|
||||
|
||||
// Initialize emulator in MIPS mode
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_MIPS, Unicorn.UC_MODE_MIPS32 + Unicorn.UC_MODE_LITTLE_ENDIAN);
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_MIPS,
|
||||
Unicorn.UC_MODE_MIPS32 + Unicorn.UC_MODE_LITTLE_ENDIAN);
|
||||
|
||||
// map 2MB memory for this emulation
|
||||
u.mem_map(ADDRESS, 2 * 1024 * 1024, Unicorn.UC_PROT_ALL);
|
||||
@@ -137,14 +141,13 @@ public class Sample_mips {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r1 = (Long)u.reg_read(Unicorn.UC_MIPS_REG_1);
|
||||
r1 = (Long) u.reg_read(Unicorn.UC_MIPS_REG_1);
|
||||
System.out.print(String.format(">>> R1 = 0x%x\n", r1.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_mips_eb();
|
||||
test_mips_el();
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ import unicorn.*;
|
||||
public class Sample_sparc {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] SPARC_CODE = {-122,0,64,2};
|
||||
public static final byte[] SPARC_CODE = { -122, 0, 64, 2 };
|
||||
//public static final byte[] SPARC_CODE = {-69,112,0,0}; //illegal code
|
||||
|
||||
// memory address where emulation starts
|
||||
@@ -47,7 +47,7 @@ public class Sample_sparc {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -56,19 +56,22 @@ public class Sample_sparc {
|
||||
// callback for tracing basic blocks
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size));
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.print(String.format(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
}
|
||||
}
|
||||
|
||||
static void test_sparc()
|
||||
{
|
||||
static void test_sparc() {
|
||||
Long g1 = 0x1230L; // G1 register
|
||||
Long g2 = 0x6789L; // G2 register
|
||||
Long g3 = 0x5555L; // G3 register
|
||||
@@ -76,7 +79,8 @@ public class Sample_sparc {
|
||||
System.out.print("Emulate SPARC code\n");
|
||||
|
||||
// Initialize emulator in Sparc mode
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_SPARC, Unicorn.UC_MODE_32 + Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
Unicorn u = new Unicorn(Unicorn.UC_ARCH_SPARC,
|
||||
Unicorn.UC_MODE_32 + Unicorn.UC_MODE_BIG_ENDIAN);
|
||||
|
||||
// map 2MB memory for this emulation
|
||||
u.mem_map(ADDRESS, 2 * 1024 * 1024, Unicorn.UC_PROT_ALL);
|
||||
@@ -102,14 +106,13 @@ public class Sample_sparc {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
g3 = (Long)u.reg_read(Unicorn.UC_SPARC_REG_G3);
|
||||
g3 = (Long) u.reg_read(Unicorn.UC_SPARC_REG_G3);
|
||||
System.out.print(String.format(">>> G3 = 0x%x\n", g3.intValue()));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_sparc();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,16 +29,30 @@ import unicorn.*;
|
||||
public class Sample_x86 {
|
||||
|
||||
// code to be emulated
|
||||
public static final byte[] X86_CODE32 = {65,74};
|
||||
public static final byte[] X86_CODE32_JUMP = {-21,2,-112,-112,-112,-112,-112,-112};
|
||||
public static final byte[] X86_CODE32_SELF = {-21,28,90,-119,-42,-117,2,102,61,-54,125,117,6,102,5,3,3,-119,2,-2,-62,61,65,65,65,65,117,-23,-1,-26,-24,-33,-1,-1,-1,49,-46,106,11,88,-103,82,104,47,47,115,104,104,47,98,105,110,-119,-29,82,83,-119,-31,-54,125,65,65,65,65};
|
||||
public static final byte[] X86_CODE32_LOOP = {65,74,-21,-2};
|
||||
public static final byte[] X86_CODE32_MEM_WRITE = {-119,13,-86,-86,-86,-86,65,74};
|
||||
public static final byte[] X86_CODE32_MEM_READ = {-117,13,-86,-86,-86,-86,65,74};
|
||||
public static final byte[] X86_CODE32_JMP_INVALID = {-23,-23,-18,-18,-18,65,74};
|
||||
public static final byte[] X86_CODE32_INOUT = {65,-28,63,74,-26,70,67};
|
||||
public static final byte[] X86_CODE64 = {65,-68,59,-80,40,42,73,15,-55,-112,77,15,-83,-49,73,-121,-3,-112,72,-127,-46,-118,-50,119,53,72,-9,-39,77,41,-12,73,-127,-55,-10,-118,-58,83,77,-121,-19,72,15,-83,-46,73,-9,-44,72,-9,-31,77,25,-59,77,-119,-59,72,-9,-42,65,-72,79,-115,107,89,77,-121,-48,104,106,30,9,60,89};
|
||||
public static final byte[] X86_CODE16 = {0, 0}; // add byte ptr [bx + si], al
|
||||
public static final byte[] X86_CODE32 = { 65, 74 };
|
||||
public static final byte[] X86_CODE32_JUMP =
|
||||
{ -21, 2, -112, -112, -112, -112, -112, -112 };
|
||||
public static final byte[] X86_CODE32_SELF = { -21, 28, 90, -119, -42, -117,
|
||||
2, 102, 61, -54, 125, 117, 6, 102, 5, 3, 3, -119, 2, -2, -62, 61, 65,
|
||||
65, 65, 65, 117, -23, -1, -26, -24, -33, -1, -1, -1, 49, -46, 106, 11,
|
||||
88, -103, 82, 104, 47, 47, 115, 104, 104, 47, 98, 105, 110, -119, -29,
|
||||
82, 83, -119, -31, -54, 125, 65, 65, 65, 65 };
|
||||
public static final byte[] X86_CODE32_LOOP = { 65, 74, -21, -2 };
|
||||
public static final byte[] X86_CODE32_MEM_WRITE =
|
||||
{ -119, 13, -86, -86, -86, -86, 65, 74 };
|
||||
public static final byte[] X86_CODE32_MEM_READ =
|
||||
{ -117, 13, -86, -86, -86, -86, 65, 74 };
|
||||
public static final byte[] X86_CODE32_JMP_INVALID =
|
||||
{ -23, -23, -18, -18, -18, 65, 74 };
|
||||
public static final byte[] X86_CODE32_INOUT =
|
||||
{ 65, -28, 63, 74, -26, 70, 67 };
|
||||
public static final byte[] X86_CODE64 = { 65, -68, 59, -80, 40, 42, 73, 15,
|
||||
-55, -112, 77, 15, -83, -49, 73, -121, -3, -112, 72, -127, -46, -118,
|
||||
-50, 119, 53, 72, -9, -39, 77, 41, -12, 73, -127, -55, -10, -118, -58,
|
||||
83, 77, -121, -19, 72, 15, -83, -46, 73, -9, -44, 72, -9, -31, 77, 25,
|
||||
-59, 77, -119, -59, 72, -9, -42, 65, -72, 79, -115, 107, 89, 77, -121,
|
||||
-48, 104, 106, 30, 9, 60, 89 };
|
||||
public static final byte[] X86_CODE16 = { 0, 0 }; // add byte ptr [bx + si], al
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x1000000;
|
||||
@@ -55,7 +69,7 @@ public class Sample_x86 {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -65,16 +79,20 @@ public class Sample_x86 {
|
||||
// callback for tracing instruction
|
||||
private static class MyBlockHook implements BlockHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.printf(">>> Tracing basic block at 0x%x, block size = 0x%x\n", address, size);
|
||||
System.out.printf(
|
||||
">>> Tracing basic block at 0x%x, block size = 0x%x\n", address,
|
||||
size);
|
||||
}
|
||||
}
|
||||
|
||||
// callback for tracing instruction
|
||||
private static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
System.out.printf(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size);
|
||||
System.out.printf(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size);
|
||||
|
||||
Long eflags = (Long)u.reg_read(Unicorn.UC_X86_REG_EFLAGS);
|
||||
Long eflags = (Long) u.reg_read(Unicorn.UC_X86_REG_EFLAGS);
|
||||
System.out.printf(">>> --- EFLAGS is 0x%x\n", eflags.intValue());
|
||||
|
||||
// Uncomment below code to stop the emulation using uc_emu_stop()
|
||||
@@ -84,11 +102,13 @@ public class Sample_x86 {
|
||||
}
|
||||
|
||||
private static class MyWriteInvalidHook implements EventMemHook {
|
||||
public boolean hook(Unicorn u, long address, int size, long value, Object user) {
|
||||
System.out.printf(">>> Missing memory is being WRITE at 0x%x, data size = %d, data value = 0x%x\n",
|
||||
public boolean hook(Unicorn u, long address, int size, long value,
|
||||
Object user) {
|
||||
System.out.printf(
|
||||
">>> Missing memory is being WRITE at 0x%x, data size = %d, data value = 0x%x\n",
|
||||
address, size, value);
|
||||
// map this memory in with 2MB in size
|
||||
u.mem_map(0xaaaa0000, 2 * 1024*1024, Unicorn.UC_PROT_ALL);
|
||||
u.mem_map(0xaaaa0000, 2 * 1024 * 1024, Unicorn.UC_PROT_ALL);
|
||||
// return true to indicate we want to continue
|
||||
return true;
|
||||
}
|
||||
@@ -97,8 +117,10 @@ public class Sample_x86 {
|
||||
// callback for tracing instruction
|
||||
private static class MyCode64Hook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user_data) {
|
||||
Long r_rip = (Long)u.reg_read(Unicorn.UC_X86_REG_RIP);
|
||||
System.out.printf(">>> Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size);
|
||||
Long r_rip = (Long) u.reg_read(Unicorn.UC_X86_REG_RIP);
|
||||
System.out.printf(
|
||||
">>> Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size);
|
||||
System.out.printf(">>> RIP is 0x%x\n", r_rip.longValue());
|
||||
|
||||
// Uncomment below code to stop the emulation using uc_emu_stop()
|
||||
@@ -107,16 +129,19 @@ public class Sample_x86 {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static class MyRead64Hook implements ReadHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user) {
|
||||
System.out.printf(">>> Memory is being READ at 0x%x, data size = %d\n", address, size);
|
||||
System.out.printf(
|
||||
">>> Memory is being READ at 0x%x, data size = %d\n", address,
|
||||
size);
|
||||
}
|
||||
}
|
||||
|
||||
private static class MyWrite64Hook implements WriteHook {
|
||||
public void hook(Unicorn u, long address, int size, long value, Object user) {
|
||||
System.out.printf(">>> Memory is being WRITE at 0x%x, data size = %d, data value = 0x%x\n",
|
||||
public void hook(Unicorn u, long address, int size, long value,
|
||||
Object user) {
|
||||
System.out.printf(
|
||||
">>> Memory is being WRITE at 0x%x, data size = %d, data value = 0x%x\n",
|
||||
address, size, value);
|
||||
}
|
||||
}
|
||||
@@ -125,11 +150,13 @@ public class Sample_x86 {
|
||||
// this returns the data read from the port
|
||||
private static class MyInHook implements InHook {
|
||||
public int hook(Unicorn u, int port, int size, Object user_data) {
|
||||
Long r_eip = (Long)u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
Long r_eip = (Long) u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
|
||||
System.out.printf("--- reading from port 0x%x, size: %d, address: 0x%x\n", port, size, r_eip.intValue());
|
||||
System.out.printf(
|
||||
"--- reading from port 0x%x, size: %d, address: 0x%x\n", port,
|
||||
size, r_eip.intValue());
|
||||
|
||||
switch(size) {
|
||||
switch (size) {
|
||||
case 1:
|
||||
// read 1 byte to AL
|
||||
return 0xf1;
|
||||
@@ -146,23 +173,26 @@ public class Sample_x86 {
|
||||
|
||||
// callback for OUT instruction (X86).
|
||||
private static class MyOutHook implements OutHook {
|
||||
public void hook(Unicorn u, int port, int size, int value, Object user) {
|
||||
Long eip = (Long)u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
public void hook(Unicorn u, int port, int size, int value,
|
||||
Object user) {
|
||||
Long eip = (Long) u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
Long tmp = null;
|
||||
System.out.printf("--- writing to port 0x%x, size: %d, value: 0x%x, address: 0x%x\n", port, size, value, eip.intValue());
|
||||
System.out.printf(
|
||||
"--- writing to port 0x%x, size: %d, value: 0x%x, address: 0x%x\n",
|
||||
port, size, value, eip.intValue());
|
||||
|
||||
// confirm that value is indeed the value of AL/AX/EAX
|
||||
switch(size) {
|
||||
switch (size) {
|
||||
default:
|
||||
return; // should never reach this
|
||||
case 1:
|
||||
tmp = (Long)u.reg_read(Unicorn.UC_X86_REG_AL);
|
||||
tmp = (Long) u.reg_read(Unicorn.UC_X86_REG_AL);
|
||||
break;
|
||||
case 2:
|
||||
tmp = (Long)u.reg_read(Unicorn.UC_X86_REG_AX);
|
||||
tmp = (Long) u.reg_read(Unicorn.UC_X86_REG_AX);
|
||||
break;
|
||||
case 4:
|
||||
tmp = (Long)u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
tmp = (Long) u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -181,7 +211,8 @@ public class Sample_x86 {
|
||||
try {
|
||||
uc = new Unicorn(Unicorn.UC_ARCH_X86, Unicorn.UC_MODE_32);
|
||||
} catch (UnicornException uex) {
|
||||
System.out.println("Failed on uc_open() with error returned: " + uex);
|
||||
System.out
|
||||
.println("Failed on uc_open() with error returned: " + uex);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -192,7 +223,8 @@ public class Sample_x86 {
|
||||
try {
|
||||
uc.mem_write(ADDRESS, X86_CODE32);
|
||||
} catch (UnicornException uex) {
|
||||
System.out.println("Failed to write emulation code to memory, quit!\n");
|
||||
System.out.println(
|
||||
"Failed to write emulation code to memory, quit!\n");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -217,23 +249,24 @@ public class Sample_x86 {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_ecx = (Long)uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long)uc.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_ecx = (Long) uc.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long) uc.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
System.out.printf(">>> EDX = 0x%x\n", r_edx.intValue());
|
||||
|
||||
// read from memory
|
||||
try {
|
||||
byte[] tmp = uc.mem_read(ADDRESS, 4);
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n", ADDRESS, toInt(tmp));
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n", ADDRESS,
|
||||
toInt(tmp));
|
||||
} catch (UnicornException ex) {
|
||||
System.out.printf(">>> Failed to read 4 bytes from [0x%x]\n", ADDRESS);
|
||||
System.out.printf(">>> Failed to read 4 bytes from [0x%x]\n",
|
||||
ADDRESS);
|
||||
}
|
||||
uc.close();
|
||||
}
|
||||
|
||||
static void test_i386_inout()
|
||||
{
|
||||
static void test_i386_inout() {
|
||||
Long r_eax = 0x1234L; // ECX register
|
||||
Long r_ecx = 0x6789L; // EDX register
|
||||
|
||||
@@ -270,16 +303,15 @@ public class Sample_x86 {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_eax = (Long)u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_eax = (Long) u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
System.out.printf(">>> EAX = 0x%x\n", r_eax.intValue());
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
static void test_i386_jump()
|
||||
{
|
||||
static void test_i386_jump() {
|
||||
System.out.print("===================================\n");
|
||||
System.out.print("Emulate i386 code with jump\n");
|
||||
|
||||
@@ -307,8 +339,7 @@ public class Sample_x86 {
|
||||
}
|
||||
|
||||
// emulate code that loop forever
|
||||
static void test_i386_loop()
|
||||
{
|
||||
static void test_i386_loop() {
|
||||
Long r_ecx = 0x1234L; // ECX register
|
||||
Long r_edx = 0x7890L; // EDX register
|
||||
|
||||
@@ -330,13 +361,14 @@ public class Sample_x86 {
|
||||
|
||||
// emulate machine code in 2 seconds, so we can quit even
|
||||
// if the code loops
|
||||
u.emu_start(ADDRESS, ADDRESS + X86_CODE32_LOOP.length, 2 * Unicorn.UC_SECOND_SCALE, 0);
|
||||
u.emu_start(ADDRESS, ADDRESS + X86_CODE32_LOOP.length,
|
||||
2 * Unicorn.UC_SECOND_SCALE, 0);
|
||||
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long)u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long) u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
System.out.printf(">>> EDX = 0x%x\n", r_edx.intValue());
|
||||
|
||||
@@ -344,8 +376,7 @@ public class Sample_x86 {
|
||||
}
|
||||
|
||||
// emulate code that read invalid memory
|
||||
static void test_i386_invalid_mem_read()
|
||||
{
|
||||
static void test_i386_invalid_mem_read() {
|
||||
Long r_ecx = 0x1234L; // ECX register
|
||||
Long r_edx = 0x7890L; // EDX register
|
||||
|
||||
@@ -376,14 +407,16 @@ public class Sample_x86 {
|
||||
u.emu_start(ADDRESS, ADDRESS + X86_CODE32_MEM_READ.length, 0, 0);
|
||||
} catch (UnicornException uex) {
|
||||
int err = u.errno();
|
||||
System.out.printf("Failed on u.emu_start() with error returned: %s\n", uex.getMessage());
|
||||
System.out.printf(
|
||||
"Failed on u.emu_start() with error returned: %s\n",
|
||||
uex.getMessage());
|
||||
}
|
||||
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long)u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long) u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
System.out.printf(">>> EDX = 0x%x\n", r_edx.intValue());
|
||||
|
||||
@@ -391,8 +424,7 @@ public class Sample_x86 {
|
||||
}
|
||||
|
||||
// emulate code that read invalid memory
|
||||
static void test_i386_invalid_mem_write()
|
||||
{
|
||||
static void test_i386_invalid_mem_write() {
|
||||
Long r_ecx = 0x1234L; // ECX register
|
||||
Long r_edx = 0x7890L; // EDX register
|
||||
|
||||
@@ -419,40 +451,45 @@ public class Sample_x86 {
|
||||
u.hook_add(new MyCodeHook(), 1, 0, null);
|
||||
|
||||
// intercept invalid memory events
|
||||
u.hook_add(new MyWriteInvalidHook(), Unicorn.UC_HOOK_MEM_WRITE_UNMAPPED, null);
|
||||
u.hook_add(new MyWriteInvalidHook(), Unicorn.UC_HOOK_MEM_WRITE_UNMAPPED,
|
||||
null);
|
||||
|
||||
// emulate machine code in infinite time
|
||||
try {
|
||||
u.emu_start(ADDRESS, ADDRESS + X86_CODE32_MEM_WRITE.length, 0, 0);
|
||||
} catch (UnicornException uex) {
|
||||
System.out.printf("Failed on uc_emu_start() with error returned: %s\n", uex.getMessage());
|
||||
System.out.printf(
|
||||
"Failed on uc_emu_start() with error returned: %s\n",
|
||||
uex.getMessage());
|
||||
}
|
||||
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long)u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long) u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
System.out.printf(">>> EDX = 0x%x\n", r_edx.intValue());
|
||||
|
||||
// read from memory
|
||||
byte tmp[] = u.mem_read(0xaaaaaaaa, 4);
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n", 0xaaaaaaaa, toInt(tmp));
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n", 0xaaaaaaaa,
|
||||
toInt(tmp));
|
||||
|
||||
try {
|
||||
u.mem_read(0xffffffaa, 4);
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n", 0xffffffaa, toInt(tmp));
|
||||
System.out.printf(">>> Read 4 bytes from [0x%x] = 0x%x\n",
|
||||
0xffffffaa, toInt(tmp));
|
||||
} catch (UnicornException uex) {
|
||||
System.out.printf(">>> Failed to read 4 bytes from [0x%x]\n", 0xffffffaa);
|
||||
System.out.printf(">>> Failed to read 4 bytes from [0x%x]\n",
|
||||
0xffffffaa);
|
||||
}
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
// emulate code that jump to invalid memory
|
||||
static void test_i386_jump_invalid()
|
||||
{
|
||||
static void test_i386_jump_invalid() {
|
||||
Long r_ecx = 0x1234L; // ECX register
|
||||
Long r_edx = 0x7890L; // EDX register
|
||||
|
||||
@@ -482,22 +519,23 @@ public class Sample_x86 {
|
||||
try {
|
||||
u.emu_start(ADDRESS, ADDRESS + X86_CODE32_JMP_INVALID.length, 0, 0);
|
||||
} catch (UnicornException uex) {
|
||||
System.out.printf("Failed on uc_emu_start() with error returned: %s\n", uex.getMessage());
|
||||
System.out.printf(
|
||||
"Failed on uc_emu_start() with error returned: %s\n",
|
||||
uex.getMessage());
|
||||
}
|
||||
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long)u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_edx = (Long) u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
System.out.printf(">>> ECX = 0x%x\n", r_ecx.intValue());
|
||||
System.out.printf(">>> EDX = 0x%x\n", r_edx.intValue());
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
static void test_x86_64()
|
||||
{
|
||||
static void test_x86_64() {
|
||||
long rax = 0x71f3029efd49d41dL;
|
||||
long rbx = 0xd87b45277f133ddbL;
|
||||
long rcx = 0xab40d1ffd8afc461L;
|
||||
@@ -548,7 +586,7 @@ public class Sample_x86 {
|
||||
u.hook_add(new MyBlockHook(), 1, 0, null);
|
||||
|
||||
// tracing all instructions in the range [ADDRESS, ADDRESS+20]
|
||||
u.hook_add(new MyCode64Hook(), ADDRESS, ADDRESS+20, null);
|
||||
u.hook_add(new MyCode64Hook(), ADDRESS, ADDRESS + 20, null);
|
||||
|
||||
// tracing all memory WRITE access (with @begin > @end)
|
||||
u.hook_add(new MyWrite64Hook(), 1, 0, null);
|
||||
@@ -563,20 +601,20 @@ public class Sample_x86 {
|
||||
// now print out some registers
|
||||
System.out.print(">>> Emulation done. Below is the CPU context\n");
|
||||
|
||||
Long r_rax = (Long)u.reg_read(Unicorn.UC_X86_REG_RAX);
|
||||
Long r_rbx = (Long)u.reg_read(Unicorn.UC_X86_REG_RBX);
|
||||
Long r_rcx = (Long)u.reg_read(Unicorn.UC_X86_REG_RCX);
|
||||
Long r_rdx = (Long)u.reg_read(Unicorn.UC_X86_REG_RDX);
|
||||
Long r_rsi = (Long)u.reg_read(Unicorn.UC_X86_REG_RSI);
|
||||
Long r_rdi = (Long)u.reg_read(Unicorn.UC_X86_REG_RDI);
|
||||
Long r_r8 = (Long)u.reg_read(Unicorn.UC_X86_REG_R8);
|
||||
Long r_r9 = (Long)u.reg_read(Unicorn.UC_X86_REG_R9);
|
||||
Long r_r10 = (Long)u.reg_read(Unicorn.UC_X86_REG_R10);
|
||||
Long r_r11 = (Long)u.reg_read(Unicorn.UC_X86_REG_R11);
|
||||
Long r_r12 = (Long)u.reg_read(Unicorn.UC_X86_REG_R12);
|
||||
Long r_r13 = (Long)u.reg_read(Unicorn.UC_X86_REG_R13);
|
||||
Long r_r14 = (Long)u.reg_read(Unicorn.UC_X86_REG_R14);
|
||||
Long r_r15 = (Long)u.reg_read(Unicorn.UC_X86_REG_R15);
|
||||
Long r_rax = (Long) u.reg_read(Unicorn.UC_X86_REG_RAX);
|
||||
Long r_rbx = (Long) u.reg_read(Unicorn.UC_X86_REG_RBX);
|
||||
Long r_rcx = (Long) u.reg_read(Unicorn.UC_X86_REG_RCX);
|
||||
Long r_rdx = (Long) u.reg_read(Unicorn.UC_X86_REG_RDX);
|
||||
Long r_rsi = (Long) u.reg_read(Unicorn.UC_X86_REG_RSI);
|
||||
Long r_rdi = (Long) u.reg_read(Unicorn.UC_X86_REG_RDI);
|
||||
Long r_r8 = (Long) u.reg_read(Unicorn.UC_X86_REG_R8);
|
||||
Long r_r9 = (Long) u.reg_read(Unicorn.UC_X86_REG_R9);
|
||||
Long r_r10 = (Long) u.reg_read(Unicorn.UC_X86_REG_R10);
|
||||
Long r_r11 = (Long) u.reg_read(Unicorn.UC_X86_REG_R11);
|
||||
Long r_r12 = (Long) u.reg_read(Unicorn.UC_X86_REG_R12);
|
||||
Long r_r13 = (Long) u.reg_read(Unicorn.UC_X86_REG_R13);
|
||||
Long r_r14 = (Long) u.reg_read(Unicorn.UC_X86_REG_R14);
|
||||
Long r_r15 = (Long) u.reg_read(Unicorn.UC_X86_REG_R15);
|
||||
|
||||
System.out.printf(">>> RAX = 0x%x\n", r_rax.longValue());
|
||||
System.out.printf(">>> RBX = 0x%x\n", r_rbx.longValue());
|
||||
@@ -596,8 +634,7 @@ public class Sample_x86 {
|
||||
u.close();
|
||||
}
|
||||
|
||||
static void test_x86_16()
|
||||
{
|
||||
static void test_x86_16() {
|
||||
Long eax = 7L;
|
||||
Long ebx = 5L;
|
||||
Long esi = 6L;
|
||||
@@ -627,13 +664,13 @@ public class Sample_x86 {
|
||||
|
||||
// read from memory
|
||||
byte[] tmp = u.mem_read(11, 1);
|
||||
System.out.printf(">>> Read 1 bytes from [0x%x] = 0x%x\n", 11, toInt(tmp));
|
||||
System.out.printf(">>> Read 1 bytes from [0x%x] = 0x%x\n", 11,
|
||||
toInt(tmp));
|
||||
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
if (args.length == 1) {
|
||||
if (args[0].equals("-32")) {
|
||||
test_i386();
|
||||
@@ -655,7 +692,7 @@ public class Sample_x86 {
|
||||
|
||||
// test memleak
|
||||
if (args[0].equals("-0")) {
|
||||
while(true) {
|
||||
while (true) {
|
||||
test_i386();
|
||||
// test_x86_64();
|
||||
}
|
||||
|
||||
@@ -31,16 +31,19 @@ public class Sample_x86_mmr {
|
||||
try {
|
||||
uc = new Unicorn(Unicorn.UC_ARCH_X86, Unicorn.UC_MODE_32);
|
||||
} catch (UnicornException uex) {
|
||||
System.out.println("Failed on uc_open() with error returned: " + uex);
|
||||
System.out
|
||||
.println("Failed on uc_open() with error returned: " + uex);
|
||||
return;
|
||||
}
|
||||
|
||||
// map 4k
|
||||
uc.mem_map(0x400000, 0x1000, Unicorn.UC_PROT_ALL);
|
||||
|
||||
X86_MMR ldtr1 = new X86_MMR(0x1111111122222222L, 0x33333333, 0x44444444, (short)0x5555);
|
||||
X86_MMR ldtr1 = new X86_MMR(0x1111111122222222L, 0x33333333, 0x44444444,
|
||||
(short) 0x5555);
|
||||
X86_MMR ldtr2;
|
||||
X86_MMR gdtr1 = new X86_MMR(0x6666666677777777L, 0x88888888, 0x99999999, (short)0xaaaa);
|
||||
X86_MMR gdtr1 = new X86_MMR(0x6666666677777777L, 0x88888888, 0x99999999,
|
||||
(short) 0xaaaa);
|
||||
X86_MMR gdtr2, gdtr3, gdtr4;
|
||||
|
||||
int eax;
|
||||
@@ -52,9 +55,9 @@ public class Sample_x86_mmr {
|
||||
uc.reg_write(Unicorn.UC_X86_REG_EAX, 0xddddddddL);
|
||||
|
||||
// read the registers back out
|
||||
eax = (int)((Long)uc.reg_read(Unicorn.UC_X86_REG_EAX)).longValue();
|
||||
ldtr2 = (X86_MMR)uc.reg_read(Unicorn.UC_X86_REG_LDTR);
|
||||
gdtr2 = (X86_MMR)uc.reg_read(Unicorn.UC_X86_REG_GDTR);
|
||||
eax = (int) ((Long) uc.reg_read(Unicorn.UC_X86_REG_EAX)).longValue();
|
||||
ldtr2 = (X86_MMR) uc.reg_read(Unicorn.UC_X86_REG_LDTR);
|
||||
gdtr2 = (X86_MMR) uc.reg_read(Unicorn.UC_X86_REG_GDTR);
|
||||
|
||||
System.out.printf(">>> EAX = 0x%x\n", eax);
|
||||
|
||||
@@ -69,8 +72,7 @@ public class Sample_x86_mmr {
|
||||
uc.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
test_x86_mmr();
|
||||
}
|
||||
|
||||
|
||||
@@ -25,12 +25,17 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
/* Sample code to trace code with Linux code with syscall */
|
||||
|
||||
import unicorn.*;
|
||||
import java.math.*;
|
||||
|
||||
public class Shellcode {
|
||||
|
||||
public static final byte[] X86_CODE32 = {-21,25,49,-64,49,-37,49,-46,49,-55,-80,4,-77,1,89,-78,5,-51,-128,49,-64,-80,1,49,-37,-51,-128,-24,-30,-1,-1,-1,104,101,108,108,111};
|
||||
public static final byte[] X86_CODE32_SELF = {-21,28,90,-119,-42,-117,2,102,61,-54,125,117,6,102,5,3,3,-119,2,-2,-62,61,65,65,65,65,117,-23,-1,-26,-24,-33,-1,-1,-1,49,-46,106,11,88,-103,82,104,47,47,115,104,104,47,98,105,110,-119,-29,82,83,-119,-31,-54,125,65,65,65,65,65,65,65,65};
|
||||
public static final byte[] X86_CODE32 = { -21, 25, 49, -64, 49, -37, 49,
|
||||
-46, 49, -55, -80, 4, -77, 1, 89, -78, 5, -51, -128, 49, -64, -80, 1,
|
||||
49, -37, -51, -128, -24, -30, -1, -1, -1, 104, 101, 108, 108, 111 };
|
||||
public static final byte[] X86_CODE32_SELF = { -21, 28, 90, -119, -42, -117,
|
||||
2, 102, 61, -54, 125, 117, 6, 102, 5, 3, 3, -119, 2, -2, -62, 61, 65,
|
||||
65, 65, 65, 117, -23, -1, -26, -24, -33, -1, -1, -1, 49, -46, 106, 11,
|
||||
88, -103, 82, 104, 47, 47, 115, 104, 104, 47, 98, 105, 110, -119, -29,
|
||||
82, 83, -119, -31, -54, 125, 65, 65, 65, 65, 65, 65, 65, 65 };
|
||||
|
||||
// memory address where emulation starts
|
||||
public static final int ADDRESS = 0x1000000;
|
||||
@@ -47,7 +52,7 @@ public class Shellcode {
|
||||
public static final byte[] toBytes(long val) {
|
||||
byte[] res = new byte[8];
|
||||
for (int i = 0; i < 8; i++) {
|
||||
res[i] = (byte)(val & 0xff);
|
||||
res[i] = (byte) (val & 0xff);
|
||||
val >>>= 8;
|
||||
}
|
||||
return res;
|
||||
@@ -56,10 +61,13 @@ public class Shellcode {
|
||||
public static class MyCodeHook implements CodeHook {
|
||||
public void hook(Unicorn u, long address, int size, Object user) {
|
||||
|
||||
System.out.print(String.format("Tracing instruction at 0x%x, instruction size = 0x%x\n", address, size));
|
||||
System.out.print(String.format(
|
||||
"Tracing instruction at 0x%x, instruction size = 0x%x\n",
|
||||
address, size));
|
||||
|
||||
Long r_eip = (Long)u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
System.out.print(String.format("*** EIP = %x ***: ", r_eip.intValue()));
|
||||
Long r_eip = (Long) u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
System.out.print(
|
||||
String.format("*** EIP = %x ***: ", r_eip.intValue()));
|
||||
|
||||
size = Math.min(16, size);
|
||||
|
||||
@@ -82,37 +90,42 @@ public class Shellcode {
|
||||
return;
|
||||
}
|
||||
|
||||
Long r_eax = (Long)u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
Long r_eip = (Long)u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
Long r_eax = (Long) u.reg_read(Unicorn.UC_X86_REG_EAX);
|
||||
Long r_eip = (Long) u.reg_read(Unicorn.UC_X86_REG_EIP);
|
||||
|
||||
switch (r_eax.intValue()) {
|
||||
default:
|
||||
System.out.print(String.format(">>> 0x%x: interrupt 0x%x, EAX = 0x%x\n", r_eip.intValue(), intno, r_eax.intValue()));
|
||||
System.out.print(
|
||||
String.format(">>> 0x%x: interrupt 0x%x, EAX = 0x%x\n",
|
||||
r_eip.intValue(), intno, r_eax.intValue()));
|
||||
break;
|
||||
case 1: // sys_exit
|
||||
System.out.print(String.format(">>> 0x%x: interrupt 0x%x, SYS_EXIT. quit!\n\n", r_eip.intValue(), intno));
|
||||
System.out.print(String.format(
|
||||
">>> 0x%x: interrupt 0x%x, SYS_EXIT. quit!\n\n",
|
||||
r_eip.intValue(), intno));
|
||||
u.emu_stop();
|
||||
break;
|
||||
case 4: // sys_write
|
||||
// ECX = buffer address
|
||||
r_ecx = (Long)u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
r_ecx = (Long) u.reg_read(Unicorn.UC_X86_REG_ECX);
|
||||
|
||||
// EDX = buffer size
|
||||
r_edx = (Long)u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
r_edx = (Long) u.reg_read(Unicorn.UC_X86_REG_EDX);
|
||||
|
||||
// read the buffer in
|
||||
size = (int)Math.min(256, r_edx);
|
||||
size = (int) Math.min(256, r_edx);
|
||||
|
||||
byte[] buffer = u.mem_read(r_ecx, size);
|
||||
System.out.print(String.format(">>> 0x%x: interrupt 0x%x, SYS_WRITE. buffer = 0x%x, size = %u, content = '%s'\n",
|
||||
r_eip.intValue(), intno, r_ecx.intValue(), r_edx.intValue(), new String(buffer)));
|
||||
System.out.print(String.format(
|
||||
">>> 0x%x: interrupt 0x%x, SYS_WRITE. buffer = 0x%x, size = %u, content = '%s'\n",
|
||||
r_eip.intValue(), intno, r_ecx.intValue(),
|
||||
r_edx.intValue(), new String(buffer)));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void test_i386()
|
||||
{
|
||||
static void test_i386() {
|
||||
Long r_esp = ADDRESS + 0x200000L; // ESP register
|
||||
|
||||
System.out.print("Emulate i386 code\n");
|
||||
@@ -146,8 +159,7 @@ public class Shellcode {
|
||||
u.close();
|
||||
}
|
||||
|
||||
public static void main(String args[])
|
||||
{
|
||||
public static void main(String args[]) {
|
||||
if (args.length == 1) {
|
||||
if ("-32".equals(args[0])) {
|
||||
test_i386();
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface Arm64Const {
|
||||
|
||||
// ARM64 CPU
|
||||
// ARM64 CPU
|
||||
|
||||
public static final int UC_CPU_ARM64_A57 = 0;
|
||||
public static final int UC_CPU_ARM64_A53 = 1;
|
||||
@@ -12,7 +12,7 @@ public interface Arm64Const {
|
||||
public static final int UC_CPU_ARM64_MAX = 3;
|
||||
public static final int UC_CPU_ARM64_ENDING = 4;
|
||||
|
||||
// ARM64 registers
|
||||
// ARM64 registers
|
||||
|
||||
public static final int UC_ARM64_REG_INVALID = 0;
|
||||
public static final int UC_ARM64_REG_X29 = 1;
|
||||
@@ -275,29 +275,29 @@ public interface Arm64Const {
|
||||
public static final int UC_ARM64_REG_V30 = 258;
|
||||
public static final int UC_ARM64_REG_V31 = 259;
|
||||
|
||||
// pseudo registers
|
||||
// pseudo registers
|
||||
public static final int UC_ARM64_REG_PC = 260;
|
||||
public static final int UC_ARM64_REG_CPACR_EL1 = 261;
|
||||
|
||||
// thread registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
// thread registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
public static final int UC_ARM64_REG_TPIDR_EL0 = 262;
|
||||
public static final int UC_ARM64_REG_TPIDRRO_EL0 = 263;
|
||||
public static final int UC_ARM64_REG_TPIDR_EL1 = 264;
|
||||
public static final int UC_ARM64_REG_PSTATE = 265;
|
||||
|
||||
// exception link registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
// exception link registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
public static final int UC_ARM64_REG_ELR_EL0 = 266;
|
||||
public static final int UC_ARM64_REG_ELR_EL1 = 267;
|
||||
public static final int UC_ARM64_REG_ELR_EL2 = 268;
|
||||
public static final int UC_ARM64_REG_ELR_EL3 = 269;
|
||||
|
||||
// stack pointers registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
// stack pointers registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
public static final int UC_ARM64_REG_SP_EL0 = 270;
|
||||
public static final int UC_ARM64_REG_SP_EL1 = 271;
|
||||
public static final int UC_ARM64_REG_SP_EL2 = 272;
|
||||
public static final int UC_ARM64_REG_SP_EL3 = 273;
|
||||
|
||||
// other CP15 registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
// other CP15 registers, depreciated, use UC_ARM64_REG_CP_REG instead
|
||||
public static final int UC_ARM64_REG_TTBR0_EL1 = 274;
|
||||
public static final int UC_ARM64_REG_TTBR1_EL1 = 275;
|
||||
public static final int UC_ARM64_REG_ESR_EL0 = 276;
|
||||
@@ -316,18 +316,18 @@ public interface Arm64Const {
|
||||
public static final int UC_ARM64_REG_VBAR_EL3 = 289;
|
||||
public static final int UC_ARM64_REG_CP_REG = 290;
|
||||
|
||||
// floating point control and status registers
|
||||
// floating point control and status registers
|
||||
public static final int UC_ARM64_REG_FPCR = 291;
|
||||
public static final int UC_ARM64_REG_FPSR = 292;
|
||||
public static final int UC_ARM64_REG_ENDING = 293;
|
||||
|
||||
// alias registers
|
||||
// alias registers
|
||||
public static final int UC_ARM64_REG_IP0 = 215;
|
||||
public static final int UC_ARM64_REG_IP1 = 216;
|
||||
public static final int UC_ARM64_REG_FP = 1;
|
||||
public static final int UC_ARM64_REG_LR = 2;
|
||||
|
||||
// ARM64 instructions
|
||||
// ARM64 instructions
|
||||
|
||||
public static final int UC_ARM64_INS_INVALID = 0;
|
||||
public static final int UC_ARM64_INS_MRS = 1;
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface ArmConst {
|
||||
|
||||
// ARM CPU
|
||||
// ARM CPU
|
||||
|
||||
public static final int UC_CPU_ARM_926 = 0;
|
||||
public static final int UC_CPU_ARM_946 = 1;
|
||||
@@ -42,7 +42,7 @@ public interface ArmConst {
|
||||
public static final int UC_CPU_ARM_MAX = 33;
|
||||
public static final int UC_CPU_ARM_ENDING = 34;
|
||||
|
||||
// ARM registers
|
||||
// ARM registers
|
||||
|
||||
public static final int UC_ARM_REG_INVALID = 0;
|
||||
public static final int UC_ARM_REG_APSR = 1;
|
||||
@@ -186,7 +186,7 @@ public interface ArmConst {
|
||||
public static final int UC_ARM_REG_CP_REG = 139;
|
||||
public static final int UC_ARM_REG_ENDING = 140;
|
||||
|
||||
// alias registers
|
||||
// alias registers
|
||||
public static final int UC_ARM_REG_R13 = 12;
|
||||
public static final int UC_ARM_REG_R14 = 10;
|
||||
public static final int UC_ARM_REG_R15 = 11;
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface BlockHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, long address, int size, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface CodeHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, long address, int size, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -22,8 +22,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface EventMemHook extends Hook {
|
||||
|
||||
public boolean hook(Unicorn u, long address, int size, long value, Object user);
|
||||
|
||||
public boolean hook(Unicorn u, long address, int size, long value,
|
||||
Object user);
|
||||
}
|
||||
|
||||
|
||||
@@ -26,4 +26,5 @@ package unicorn;
|
||||
*/
|
||||
|
||||
public interface Hook {
|
||||
|
||||
}
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface InHook extends Hook {
|
||||
|
||||
public int hook(Unicorn u, int port, int size, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface InterruptHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, int intno, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface M68kConst {
|
||||
|
||||
// M68K CPU
|
||||
// M68K CPU
|
||||
|
||||
public static final int UC_CPU_M68K_M5206 = 0;
|
||||
public static final int UC_CPU_M68K_M68000 = 1;
|
||||
@@ -17,7 +17,7 @@ public interface M68kConst {
|
||||
public static final int UC_CPU_M68K_ANY = 8;
|
||||
public static final int UC_CPU_M68K_ENDING = 9;
|
||||
|
||||
// M68K registers
|
||||
// M68K registers
|
||||
|
||||
public static final int UC_M68K_REG_INVALID = 0;
|
||||
public static final int UC_M68K_REG_A0 = 1;
|
||||
|
||||
@@ -21,7 +21,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
package unicorn;
|
||||
|
||||
public interface MemHook extends ReadHook,WriteHook {
|
||||
public interface MemHook extends ReadHook, WriteHook {
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -22,7 +22,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public class MemRegion {
|
||||
|
||||
public long begin;
|
||||
public long end;
|
||||
public int perms;
|
||||
@@ -32,6 +31,4 @@ public class MemRegion {
|
||||
this.end = end;
|
||||
this.perms = perms;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface MipsConst {
|
||||
|
||||
// MIPS32 CPUS
|
||||
// MIPS32 CPUS
|
||||
|
||||
public static final int UC_CPU_MIPS32_4KC = 0;
|
||||
public static final int UC_CPU_MIPS32_4KM = 1;
|
||||
@@ -24,7 +24,7 @@ public interface MipsConst {
|
||||
public static final int UC_CPU_MIPS32_I7200 = 15;
|
||||
public static final int UC_CPU_MIPS32_ENDING = 16;
|
||||
|
||||
// MIPS64 CPUS
|
||||
// MIPS64 CPUS
|
||||
|
||||
public static final int UC_CPU_MIPS64_R4000 = 0;
|
||||
public static final int UC_CPU_MIPS64_VR5432 = 1;
|
||||
@@ -41,11 +41,11 @@ public interface MipsConst {
|
||||
public static final int UC_CPU_MIPS64_MIPS64DSPR2 = 12;
|
||||
public static final int UC_CPU_MIPS64_ENDING = 13;
|
||||
|
||||
// MIPS registers
|
||||
// MIPS registers
|
||||
|
||||
public static final int UC_MIPS_REG_INVALID = 0;
|
||||
|
||||
// General purpose registers
|
||||
// General purpose registers
|
||||
public static final int UC_MIPS_REG_PC = 1;
|
||||
public static final int UC_MIPS_REG_0 = 2;
|
||||
public static final int UC_MIPS_REG_1 = 3;
|
||||
@@ -80,7 +80,7 @@ public interface MipsConst {
|
||||
public static final int UC_MIPS_REG_30 = 32;
|
||||
public static final int UC_MIPS_REG_31 = 33;
|
||||
|
||||
// DSP registers
|
||||
// DSP registers
|
||||
public static final int UC_MIPS_REG_DSPCCOND = 34;
|
||||
public static final int UC_MIPS_REG_DSPCARRY = 35;
|
||||
public static final int UC_MIPS_REG_DSPEFI = 36;
|
||||
@@ -93,13 +93,13 @@ public interface MipsConst {
|
||||
public static final int UC_MIPS_REG_DSPPOS = 43;
|
||||
public static final int UC_MIPS_REG_DSPSCOUNT = 44;
|
||||
|
||||
// ACC registers
|
||||
// ACC registers
|
||||
public static final int UC_MIPS_REG_AC0 = 45;
|
||||
public static final int UC_MIPS_REG_AC1 = 46;
|
||||
public static final int UC_MIPS_REG_AC2 = 47;
|
||||
public static final int UC_MIPS_REG_AC3 = 48;
|
||||
|
||||
// COP registers
|
||||
// COP registers
|
||||
public static final int UC_MIPS_REG_CC0 = 49;
|
||||
public static final int UC_MIPS_REG_CC1 = 50;
|
||||
public static final int UC_MIPS_REG_CC2 = 51;
|
||||
@@ -109,7 +109,7 @@ public interface MipsConst {
|
||||
public static final int UC_MIPS_REG_CC6 = 55;
|
||||
public static final int UC_MIPS_REG_CC7 = 56;
|
||||
|
||||
// FPU registers
|
||||
// FPU registers
|
||||
public static final int UC_MIPS_REG_F0 = 57;
|
||||
public static final int UC_MIPS_REG_F1 = 58;
|
||||
public static final int UC_MIPS_REG_F2 = 59;
|
||||
@@ -151,7 +151,7 @@ public interface MipsConst {
|
||||
public static final int UC_MIPS_REG_FCC6 = 95;
|
||||
public static final int UC_MIPS_REG_FCC7 = 96;
|
||||
|
||||
// AFPR128
|
||||
// AFPR128
|
||||
public static final int UC_MIPS_REG_W0 = 97;
|
||||
public static final int UC_MIPS_REG_W1 = 98;
|
||||
public static final int UC_MIPS_REG_W2 = 99;
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface OutHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, int port, int size, int value, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface PpcConst {
|
||||
|
||||
// PPC CPU
|
||||
// PPC CPU
|
||||
|
||||
public static final int UC_CPU_PPC32_401 = 0;
|
||||
public static final int UC_CPU_PPC32_401A1 = 1;
|
||||
@@ -298,7 +298,7 @@ public interface PpcConst {
|
||||
public static final int UC_CPU_PPC32_7457A_V1_2 = 289;
|
||||
public static final int UC_CPU_PPC32_ENDING = 290;
|
||||
|
||||
// PPC64 CPU
|
||||
// PPC64 CPU
|
||||
|
||||
public static final int UC_CPU_PPC64_E5500 = 0;
|
||||
public static final int UC_CPU_PPC64_E6500 = 1;
|
||||
@@ -321,11 +321,11 @@ public interface PpcConst {
|
||||
public static final int UC_CPU_PPC64_POWER10_V1_0 = 18;
|
||||
public static final int UC_CPU_PPC64_ENDING = 19;
|
||||
|
||||
// PPC registers
|
||||
// PPC registers
|
||||
|
||||
public static final int UC_PPC_REG_INVALID = 0;
|
||||
|
||||
// General purpose registers
|
||||
// General purpose registers
|
||||
public static final int UC_PPC_REG_PC = 1;
|
||||
public static final int UC_PPC_REG_0 = 2;
|
||||
public static final int UC_PPC_REG_1 = 3;
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface ReadHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, long address, int size, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface RiscvConst {
|
||||
|
||||
// RISCV32 CPU
|
||||
// RISCV32 CPU
|
||||
|
||||
public static final int UC_CPU_RISCV32_ANY = 0;
|
||||
public static final int UC_CPU_RISCV32_BASE32 = 1;
|
||||
@@ -12,7 +12,7 @@ public interface RiscvConst {
|
||||
public static final int UC_CPU_RISCV32_SIFIVE_U34 = 3;
|
||||
public static final int UC_CPU_RISCV32_ENDING = 4;
|
||||
|
||||
// RISCV64 CPU
|
||||
// RISCV64 CPU
|
||||
|
||||
public static final int UC_CPU_RISCV64_ANY = 0;
|
||||
public static final int UC_CPU_RISCV64_BASE64 = 1;
|
||||
@@ -20,11 +20,11 @@ public interface RiscvConst {
|
||||
public static final int UC_CPU_RISCV64_SIFIVE_U54 = 3;
|
||||
public static final int UC_CPU_RISCV64_ENDING = 4;
|
||||
|
||||
// RISCV registers
|
||||
// RISCV registers
|
||||
|
||||
public static final int UC_RISCV_REG_INVALID = 0;
|
||||
|
||||
// General purpose registers
|
||||
// General purpose registers
|
||||
public static final int UC_RISCV_REG_X0 = 1;
|
||||
public static final int UC_RISCV_REG_X1 = 2;
|
||||
public static final int UC_RISCV_REG_X2 = 3;
|
||||
@@ -58,7 +58,7 @@ public interface RiscvConst {
|
||||
public static final int UC_RISCV_REG_X30 = 31;
|
||||
public static final int UC_RISCV_REG_X31 = 32;
|
||||
|
||||
// RISCV CSR
|
||||
// RISCV CSR
|
||||
public static final int UC_RISCV_REG_USTATUS = 33;
|
||||
public static final int UC_RISCV_REG_UIE = 34;
|
||||
public static final int UC_RISCV_REG_UTVEC = 35;
|
||||
@@ -185,7 +185,7 @@ public interface RiscvConst {
|
||||
public static final int UC_RISCV_REG_HTIMEDELTA = 156;
|
||||
public static final int UC_RISCV_REG_HTIMEDELTAH = 157;
|
||||
|
||||
// Floating-point registers
|
||||
// Floating-point registers
|
||||
public static final int UC_RISCV_REG_F0 = 158;
|
||||
public static final int UC_RISCV_REG_F1 = 159;
|
||||
public static final int UC_RISCV_REG_F2 = 160;
|
||||
@@ -221,7 +221,7 @@ public interface RiscvConst {
|
||||
public static final int UC_RISCV_REG_PC = 190;
|
||||
public static final int UC_RISCV_REG_ENDING = 191;
|
||||
|
||||
// Alias registers
|
||||
// Alias registers
|
||||
public static final int UC_RISCV_REG_ZERO = 1;
|
||||
public static final int UC_RISCV_REG_RA = 2;
|
||||
public static final int UC_RISCV_REG_SP = 3;
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface S390xConst {
|
||||
|
||||
// S390X CPU
|
||||
// S390X CPU
|
||||
|
||||
public static final int UC_CPU_S390X_Z900 = 0;
|
||||
public static final int UC_CPU_S390X_Z900_2 = 1;
|
||||
@@ -46,11 +46,11 @@ public interface S390xConst {
|
||||
public static final int UC_CPU_S390X_MAX = 37;
|
||||
public static final int UC_CPU_S390X_ENDING = 38;
|
||||
|
||||
// S390X registers
|
||||
// S390X registers
|
||||
|
||||
public static final int UC_S390X_REG_INVALID = 0;
|
||||
|
||||
// General purpose registers
|
||||
// General purpose registers
|
||||
public static final int UC_S390X_REG_R0 = 1;
|
||||
public static final int UC_S390X_REG_R1 = 2;
|
||||
public static final int UC_S390X_REG_R2 = 3;
|
||||
@@ -68,7 +68,7 @@ public interface S390xConst {
|
||||
public static final int UC_S390X_REG_R14 = 15;
|
||||
public static final int UC_S390X_REG_R15 = 16;
|
||||
|
||||
// Floating point registers
|
||||
// Floating point registers
|
||||
public static final int UC_S390X_REG_F0 = 17;
|
||||
public static final int UC_S390X_REG_F1 = 18;
|
||||
public static final int UC_S390X_REG_F2 = 19;
|
||||
@@ -102,7 +102,7 @@ public interface S390xConst {
|
||||
public static final int UC_S390X_REG_F30 = 47;
|
||||
public static final int UC_S390X_REG_F31 = 48;
|
||||
|
||||
// Access registers
|
||||
// Access registers
|
||||
public static final int UC_S390X_REG_A0 = 49;
|
||||
public static final int UC_S390X_REG_A1 = 50;
|
||||
public static final int UC_S390X_REG_A2 = 51;
|
||||
@@ -123,6 +123,6 @@ public interface S390xConst {
|
||||
public static final int UC_S390X_REG_PSWM = 66;
|
||||
public static final int UC_S390X_REG_ENDING = 67;
|
||||
|
||||
// Alias registers
|
||||
// Alias registers
|
||||
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface SparcConst {
|
||||
|
||||
// SPARC32 CPU
|
||||
// SPARC32 CPU
|
||||
|
||||
public static final int UC_CPU_SPARC32_FUJITSU_MB86904 = 0;
|
||||
public static final int UC_CPU_SPARC32_FUJITSU_MB86907 = 1;
|
||||
@@ -21,7 +21,7 @@ public interface SparcConst {
|
||||
public static final int UC_CPU_SPARC32_LEON3 = 12;
|
||||
public static final int UC_CPU_SPARC32_ENDING = 13;
|
||||
|
||||
// SPARC64 CPU
|
||||
// SPARC64 CPU
|
||||
|
||||
public static final int UC_CPU_SPARC64_FUJITSU = 0;
|
||||
public static final int UC_CPU_SPARC64_FUJITSU_III = 1;
|
||||
@@ -42,7 +42,7 @@ public interface SparcConst {
|
||||
public static final int UC_CPU_SPARC64_NEC_ULTRASPARC_I = 16;
|
||||
public static final int UC_CPU_SPARC64_ENDING = 17;
|
||||
|
||||
// SPARC registers
|
||||
// SPARC registers
|
||||
|
||||
public static final int UC_SPARC_REG_INVALID = 0;
|
||||
public static final int UC_SPARC_REG_F0 = 1;
|
||||
|
||||
@@ -22,8 +22,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface SyscallHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, Object user);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,14 +4,14 @@ package unicorn;
|
||||
|
||||
public interface TriCoreConst {
|
||||
|
||||
// TRICORE CPU
|
||||
// TRICORE CPU
|
||||
|
||||
public static final int UC_CPU_TRICORE_TC1796 = 0;
|
||||
public static final int UC_CPU_TRICORE_TC1797 = 1;
|
||||
public static final int UC_CPU_TRICORE_TC27X = 2;
|
||||
public static final int UC_CPU_TRICORE_ENDING = 3;
|
||||
|
||||
// TRICORE registers
|
||||
// TRICORE registers
|
||||
|
||||
public static final int UC_TRICORE_REG_INVALID = 0;
|
||||
public static final int UC_TRICORE_REG_A0 = 1;
|
||||
|
||||
@@ -21,9 +21,12 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
package unicorn;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Hashtable;
|
||||
|
||||
public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, SparcConst, MipsConst, X86Const {
|
||||
public class Unicorn
|
||||
implements UnicornConst, ArmConst, Arm64Const, M68kConst, SparcConst,
|
||||
MipsConst, X86Const {
|
||||
|
||||
public long eng;
|
||||
private int arch;
|
||||
@@ -33,7 +36,8 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
private long interruptHandle = 0;
|
||||
private long codeHandle = 0;
|
||||
|
||||
private Hashtable<Integer, Long> eventMemHandles = new Hashtable<Integer, Long>();
|
||||
private Hashtable<Integer, Long> eventMemHandles =
|
||||
new Hashtable<Integer, Long>();
|
||||
private long readInvalidHandle = 0;
|
||||
private long writeInvalidHandle = 0;
|
||||
private long fetchProtHandle = 0;
|
||||
@@ -49,6 +53,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
private class Tuple {
|
||||
public Hook function;
|
||||
public Object data;
|
||||
|
||||
public Tuple(Hook f, Object d) {
|
||||
function = f;
|
||||
data = d;
|
||||
@@ -64,16 +69,20 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
private ArrayList<Tuple> outList = new ArrayList<Tuple>();
|
||||
private ArrayList<Tuple> syscallList = new ArrayList<Tuple>();
|
||||
|
||||
private Hashtable<Integer, ArrayList<Tuple> > eventMemLists = new Hashtable<Integer, ArrayList<Tuple> >();
|
||||
private Hashtable<Integer, ArrayList<Tuple>> eventMemLists =
|
||||
new Hashtable<Integer, ArrayList<Tuple>>();
|
||||
|
||||
private ArrayList<ArrayList<Tuple>> allLists = new ArrayList<ArrayList<Tuple>>();
|
||||
private ArrayList<ArrayList<Tuple>> allLists =
|
||||
new ArrayList<ArrayList<Tuple>>();
|
||||
|
||||
private static Hashtable<Integer,Integer> eventMemMap = new Hashtable<Integer,Integer>();
|
||||
private static Hashtable<Long,Unicorn> unicorns = new Hashtable<Long,Unicorn>();
|
||||
private static Hashtable<Integer, Integer> eventMemMap =
|
||||
new Hashtable<Integer, Integer>();
|
||||
private static Hashtable<Long, Unicorn> unicorns =
|
||||
new Hashtable<Long, Unicorn>();
|
||||
|
||||
//required to load native method implementations
|
||||
// required to load native method implementations
|
||||
static {
|
||||
System.loadLibrary("unicorn_java"); //loads unicorn.dll or libunicorn.so
|
||||
System.loadLibrary("unicorn_java"); // loads unicorn.dll or libunicorn.so
|
||||
eventMemMap.put(UC_HOOK_MEM_READ_UNMAPPED, UC_MEM_READ_UNMAPPED);
|
||||
eventMemMap.put(UC_HOOK_MEM_WRITE_UNMAPPED, UC_MEM_WRITE_UNMAPPED);
|
||||
eventMemMap.put(UC_HOOK_MEM_FETCH_UNMAPPED, UC_MEM_FETCH_UNMAPPED);
|
||||
@@ -86,7 +95,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
eventMemMap.put(UC_HOOK_MEM_READ_AFTER, UC_MEM_READ_AFTER);
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_BLOCK callbacks registered for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_BLOCK
|
||||
@@ -100,13 +109,13 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
Unicorn u = unicorns.get(eng);
|
||||
if (u != null) {
|
||||
for (Tuple p : u.blockList) {
|
||||
BlockHook bh = (BlockHook)p.function;
|
||||
BlockHook bh = (BlockHook) p.function;
|
||||
bh.hook(u, address, size, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_INTR callbacks registered for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_INTR
|
||||
@@ -119,13 +128,13 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
Unicorn u = unicorns.get(eng);
|
||||
if (u != null) {
|
||||
for (Tuple p : u.intrList) {
|
||||
InterruptHook ih = (InterruptHook)p.function;
|
||||
InterruptHook ih = (InterruptHook) p.function;
|
||||
ih.hook(u, intno, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_CODE callbacks registered for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_CODE
|
||||
@@ -139,14 +148,15 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
Unicorn u = unicorns.get(eng);
|
||||
if (u != null) {
|
||||
for (Tuple p : u.codeList) {
|
||||
CodeHook ch = (CodeHook)p.function;
|
||||
CodeHook ch = (CodeHook) p.function;
|
||||
ch.hook(u, address, size, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Invoke all UC_HOOK_MEM_XXX_UNMAPPED and/or UC_HOOK_MEM_XXX_PROT callbacks registered
|
||||
/**
|
||||
* Invoke all UC_HOOK_MEM_XXX_UNMAPPED and/or UC_HOOK_MEM_XXX_PROT callbacks
|
||||
* registered
|
||||
* for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_MEM_XXX_UNMAPPED or UC_HOOK_MEM_XXX_PROT
|
||||
@@ -155,18 +165,21 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
* @param type The type of event that is taking place
|
||||
* @param address Address of instruction being executed
|
||||
* @param size Size of data being read or written
|
||||
* @param value Value of data being written to memory, or irrelevant if type = READ.
|
||||
* @param value Value of data being written to memory, or irrelevant if type =
|
||||
* READ.
|
||||
* @return true to continue, or false to stop program (due to invalid memory).
|
||||
* @see hook_add, unicorn.EventMemHook
|
||||
*/
|
||||
private static boolean invokeEventMemCallbacks(long eng, int type, long address, int size, long value) {
|
||||
private static boolean invokeEventMemCallbacks(long eng, int type,
|
||||
long address, int size,
|
||||
long value) {
|
||||
Unicorn u = unicorns.get(eng);
|
||||
boolean result = true;
|
||||
if (u != null) {
|
||||
ArrayList<Tuple> funcList = u.eventMemLists.get(type);
|
||||
if (funcList != null) {
|
||||
for (Tuple p : funcList) {
|
||||
EventMemHook emh = (EventMemHook)p.function;
|
||||
EventMemHook emh = (EventMemHook) p.function;
|
||||
result &= emh.hook(u, address, size, value, p.data);
|
||||
}
|
||||
}
|
||||
@@ -174,7 +187,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_MEM_READ callbacks registered for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_MEM_READ
|
||||
@@ -188,13 +201,13 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
Unicorn u = unicorns.get(eng);
|
||||
if (u != null) {
|
||||
for (Tuple p : u.readList) {
|
||||
ReadHook rh = (ReadHook)p.function;
|
||||
ReadHook rh = (ReadHook) p.function;
|
||||
rh.hook(u, address, size, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_MEM_WRITE callbacks registered for a specific Unicorn.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
* for UC_HOOK_MEM_WRITE
|
||||
@@ -205,17 +218,18 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
* @param value value being written
|
||||
* @see hook_add, unicorn.WriteHook
|
||||
*/
|
||||
private static void invokeWriteCallbacks(long eng, long address, int size, long value) {
|
||||
private static void invokeWriteCallbacks(long eng, long address, int size,
|
||||
long value) {
|
||||
Unicorn u = unicorns.get(eng);
|
||||
if (u != null) {
|
||||
for (Tuple p : u.writeList) {
|
||||
WriteHook wh = (WriteHook)p.function;
|
||||
WriteHook wh = (WriteHook) p.function;
|
||||
wh.hook(u, address, size, value, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_INSN callbacks registered for a specific Unicorn.
|
||||
* This is specifically for the x86 IN instruction.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
@@ -232,14 +246,14 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
int result = 0;
|
||||
if (u != null) {
|
||||
for (Tuple p : u.inList) {
|
||||
InHook ih = (InHook)p.function;
|
||||
InHook ih = (InHook) p.function;
|
||||
result = ih.hook(u, port, size, p.data);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_INSN callbacks registered for a specific Unicorn.
|
||||
* This is specifically for the x86 OUT instruction.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
@@ -250,18 +264,19 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
* @param size Data size (1/2/4) to be written to this port
|
||||
* @see hook_add, unicorn.OutHook
|
||||
*/
|
||||
private static void invokeOutCallbacks(long eng, int port, int size, int value) {
|
||||
private static void invokeOutCallbacks(long eng, int port, int size,
|
||||
int value) {
|
||||
Unicorn u = unicorns.get(eng);
|
||||
int result = 0;
|
||||
if (u != null) {
|
||||
for (Tuple p : u.outList) {
|
||||
OutHook oh = (OutHook)p.function;
|
||||
OutHook oh = (OutHook) p.function;
|
||||
oh.hook(u, port, size, value, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Invoke all UC_HOOK_INSN callbacks registered for a specific Unicorn.
|
||||
* This is specifically for the x86 SYSCALL and SYSENTER instruction.
|
||||
* This function gets invoked from the native C callback registered for
|
||||
@@ -275,29 +290,32 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
int result = 0;
|
||||
if (u != null) {
|
||||
for (Tuple p : u.syscallList) {
|
||||
SyscallHook sh = (SyscallHook)p.function;
|
||||
SyscallHook sh = (SyscallHook) p.function;
|
||||
sh.hook(u, p.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Write to register.
|
||||
*
|
||||
* @param regid Register ID that is to be modified.
|
||||
* @param value Number containing the new register value
|
||||
*/
|
||||
private native void reg_write_num(int regid, Number value) throws UnicornException;
|
||||
private native void reg_write_num(int regid, Number value)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Write to register.
|
||||
*
|
||||
* @param regid Register ID that is to be modified.
|
||||
* @param value X86 specific memory management register containing the new register value
|
||||
* @param value X86 specific memory management register containing the new
|
||||
* register value
|
||||
*/
|
||||
private native void reg_write_mmr(int regid, X86_MMR value) throws UnicornException;
|
||||
private native void reg_write_mmr(int regid, X86_MMR value)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Read register value.
|
||||
*
|
||||
* @param regid Register ID that is to be retrieved.
|
||||
@@ -305,7 +323,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
private native Number reg_read_num(int regid) throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Read register value.
|
||||
*
|
||||
* @param regid Register ID that is to be retrieved.
|
||||
@@ -313,7 +331,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
private native Number reg_read_mmr(int regid) throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Native access to uc_open
|
||||
*
|
||||
* @param arch Architecture type (UC_ARCH_*)
|
||||
@@ -321,7 +339,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
private native long open(int arch, int mode) throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Create a new Unicorn object
|
||||
*
|
||||
* @param arch Architecture type (UC_ARCH_*)
|
||||
@@ -330,7 +348,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*
|
||||
*/
|
||||
public Unicorn(int arch, int mode) throws UnicornException {
|
||||
//remember these in case we need arch specific code
|
||||
// remember these in case we need arch specific code
|
||||
this.arch = arch;
|
||||
this.mode = mode;
|
||||
eng = open(arch, mode);
|
||||
@@ -345,7 +363,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
allLists.add(syscallList);
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Perform native cleanup tasks associated with a Unicorn object
|
||||
*
|
||||
*/
|
||||
@@ -354,16 +372,17 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
close();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Return combined API version & major and minor version numbers.
|
||||
*
|
||||
* @return hexadecimal number as (major << 8 | minor), which encodes both major & minor versions.
|
||||
* @return hexadecimal number as (major << 8 | minor), which encodes both major
|
||||
* & minor versions.
|
||||
*
|
||||
* For example Unicorn version 1.2 whould yield 0x0102
|
||||
*/
|
||||
public native static int version();
|
||||
|
||||
/**
|
||||
/**
|
||||
* Determine if the given architecture is supported by this library.
|
||||
*
|
||||
* @param arch Architecture type (UC_ARCH_*)
|
||||
@@ -372,13 +391,13 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
public native static boolean arch_supported(int arch);
|
||||
|
||||
/**
|
||||
/**
|
||||
* Close the underlying uc_engine* eng associated with this Unicorn object
|
||||
*
|
||||
*/
|
||||
public native void close() throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Query internal status of engine.
|
||||
*
|
||||
* @param type query type. See UC_QUERY_*
|
||||
@@ -389,7 +408,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
public native int query(int type) throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Report the last error number when some API function fail.
|
||||
* Like glibc's errno, uc_errno might not retain its old value once accessed.
|
||||
*
|
||||
@@ -398,7 +417,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
public native int errno();
|
||||
|
||||
/**
|
||||
/**
|
||||
* Return a string describing given error code.
|
||||
*
|
||||
* @param code Error code (see UC_ERR_* above)
|
||||
@@ -407,17 +426,18 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
public native static String strerror(int code);
|
||||
|
||||
/**
|
||||
/**
|
||||
* Write to register.
|
||||
*
|
||||
* @deprecated use reg_write(int regid, Object value) instead
|
||||
* @param regid Register ID that is to be modified.
|
||||
* @param value Array containing value that will be written into register @regid
|
||||
*/
|
||||
@Deprecated
|
||||
public native void reg_write(int regid, byte[] value) throws UnicornException;
|
||||
@Deprecated
|
||||
public native void reg_write(int regid, byte[] value)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Write to register.
|
||||
*
|
||||
* @param regid Register ID that is to be modified.
|
||||
@@ -426,19 +446,17 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
*/
|
||||
public void reg_write(int regid, Object value) throws UnicornException {
|
||||
if (value instanceof Number) {
|
||||
reg_write_num(regid, (Number)value);
|
||||
}
|
||||
else if (arch == UC_ARCH_X86 && value instanceof X86_MMR) {
|
||||
reg_write_num(regid, (Number) value);
|
||||
} else if (arch == UC_ARCH_X86 && value instanceof X86_MMR) {
|
||||
if (regid >= UC_X86_REG_IDTR && regid <= UC_X86_REG_TR) {
|
||||
reg_write_mmr(regid, (X86_MMR)value);
|
||||
reg_write_mmr(regid, (X86_MMR) value);
|
||||
}
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
throw new ClassCastException("Invalid value type");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Read register value.
|
||||
*
|
||||
* @deprecated use Object reg_read(int regid) instead
|
||||
@@ -446,10 +464,10 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
* @param regsz Size of the register being retrieved.
|
||||
* @return Byte array containing the requested register value.
|
||||
*/
|
||||
@Deprecated
|
||||
@Deprecated
|
||||
public native byte[] reg_read(int regid, int regsz) throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Read register value.
|
||||
*
|
||||
* @param regid Register ID that is to be retrieved.
|
||||
@@ -457,21 +475,22 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
* other custom class used to represent register values
|
||||
*/
|
||||
public Object reg_read(int regid) throws UnicornException {
|
||||
if (arch == UC_ARCH_X86 && regid >= UC_X86_REG_IDTR && regid <= UC_X86_REG_TR) {
|
||||
if (arch == UC_ARCH_X86 && regid >= UC_X86_REG_IDTR &&
|
||||
regid <= UC_X86_REG_TR) {
|
||||
return reg_read_mmr(regid);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
return reg_read_num(regid);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Batch write register values. regids.length == vals.length or UC_ERR_ARG
|
||||
*
|
||||
* @param regids Array of register IDs to be written.
|
||||
* @param vals Array of register values to be written.
|
||||
*/
|
||||
public void reg_write_batch(int regids[], Object vals[]) throws UnicornException {
|
||||
public void reg_write_batch(int regids[], Object vals[])
|
||||
throws UnicornException {
|
||||
if (regids.length != vals.length) {
|
||||
throw new UnicornException(strerror(UC_ERR_ARG));
|
||||
}
|
||||
@@ -480,7 +499,7 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Batch read register values.
|
||||
*
|
||||
* @param regids Array of register IDs to be read.
|
||||
@@ -494,181 +513,232 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
return vals;
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Write to memory.
|
||||
*
|
||||
* @param address Start addres of the memory region to be written.
|
||||
* @param bytes The values to be written into memory. bytes.length bytes will be written.
|
||||
* @param bytes The values to be written into memory. bytes.length bytes will
|
||||
* be written.
|
||||
*/
|
||||
public native void mem_write(long address, byte[] bytes) throws UnicornException;
|
||||
public native void mem_write(long address, byte[] bytes)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Read memory contents.
|
||||
*
|
||||
* @param address Start addres of the memory region to be read.
|
||||
* @param size Number of bytes to be retrieved.
|
||||
* @return Byte array containing the contents of the requested memory range.
|
||||
*/
|
||||
public native byte[] mem_read(long address, long size) throws UnicornException;
|
||||
public native byte[] mem_read(long address, long size)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Emulate machine code in a specific duration of time.
|
||||
*
|
||||
* @param begin Address where emulation starts
|
||||
* @param until Address where emulation stops (i.e when this address is hit)
|
||||
* @param timeout Duration to emulate the code (in microseconds). When this value is 0, we will emulate the code in infinite time, until the code is finished.
|
||||
* @param count The number of instructions to be emulated. When this value is 0, we will emulate all the code available, until the code is finished.
|
||||
* @param timeout Duration to emulate the code (in microseconds). When this
|
||||
* value is 0, we will emulate the code in infinite time, until
|
||||
* the code is finished.
|
||||
* @param count The number of instructions to be emulated. When this value is
|
||||
* 0, we will emulate all the code available, until the code is
|
||||
* finished.
|
||||
*/
|
||||
public native void emu_start(long begin, long until, long timeout, long count) throws UnicornException;
|
||||
public native void emu_start(long begin, long until, long timeout,
|
||||
long count)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Stop emulation (which was started by emu_start() ).
|
||||
* This is typically called from callback functions registered via tracing APIs.
|
||||
* NOTE: for now, this will stop the execution only after the current block.
|
||||
*/
|
||||
public native void emu_stop() throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Hook registration helper for hook types that require no additional arguments.
|
||||
*
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn object
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn
|
||||
* object
|
||||
* @param type UC_HOOK_* hook type
|
||||
* @return Unicorn uch returned for registered hook function
|
||||
*/
|
||||
private native static long registerHook(long eng, int type);
|
||||
|
||||
/**
|
||||
/**
|
||||
* Hook registration helper for hook types that require one additional argument.
|
||||
*
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn object
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn
|
||||
* object
|
||||
* @param type UC_HOOK_* hook type
|
||||
* @param arg1 Additional varargs argument
|
||||
* @return Unicorn uch returned for registered hook function
|
||||
*/
|
||||
private native static long registerHook(long eng, int type, int arg1);
|
||||
|
||||
/**
|
||||
* Hook registration helper for hook types that require two additional arguments.
|
||||
/**
|
||||
* Hook registration helper for hook types that require two additional
|
||||
* arguments.
|
||||
*
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn object
|
||||
* @param eng Internal unicorn uc_engine* eng associated with hooking Unicorn
|
||||
* object
|
||||
* @param type UC_HOOK_* hook type
|
||||
* @param arg1 First additional varargs argument
|
||||
* @param arg2 Second additional varargs argument
|
||||
* @return Unicorn uch returned for registered hook function
|
||||
*/
|
||||
private native static long registerHook(long eng, int type, long arg1, long arg2);
|
||||
private native static long registerHook(long eng, int type, long arg1,
|
||||
long arg2);
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_BLOCK hooks. The registered callback function will be
|
||||
* invoked when a basic block is entered and the address of the basic block (BB) falls in the
|
||||
* range begin <= BB <= end. For the special case in which begin > end, the callback will be
|
||||
/**
|
||||
* Hook registration for UC_HOOK_BLOCK hooks. The registered callback function
|
||||
* will be
|
||||
* invoked when a basic block is entered and the address of the basic block (BB)
|
||||
* falls in the
|
||||
* range begin <= BB <= end. For the special case in which begin > end, the
|
||||
* callback will be
|
||||
* invoked whenver any basic block is entered.
|
||||
*
|
||||
* @param callback Implementation of a BlockHook interface
|
||||
* @param begin Start address of hooking range
|
||||
* @param end End address of hooking range
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(BlockHook callback, long begin, long end, Object user_data) throws UnicornException {
|
||||
public void hook_add(BlockHook callback, long begin, long end,
|
||||
Object user_data)
|
||||
throws UnicornException {
|
||||
if (blockHandle == 0) {
|
||||
blockHandle = registerHook(eng, UC_HOOK_BLOCK, begin, end);
|
||||
}
|
||||
blockList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INTR hooks. The registered callback function will be
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INTR hooks. The registered callback function
|
||||
* will be
|
||||
* invoked whenever an interrupt instruction is executed.
|
||||
*
|
||||
* @param callback Implementation of a InterruptHook interface
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(InterruptHook callback, Object user_data) throws UnicornException {
|
||||
public void hook_add(InterruptHook callback, Object user_data)
|
||||
throws UnicornException {
|
||||
if (interruptHandle == 0) {
|
||||
interruptHandle = registerHook(eng, UC_HOOK_INTR);
|
||||
}
|
||||
intrList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_CODE hooks. The registered callback function will be
|
||||
* invoked when an instruction is executed from the address range begin <= PC <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL instructions.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_CODE hooks. The registered callback function
|
||||
* will be
|
||||
* invoked when an instruction is executed from the address range begin <= PC <=
|
||||
* end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL
|
||||
* instructions.
|
||||
*
|
||||
* @param callback Implementation of a CodeHook interface
|
||||
* @param begin Start address of hooking range
|
||||
* @param end End address of hooking range
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(CodeHook callback, long begin, long end, Object user_data) throws UnicornException {
|
||||
public void hook_add(CodeHook callback, long begin, long end,
|
||||
Object user_data)
|
||||
throws UnicornException {
|
||||
if (codeHandle == 0) {
|
||||
codeHandle = registerHook(eng, UC_HOOK_CODE, begin, end);
|
||||
}
|
||||
codeList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_READ hooks. The registered callback function will be
|
||||
* invoked whenever a memory read is performed within the address range begin <= read_addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL memory reads.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_READ hooks. The registered callback
|
||||
* function will be
|
||||
* invoked whenever a memory read is performed within the address range begin <=
|
||||
* read_addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL
|
||||
* memory reads.
|
||||
*
|
||||
* @param callback Implementation of a ReadHook interface
|
||||
* @param begin Start address of memory read range
|
||||
* @param end End address of memory read range
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(ReadHook callback, long begin, long end, Object user_data) throws UnicornException {
|
||||
public void hook_add(ReadHook callback, long begin, long end,
|
||||
Object user_data)
|
||||
throws UnicornException {
|
||||
if (readHandle == 0) {
|
||||
readHandle = registerHook(eng, UC_HOOK_MEM_READ, begin, end);
|
||||
}
|
||||
readList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_WRITE hooks. The registered callback function will be
|
||||
* invoked whenever a memory write is performed within the address range begin <= write_addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL memory writes.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_WRITE hooks. The registered callback
|
||||
* function will be
|
||||
* invoked whenever a memory write is performed within the address range begin
|
||||
* <= write_addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL
|
||||
* memory writes.
|
||||
*
|
||||
* @param callback Implementation of a WriteHook interface
|
||||
* @param begin Start address of memory write range
|
||||
* @param end End address of memory write range
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(WriteHook callback, long begin, long end, Object user_data) throws UnicornException {
|
||||
public void hook_add(WriteHook callback, long begin, long end,
|
||||
Object user_data)
|
||||
throws UnicornException {
|
||||
if (writeHandle == 0) {
|
||||
writeHandle = registerHook(eng, UC_HOOK_MEM_WRITE, begin, end);
|
||||
}
|
||||
writeList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_WRITE | UC_HOOK_MEM_WRITE hooks. The registered callback function will be
|
||||
* invoked whenever a memory write or read is performed within the address range begin <= addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL memory writes.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_WRITE | UC_HOOK_MEM_WRITE hooks. The
|
||||
* registered callback function will be
|
||||
* invoked whenever a memory write or read is performed within the address range
|
||||
* begin <= addr <= end. For
|
||||
* the special case in which begin > end, the callback will be invoked for ALL
|
||||
* memory writes.
|
||||
*
|
||||
* @param callback Implementation of a MemHook interface
|
||||
* @param begin Start address of memory range
|
||||
* @param end End address of memory range
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(MemHook callback, long begin, long end, Object user_data) throws UnicornException {
|
||||
hook_add((ReadHook)callback, begin, end, user_data);
|
||||
hook_add((WriteHook)callback, begin, end, user_data);
|
||||
public void hook_add(MemHook callback, long begin, long end,
|
||||
Object user_data)
|
||||
throws UnicornException {
|
||||
hook_add((ReadHook) callback, begin, end, user_data);
|
||||
hook_add((WriteHook) callback, begin, end, user_data);
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_XXX_UNMAPPED and UC_HOOK_MEM_XXX_PROT hooks.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_MEM_XXX_UNMAPPED and UC_HOOK_MEM_XXX_PROT
|
||||
* hooks.
|
||||
* The registered callback function will be invoked whenever a read or write is
|
||||
* attempted from an invalid or protected memory address.
|
||||
*
|
||||
* @param callback Implementation of a EventMemHook interface
|
||||
* @param type Type of memory event being hooked such as UC_HOOK_MEM_READ_UNMAPPED or UC_HOOK_MEM_WRITE_PROT
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param type Type of memory event being hooked such as
|
||||
* UC_HOOK_MEM_READ_UNMAPPED or UC_HOOK_MEM_WRITE_PROT
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(EventMemHook callback, int type, Object user_data) throws UnicornException {
|
||||
//test all of the EventMem related bits in type
|
||||
public void hook_add(EventMemHook callback, int type, Object user_data)
|
||||
throws UnicornException {
|
||||
// test all of the EventMem related bits in type
|
||||
for (Integer htype : eventMemMap.keySet()) {
|
||||
if ((type & htype) != 0) { //the 'htype' bit is set in type
|
||||
if ((type & htype) != 0) { // the 'htype' bit is set in type
|
||||
Long handle = eventMemHandles.get(htype);
|
||||
if (handle == null) {
|
||||
eventMemHandles.put(htype, registerHook(eng, htype));
|
||||
@@ -685,44 +755,55 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 IN instruction only). The registered callback
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 IN instruction only). The
|
||||
* registered callback
|
||||
* function will be invoked whenever an x86 IN instruction is executed.
|
||||
*
|
||||
* @param callback Implementation of a InHook interface
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(InHook callback, Object user_data) throws UnicornException {
|
||||
public void hook_add(InHook callback, Object user_data)
|
||||
throws UnicornException {
|
||||
if (inHandle == 0) {
|
||||
inHandle = registerHook(eng, UC_HOOK_INSN, Unicorn.UC_X86_INS_IN);
|
||||
}
|
||||
inList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 OUT instruction only). The registered callback
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 OUT instruction only). The
|
||||
* registered callback
|
||||
* function will be invoked whenever an x86 OUT instruction is executed.
|
||||
*
|
||||
* @param callback Implementation of a OutHook interface
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(OutHook callback, Object user_data) throws UnicornException {
|
||||
public void hook_add(OutHook callback, Object user_data)
|
||||
throws UnicornException {
|
||||
if (outHandle == 0) {
|
||||
outHandle = registerHook(eng, UC_HOOK_INSN, Unicorn.UC_X86_INS_OUT);
|
||||
}
|
||||
outList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 SYSCALL/SYSENTER instruction only). The registered callback
|
||||
* function will be invoked whenever an x86 SYSCALL or SYSENTER instruction is executed.
|
||||
/**
|
||||
* Hook registration for UC_HOOK_INSN hooks (x86 SYSCALL/SYSENTER instruction
|
||||
* only). The registered callback
|
||||
* function will be invoked whenever an x86 SYSCALL or SYSENTER instruction is
|
||||
* executed.
|
||||
*
|
||||
* @param callback Implementation of a SyscallHook interface
|
||||
* @param user_data User data to be passed to the callback function each time the event is triggered
|
||||
* @param user_data User data to be passed to the callback function each time
|
||||
* the event is triggered
|
||||
*/
|
||||
public void hook_add(SyscallHook callback, Object user_data) throws UnicornException {
|
||||
public void hook_add(SyscallHook callback, Object user_data)
|
||||
throws UnicornException {
|
||||
if (syscallHandle == 0) {
|
||||
syscallHandle = registerHook(eng, UC_HOOK_INSN, Unicorn.UC_X86_INS_SYSCALL);
|
||||
syscallHandle =
|
||||
registerHook(eng, UC_HOOK_INSN, Unicorn.UC_X86_INS_SYSCALL);
|
||||
}
|
||||
syscallList.add(new Tuple(callback, user_data));
|
||||
}
|
||||
@@ -738,94 +819,104 @@ public class Unicorn implements UnicornConst, ArmConst, Arm64Const, M68kConst, S
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Map a range of memory.
|
||||
*
|
||||
* @param address Base address of the memory range
|
||||
* @param size Size of the memory block.
|
||||
* @param perms Permissions on the memory block. A combination of UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
* @param perms Permissions on the memory block. A combination of
|
||||
* UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
*/
|
||||
public native void mem_map(long address, long size, int perms) throws UnicornException;
|
||||
public native void mem_map(long address, long size, int perms)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Map existing host memory in for emulation.
|
||||
* This API adds a memory region that can be used by emulation.
|
||||
*
|
||||
* @param address Base address of the memory range
|
||||
* @param size Size of the memory block.
|
||||
* @param perms Permissions on the memory block. A combination of UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
* @param ptr Block of host memory backing the newly mapped memory. This block is
|
||||
* expected to be an equal or larger size than provided, and be mapped with at
|
||||
* least PROT_READ | PROT_WRITE. If it is not, the resulting behavior is undefined.
|
||||
* @param perms Permissions on the memory block. A combination of
|
||||
* UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
* @param ptr Block of host memory backing the newly mapped memory. This
|
||||
* block is
|
||||
* expected to be an equal or larger size than provided, and be
|
||||
* mapped with at
|
||||
* least PROT_READ | PROT_WRITE. If it is not, the resulting
|
||||
* behavior is undefined.
|
||||
*/
|
||||
public native void mem_map_ptr(long address, long size, int perms, byte[] block) throws UnicornException;
|
||||
public native void mem_map_ptr(long address, long size, int perms,
|
||||
byte[] block)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Unmap a range of memory.
|
||||
*
|
||||
* @param address Base address of the memory range
|
||||
* @param size Size of the memory block.
|
||||
*/
|
||||
public native void mem_unmap(long address, long size) throws UnicornException;
|
||||
public native void mem_unmap(long address, long size)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Change permissions on a range of memory.
|
||||
*
|
||||
* @param address Base address of the memory range
|
||||
* @param size Size of the memory block.
|
||||
* @param perms New permissions on the memory block. A combination of UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
* @param perms New permissions on the memory block. A combination of
|
||||
* UC_PROT_READ, UC_PROT_WRITE, UC_PROT_EXEC
|
||||
*/
|
||||
public native void mem_protect(long address, long size, int perms) throws UnicornException;
|
||||
public native void mem_protect(long address, long size, int perms)
|
||||
throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Retrieve all memory regions mapped by mem_map() and mem_map_ptr()
|
||||
* NOTE: memory regions may be split by mem_unmap()
|
||||
*
|
||||
* @return list of mapped regions.
|
||||
*/
|
||||
*/
|
||||
public native MemRegion[] mem_regions() throws UnicornException;
|
||||
|
||||
/**
|
||||
/**
|
||||
* Allocate a region that can be used with uc_context_{save,restore} to perform
|
||||
* quick save/rollback of the CPU context, which includes registers and some
|
||||
* internal metadata. Contexts may not be shared across engine instances with
|
||||
* differing arches or modes.
|
||||
*
|
||||
* @return context handle for use with save/restore.
|
||||
*/
|
||||
*/
|
||||
public native long context_alloc();
|
||||
|
||||
/**
|
||||
/**
|
||||
* Free a resource allocated within Unicorn. Use for handles
|
||||
* allocated by context_alloc.
|
||||
*
|
||||
* @param Previously allocated Unicorn object handle.
|
||||
*/
|
||||
*/
|
||||
public native void free(long handle);
|
||||
|
||||
/**
|
||||
/**
|
||||
* Save a copy of the internal CPU context.
|
||||
* This API should be used to efficiently make or update a saved copy of the
|
||||
* internal CPU state.
|
||||
*
|
||||
* @param context handle previously returned by context_alloc.
|
||||
*/
|
||||
*/
|
||||
public native void context_save(long context);
|
||||
|
||||
/**
|
||||
/**
|
||||
* Restore the current CPU context from a saved copy.
|
||||
* This API should be used to roll the CPU context back to a previous
|
||||
* state saved by uc_context_save().
|
||||
*
|
||||
* @param context handle previously returned by context_alloc.
|
||||
*/
|
||||
*/
|
||||
public native void context_restore(long context);
|
||||
|
||||
/**
|
||||
* Set the emulated cpu model.
|
||||
*
|
||||
* @param cpu_model CPU model type (see UC_CPU_*).
|
||||
*/
|
||||
*/
|
||||
public native void ctl_set_cpu_model(int cpu_model);
|
||||
}
|
||||
|
||||
|
||||
@@ -22,7 +22,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public class UnicornException extends RuntimeException {
|
||||
|
||||
public UnicornException() {
|
||||
super();
|
||||
}
|
||||
@@ -30,5 +29,4 @@ public class UnicornException extends RuntimeException {
|
||||
public UnicornException(String msg) {
|
||||
super(msg);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -22,8 +22,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public interface WriteHook extends Hook {
|
||||
|
||||
public void hook(Unicorn u, long address, int size, long value, Object user);
|
||||
|
||||
public void hook(Unicorn u, long address, int size, long value,
|
||||
Object user);
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ package unicorn;
|
||||
|
||||
public interface X86Const {
|
||||
|
||||
// X86 CPU
|
||||
// X86 CPU
|
||||
|
||||
public static final int UC_CPU_X86_QEMU64 = 0;
|
||||
public static final int UC_CPU_X86_PHENOM = 1;
|
||||
@@ -46,7 +46,7 @@ public interface X86Const {
|
||||
public static final int UC_CPU_X86_EPYC_ROME = 37;
|
||||
public static final int UC_CPU_X86_ENDING = 38;
|
||||
|
||||
// X86 registers
|
||||
// X86 registers
|
||||
|
||||
public static final int UC_X86_REG_INVALID = 0;
|
||||
public static final int UC_X86_REG_AH = 1;
|
||||
@@ -289,7 +289,7 @@ public interface X86Const {
|
||||
public static final int UC_X86_REG_FOP = 258;
|
||||
public static final int UC_X86_REG_ENDING = 259;
|
||||
|
||||
// X86 instructions
|
||||
// X86 instructions
|
||||
|
||||
public static final int UC_X86_INS_INVALID = 0;
|
||||
public static final int UC_X86_INS_AAA = 1;
|
||||
|
||||
@@ -22,7 +22,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
package unicorn;
|
||||
|
||||
public class X86_MMR {
|
||||
|
||||
public long base;
|
||||
public int limit;
|
||||
public int flags;
|
||||
@@ -41,6 +40,4 @@ public class X86_MMR {
|
||||
selector = 0;
|
||||
flags = 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
#include <unicorn/x86.h>
|
||||
#include "unicorn_Unicorn.h"
|
||||
|
||||
//cache jmethodID values as we look them up
|
||||
// cache jmethodID values as we look them up
|
||||
static jmethodID invokeBlockCallbacks = 0;
|
||||
static jmethodID invokeInterruptCallbacks = 0;
|
||||
static jmethodID invokeCodeCallbacks = 0;
|
||||
@@ -40,9 +40,10 @@ static jmethodID invokeInCallbacks = 0;
|
||||
static jmethodID invokeOutCallbacks = 0;
|
||||
static jmethodID invokeSyscallCallbacks = 0;
|
||||
|
||||
static JavaVM* cachedJVM;
|
||||
static JavaVM *cachedJVM;
|
||||
|
||||
JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void *reserved) {
|
||||
JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void *reserved)
|
||||
{
|
||||
cachedJVM = jvm;
|
||||
return JNI_VERSION_1_6;
|
||||
}
|
||||
@@ -51,14 +52,17 @@ JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void *reserved) {
|
||||
// @address: address where the code is being executed
|
||||
// @size: size of machine instruction being executed
|
||||
// @user_data: user data passed to tracing APIs.
|
||||
static void cb_hookcode(uc_engine *eng, uint64_t address, uint32_t size, void *user_data) {
|
||||
static void cb_hookcode(uc_engine *eng, uint64_t address, uint32_t size,
|
||||
void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return;
|
||||
}
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeCodeCallbacks, (jlong)eng, (jlong)address, (int)size);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeCodeCallbacks, (jlong)eng,
|
||||
(jlong)address, (int)size);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
}
|
||||
|
||||
@@ -66,28 +70,33 @@ static void cb_hookcode(uc_engine *eng, uint64_t address, uint32_t size, void *u
|
||||
// @address: address where the code is being executed
|
||||
// @size: size of machine instruction being executed
|
||||
// @user_data: user data passed to tracing APIs.
|
||||
static void cb_hookblock(uc_engine *eng, uint64_t address, uint32_t size, void *user_data) {
|
||||
static void cb_hookblock(uc_engine *eng, uint64_t address, uint32_t size,
|
||||
void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return;
|
||||
}
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeBlockCallbacks, (jlong)eng, (jlong)address, (int)size);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeBlockCallbacks, (jlong)eng,
|
||||
(jlong)address, (int)size);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
}
|
||||
|
||||
// Callback function for tracing interrupts (for uc_hook_intr())
|
||||
// @intno: interrupt number
|
||||
// @user_data: user data passed to tracing APIs.
|
||||
static void cb_hookintr(uc_engine *eng, uint32_t intno, void *user_data) {
|
||||
static void cb_hookintr(uc_engine *eng, uint32_t intno, void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return;
|
||||
}
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeInterruptCallbacks, (jlong)eng, (int)intno);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeInterruptCallbacks, (jlong)eng,
|
||||
(int)intno);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
}
|
||||
|
||||
@@ -95,7 +104,9 @@ static void cb_hookintr(uc_engine *eng, uint32_t intno, void *user_data) {
|
||||
// @port: port number
|
||||
// @size: data size (1/2/4) to be read from this port
|
||||
// @user_data: user data passed to tracing APIs.
|
||||
static uint32_t cb_insn_in(uc_engine *eng, uint32_t port, int size, void *user_data) {
|
||||
static uint32_t cb_insn_in(uc_engine *eng, uint32_t port, int size,
|
||||
void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
uint32_t res = 0;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
@@ -103,7 +114,8 @@ static uint32_t cb_insn_in(uc_engine *eng, uint32_t port, int size, void *user_d
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return 0;
|
||||
}
|
||||
res = (uint32_t)(*env)->CallStaticIntMethod(env, clz, invokeInCallbacks, (jlong)eng, (jint)port, (jint)size);
|
||||
res = (uint32_t)(*env)->CallStaticIntMethod(
|
||||
env, clz, invokeInCallbacks, (jlong)eng, (jint)port, (jint)size);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
return res;
|
||||
}
|
||||
@@ -112,19 +124,23 @@ static uint32_t cb_insn_in(uc_engine *eng, uint32_t port, int size, void *user_d
|
||||
// @port: port number
|
||||
// @size: data size (1/2/4) to be written to this port
|
||||
// @value: data value to be written to this port
|
||||
static void cb_insn_out(uc_engine *eng, uint32_t port, int size, uint32_t value, void *user_data) {
|
||||
static void cb_insn_out(uc_engine *eng, uint32_t port, int size, uint32_t value,
|
||||
void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return;
|
||||
}
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeOutCallbacks, (jlong)eng, (jint)port, (jint)size, (jint)value);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeOutCallbacks, (jlong)eng,
|
||||
(jint)port, (jint)size, (jint)value);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
}
|
||||
|
||||
// x86's handler for SYSCALL/SYSENTER
|
||||
static void cb_insn_syscall(uc_engine *eng, void *user_data) {
|
||||
static void cb_insn_syscall(uc_engine *eng, void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
@@ -141,8 +157,9 @@ static void cb_insn_syscall(uc_engine *eng, void *user_data) {
|
||||
// @size: size of data being read or written
|
||||
// @value: value of data being written to memory, or irrelevant if type = READ.
|
||||
// @user_data: user data passed to tracing APIs
|
||||
static void cb_hookmem(uc_engine *eng, uc_mem_type type,
|
||||
uint64_t address, int size, int64_t value, void *user_data) {
|
||||
static void cb_hookmem(uc_engine *eng, uc_mem_type type, uint64_t address,
|
||||
int size, int64_t value, void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
@@ -151,10 +168,12 @@ static void cb_hookmem(uc_engine *eng, uc_mem_type type,
|
||||
}
|
||||
switch (type) {
|
||||
case UC_MEM_READ:
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeReadCallbacks, (jlong)eng, (jlong)address, (int)size);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeReadCallbacks, (jlong)eng,
|
||||
(jlong)address, (int)size);
|
||||
break;
|
||||
case UC_MEM_WRITE:
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeWriteCallbacks, (jlong)eng, (jlong)address, (int)size, (jlong)value);
|
||||
(*env)->CallStaticVoidMethod(env, clz, invokeWriteCallbacks, (jlong)eng,
|
||||
(jlong)address, (int)size, (jlong)value);
|
||||
break;
|
||||
}
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
@@ -166,22 +185,27 @@ static void cb_hookmem(uc_engine *eng, uc_mem_type type,
|
||||
// @size: size of data being read or written
|
||||
// @value: value of data being written to memory, or irrelevant if type = READ.
|
||||
// @user_data: user data passed to tracing APIs
|
||||
// @return: return true to continue, or false to stop program (due to invalid memory).
|
||||
static bool cb_eventmem(uc_engine *eng, uc_mem_type type,
|
||||
uint64_t address, int size, int64_t value, void *user_data) {
|
||||
// @return: return true to continue, or false to stop program (due to invalid
|
||||
// memory).
|
||||
static bool cb_eventmem(uc_engine *eng, uc_mem_type type, uint64_t address,
|
||||
int size, int64_t value, void *user_data)
|
||||
{
|
||||
JNIEnv *env;
|
||||
(*cachedJVM)->AttachCurrentThread(cachedJVM, (void **)&env, NULL);
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/Unicorn");
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return false;
|
||||
}
|
||||
jboolean res = (*env)->CallStaticBooleanMethod(env, clz, invokeEventMemCallbacks, (jlong)eng, (int)type, (jlong)address, (int)size, (jlong)value);
|
||||
jboolean res = (*env)->CallStaticBooleanMethod(
|
||||
env, clz, invokeEventMemCallbacks, (jlong)eng, (int)type,
|
||||
(jlong)address, (int)size, (jlong)value);
|
||||
(*cachedJVM)->DetachCurrentThread(cachedJVM);
|
||||
return res;
|
||||
}
|
||||
|
||||
static void throwException(JNIEnv *env, uc_err err) {
|
||||
//throw exception
|
||||
static void throwException(JNIEnv *env, uc_err err)
|
||||
{
|
||||
// throw exception
|
||||
jclass clazz = (*env)->FindClass(env, "unicorn/UnicornException");
|
||||
if (err != UC_ERR_OK) {
|
||||
const char *msg = uc_strerror(err);
|
||||
@@ -189,11 +213,12 @@ static void throwException(JNIEnv *env, uc_err err) {
|
||||
}
|
||||
}
|
||||
|
||||
static uc_engine *getEngine(JNIEnv *env, jobject self) {
|
||||
static uc_engine *getEngine(JNIEnv *env, jobject self)
|
||||
{
|
||||
static int haveFid = 0;
|
||||
static jfieldID fid;
|
||||
if (haveFid == 0) {
|
||||
//cache the field id
|
||||
// cache the field id
|
||||
jclass clazz = (*env)->GetObjectClass(env, self);
|
||||
fid = (*env)->GetFieldID(env, clazz, "eng", "J");
|
||||
haveFid = 1;
|
||||
@@ -206,8 +231,11 @@ static uc_engine *getEngine(JNIEnv *env, jobject self) {
|
||||
* Method: reg_write_num
|
||||
* Signature: (ILjava/lang/Number;)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1num
|
||||
(JNIEnv *env, jobject self, jint regid, jobject value) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1num(JNIEnv *env,
|
||||
jobject self,
|
||||
jint regid,
|
||||
jobject value)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
jclass clz = (*env)->FindClass(env, "java/lang/Number");
|
||||
@@ -228,8 +256,11 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1num
|
||||
* Method: reg_write_mmr
|
||||
* Signature: (ILunicorn/X86_MMR;)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1mmr
|
||||
(JNIEnv *env, jobject self, jint regid, jobject value) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1mmr(JNIEnv *env,
|
||||
jobject self,
|
||||
jint regid,
|
||||
jobject value)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_x86_mmr mmr;
|
||||
|
||||
@@ -261,8 +292,10 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write_1mmr
|
||||
* Method: reg_read_num
|
||||
* Signature: (I)Ljava/lang/Number;
|
||||
*/
|
||||
JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1num
|
||||
(JNIEnv *env, jobject self, jint regid) {
|
||||
JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1num(JNIEnv *env,
|
||||
jobject self,
|
||||
jint regid)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
jclass clz = (*env)->FindClass(env, "java/lang/Long");
|
||||
@@ -289,8 +322,10 @@ JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1num
|
||||
* Method: reg_read_mmr
|
||||
* Signature: (I)Ljava/lang/Number;
|
||||
*/
|
||||
JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1mmr
|
||||
(JNIEnv *env, jobject self, jint regid) {
|
||||
JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1mmr(JNIEnv *env,
|
||||
jobject self,
|
||||
jint regid)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
jclass clz = (*env)->FindClass(env, "unicorn/X86_MMR");
|
||||
@@ -305,7 +340,8 @@ JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1mmr
|
||||
}
|
||||
|
||||
jmethodID cons = (*env)->GetMethodID(env, clz, "<init>", "(JIIS)V");
|
||||
jobject result = (*env)->NewObject(env, clz, cons, mmr.base, mmr.limit, mmr.flags, mmr.selector);
|
||||
jobject result = (*env)->NewObject(env, clz, cons, mmr.base, mmr.limit,
|
||||
mmr.flags, mmr.selector);
|
||||
if ((*env)->ExceptionCheck(env)) {
|
||||
return NULL;
|
||||
}
|
||||
@@ -317,8 +353,9 @@ JNIEXPORT jobject JNICALL Java_unicorn_Unicorn_reg_1read_1mmr
|
||||
* Method: open
|
||||
* Signature: (II)J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_open
|
||||
(JNIEnv *env, jobject self, jint arch, jint mode) {
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_open(JNIEnv *env, jobject self,
|
||||
jint arch, jint mode)
|
||||
{
|
||||
uc_engine *eng = NULL;
|
||||
uc_err err = uc_open((uc_arch)arch, (uc_mode)mode, &eng);
|
||||
if (err != UC_ERR_OK) {
|
||||
@@ -332,8 +369,8 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_open
|
||||
* Method: version
|
||||
* Signature: ()I
|
||||
*/
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_version
|
||||
(JNIEnv *env, jclass clz) {
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_version(JNIEnv *env, jclass clz)
|
||||
{
|
||||
return (jint)uc_version(NULL, NULL);
|
||||
}
|
||||
|
||||
@@ -342,8 +379,10 @@ JNIEXPORT jint JNICALL Java_unicorn_Unicorn_version
|
||||
* Method: arch_supported
|
||||
* Signature: (I)Z
|
||||
*/
|
||||
JNIEXPORT jboolean JNICALL Java_unicorn_Unicorn_arch_1supported
|
||||
(JNIEnv *env, jclass clz, jint arch) {
|
||||
JNIEXPORT jboolean JNICALL Java_unicorn_Unicorn_arch_1supported(JNIEnv *env,
|
||||
jclass clz,
|
||||
jint arch)
|
||||
{
|
||||
return (jboolean)(uc_arch_supported((uc_arch)arch) != 0);
|
||||
}
|
||||
|
||||
@@ -352,15 +391,15 @@ JNIEXPORT jboolean JNICALL Java_unicorn_Unicorn_arch_1supported
|
||||
* Method: close
|
||||
* Signature: ()V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_close
|
||||
(JNIEnv *env, jobject self) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_close(JNIEnv *env, jobject self)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_err err = uc_close(eng);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
//We also need to ReleaseByteArrayElements for any regions that
|
||||
//were mapped with uc_mem_map_ptr
|
||||
// We also need to ReleaseByteArrayElements for any regions that
|
||||
// were mapped with uc_mem_map_ptr
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -368,8 +407,9 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_close
|
||||
* Method: query
|
||||
* Signature: (I)I
|
||||
*/
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_query
|
||||
(JNIEnv *env, jobject self, jint type) {
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_query(JNIEnv *env, jobject self,
|
||||
jint type)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
size_t result;
|
||||
uc_err err = uc_query(eng, type, &result);
|
||||
@@ -384,8 +424,8 @@ JNIEXPORT jint JNICALL Java_unicorn_Unicorn_query
|
||||
* Method: errno
|
||||
* Signature: ()I
|
||||
*/
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_errno
|
||||
(JNIEnv *env, jobject self) {
|
||||
JNIEXPORT jint JNICALL Java_unicorn_Unicorn_errno(JNIEnv *env, jobject self)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
return (jint)uc_errno(eng);
|
||||
}
|
||||
@@ -395,8 +435,9 @@ JNIEXPORT jint JNICALL Java_unicorn_Unicorn_errno
|
||||
* Method: strerror
|
||||
* Signature: (I)Ljava/lang/String;
|
||||
*/
|
||||
JNIEXPORT jstring JNICALL Java_unicorn_Unicorn_strerror
|
||||
(JNIEnv *env, jclass clz, jint code) {
|
||||
JNIEXPORT jstring JNICALL Java_unicorn_Unicorn_strerror(JNIEnv *env, jclass clz,
|
||||
jint code)
|
||||
{
|
||||
const char *err = uc_strerror((int)code);
|
||||
jstring s = (*env)->NewStringUTF(env, err);
|
||||
return s;
|
||||
@@ -407,8 +448,10 @@ JNIEXPORT jstring JNICALL Java_unicorn_Unicorn_strerror
|
||||
* Method: reg_write
|
||||
* Signature: (I[B)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write
|
||||
(JNIEnv *env, jobject self, jint regid, jbyteArray value) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write(JNIEnv *env,
|
||||
jobject self, jint regid,
|
||||
jbyteArray value)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
jbyte *array = (*env)->GetByteArrayElements(env, value, NULL);
|
||||
uc_err err = uc_reg_write(eng, (int)regid, (void *)array);
|
||||
@@ -423,8 +466,11 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_reg_1write
|
||||
* Method: reg_read
|
||||
* Signature: (II)[B
|
||||
*/
|
||||
JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_reg_1read
|
||||
(JNIEnv *env, jobject self, jint regid, jint regsz) {
|
||||
JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_reg_1read(JNIEnv *env,
|
||||
jobject self,
|
||||
jint regid,
|
||||
jint regsz)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
jbyteArray regval = (*env)->NewByteArray(env, (jsize)regsz);
|
||||
jbyte *array = (*env)->GetByteArrayElements(env, regval, NULL);
|
||||
@@ -441,8 +487,11 @@ JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_reg_1read
|
||||
* Method: mem_write
|
||||
* Signature: (J[B)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1write
|
||||
(JNIEnv *env , jobject self, jlong address, jbyteArray bytes) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1write(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong address,
|
||||
jbyteArray bytes)
|
||||
{
|
||||
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
jbyte *array = (*env)->GetByteArrayElements(env, bytes, NULL);
|
||||
@@ -461,8 +510,11 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1write
|
||||
* Method: mem_read
|
||||
* Signature: (JJ)[B
|
||||
*/
|
||||
JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_mem_1read
|
||||
(JNIEnv *env, jobject self, jlong address, jlong size) {
|
||||
JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_mem_1read(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong address,
|
||||
jlong size)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
jbyteArray bytes = (*env)->NewByteArray(env, (jsize)size);
|
||||
@@ -480,11 +532,16 @@ JNIEXPORT jbyteArray JNICALL Java_unicorn_Unicorn_mem_1read
|
||||
* Method: emu_start
|
||||
* Signature: (JJJJ)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1start
|
||||
(JNIEnv *env, jobject self, jlong begin, jlong until, jlong timeout, jlong count) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1start(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong begin, jlong until,
|
||||
jlong timeout,
|
||||
jlong count)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_err err = uc_emu_start(eng, (uint64_t)begin, (uint64_t)until, (uint64_t)timeout, (size_t)count);
|
||||
uc_err err = uc_emu_start(eng, (uint64_t)begin, (uint64_t)until,
|
||||
(uint64_t)timeout, (size_t)count);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
@@ -495,8 +552,8 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1start
|
||||
* Method: emu_stop
|
||||
* Signature: ()V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1stop
|
||||
(JNIEnv *env, jobject self) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1stop(JNIEnv *env, jobject self)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_err err = uc_emu_stop(eng);
|
||||
@@ -510,27 +567,36 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_emu_1stop
|
||||
* Method: registerHook
|
||||
* Signature: (JI)J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JI
|
||||
(JNIEnv *env, jclass clz, jlong eng, jint type) {
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JI(JNIEnv *env,
|
||||
jclass clz,
|
||||
jlong eng,
|
||||
jint type)
|
||||
{
|
||||
uc_hook hh = 0;
|
||||
uc_err err = 0;
|
||||
switch (type) {
|
||||
case UC_HOOK_INTR: // Hook all interrupt events
|
||||
if (invokeInterruptCallbacks == 0) {
|
||||
invokeInterruptCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeInterruptCallbacks", "(JI)V");
|
||||
invokeInterruptCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeInterruptCallbacks", "(JI)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_hookintr, env, 1, 0);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_hookintr, env, 1, 0);
|
||||
break;
|
||||
case UC_HOOK_MEM_FETCH_UNMAPPED: // Hook for all invalid memory access events
|
||||
case UC_HOOK_MEM_FETCH_UNMAPPED: // Hook for all invalid memory access
|
||||
// events
|
||||
case UC_HOOK_MEM_READ_UNMAPPED: // Hook for all invalid memory access events
|
||||
case UC_HOOK_MEM_WRITE_UNMAPPED: // Hook for all invalid memory access events
|
||||
case UC_HOOK_MEM_WRITE_UNMAPPED: // Hook for all invalid memory access
|
||||
// events
|
||||
case UC_HOOK_MEM_FETCH_PROT: // Hook for all invalid memory access events
|
||||
case UC_HOOK_MEM_READ_PROT: // Hook for all invalid memory access events
|
||||
case UC_HOOK_MEM_WRITE_PROT: // Hook for all invalid memory access events
|
||||
if (invokeEventMemCallbacks == 0) {
|
||||
invokeEventMemCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeEventMemCallbacks", "(JIJIJ)Z");
|
||||
invokeEventMemCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeEventMemCallbacks", "(JIJIJ)Z");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_eventmem, env, 1, 0);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_eventmem, env, 1, 0);
|
||||
break;
|
||||
}
|
||||
return (jlong)hh;
|
||||
@@ -541,8 +607,9 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JI
|
||||
* Method: registerHook
|
||||
* Signature: (JII)J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JII
|
||||
(JNIEnv *env, jclass clz, jlong eng, jint type, jint arg1) {
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JII(
|
||||
JNIEnv *env, jclass clz, jlong eng, jint type, jint arg1)
|
||||
{
|
||||
uc_hook hh = 0;
|
||||
uc_err err = 0;
|
||||
switch (type) {
|
||||
@@ -550,20 +617,26 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JII
|
||||
switch (arg1) {
|
||||
case UC_X86_INS_OUT:
|
||||
if (invokeOutCallbacks == 0) {
|
||||
invokeOutCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeOutCallbacks", "(JIII)V");
|
||||
invokeOutCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeOutCallbacks", "(JIII)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_insn_out, env, 1, 0, arg1);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_insn_out, env, 1, 0, arg1);
|
||||
case UC_X86_INS_IN:
|
||||
if (invokeInCallbacks == 0) {
|
||||
invokeInCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeInCallbacks", "(JII)I");
|
||||
invokeInCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeInCallbacks", "(JII)I");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_insn_in, env, 1, 0, arg1);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_insn_in, env, 1, 0, arg1);
|
||||
case UC_X86_INS_SYSENTER:
|
||||
case UC_X86_INS_SYSCALL:
|
||||
if (invokeSyscallCallbacks == 0) {
|
||||
invokeSyscallCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeSyscallCallbacks", "(J)V");
|
||||
invokeSyscallCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeSyscallCallbacks", "(J)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_insn_syscall, env, 1, 0, arg1);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_insn_syscall, env, 1, 0, arg1);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -575,34 +648,43 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JII
|
||||
* Method: registerHook
|
||||
* Signature: (JIJJ)J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JIJJ
|
||||
(JNIEnv *env, jclass clz, jlong eng, jint type, jlong arg1, jlong arg2) {
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JIJJ(
|
||||
JNIEnv *env, jclass clz, jlong eng, jint type, jlong arg1, jlong arg2)
|
||||
{
|
||||
uc_hook hh = 0;
|
||||
uc_err err = 0;
|
||||
switch (type) {
|
||||
case UC_HOOK_CODE: // Hook a range of code
|
||||
if (invokeCodeCallbacks == 0) {
|
||||
invokeCodeCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeCodeCallbacks", "(JJI)V");
|
||||
invokeCodeCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeCodeCallbacks", "(JJI)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_hookcode, env, 1, 0, arg1, arg2);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_hookcode, env, 1, 0, arg1, arg2);
|
||||
break;
|
||||
case UC_HOOK_BLOCK: // Hook basic blocks
|
||||
if (invokeBlockCallbacks == 0) {
|
||||
invokeBlockCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeBlockCallbacks", "(JJI)V");
|
||||
invokeBlockCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeBlockCallbacks", "(JJI)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_hookblock, env, 1, 0, arg1, arg2);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type,
|
||||
cb_hookblock, env, 1, 0, arg1, arg2);
|
||||
break;
|
||||
case UC_HOOK_MEM_READ: // Hook all memory read events.
|
||||
if (invokeReadCallbacks == 0) {
|
||||
invokeReadCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeReadCallbacks", "(JJI)V");
|
||||
invokeReadCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeReadCallbacks", "(JJI)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_hookmem, env, 1, 0, arg1, arg2);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type, cb_hookmem,
|
||||
env, 1, 0, arg1, arg2);
|
||||
break;
|
||||
case UC_HOOK_MEM_WRITE: // Hook all memory write events.
|
||||
if (invokeWriteCallbacks == 0) {
|
||||
invokeWriteCallbacks = (*env)->GetStaticMethodID(env, clz, "invokeWriteCallbacks", "(JJIJ)V");
|
||||
invokeWriteCallbacks = (*env)->GetStaticMethodID(
|
||||
env, clz, "invokeWriteCallbacks", "(JJIJ)V");
|
||||
}
|
||||
err = uc_hook_add((uc_engine*)eng, &hh, (uc_hook_type)type, cb_hookmem, env, 1, 0, arg1, arg2);
|
||||
err = uc_hook_add((uc_engine *)eng, &hh, (uc_hook_type)type, cb_hookmem,
|
||||
env, 1, 0, arg1, arg2);
|
||||
break;
|
||||
}
|
||||
return (jlong)hh;
|
||||
@@ -613,8 +695,9 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_registerHook__JIJJ
|
||||
* Method: hook_del
|
||||
* Signature: (J)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_hook_1del
|
||||
(JNIEnv *env, jobject self, jlong hh) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_hook_1del(JNIEnv *env, jobject self,
|
||||
jlong hh)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
//**** TODO remove hook from any internal hook tables as well
|
||||
@@ -630,11 +713,14 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_hook_1del
|
||||
* Method: mem_map
|
||||
* Signature: (JJI)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1map
|
||||
(JNIEnv *env, jobject self, jlong address, jlong size, jint perms) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1map(JNIEnv *env, jobject self,
|
||||
jlong address, jlong size,
|
||||
jint perms)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_err err = uc_mem_map(eng, (uint64_t)address, (size_t)size, (uint32_t)perms);
|
||||
uc_err err =
|
||||
uc_mem_map(eng, (uint64_t)address, (size_t)size, (uint32_t)perms);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
@@ -645,16 +731,19 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1map
|
||||
* Method: mem_map_ptr
|
||||
* Signature: (JJI[B)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1map_1ptr
|
||||
(JNIEnv *env, jobject self, jlong address, jlong size, jint perms, jbyteArray block) {
|
||||
JNIEXPORT void JNICALL
|
||||
Java_unicorn_Unicorn_mem_1map_1ptr(JNIEnv *env, jobject self, jlong address,
|
||||
jlong size, jint perms, jbyteArray block)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
jbyte *array = (*env)->GetByteArrayElements(env, block, NULL);
|
||||
uc_err err = uc_mem_map_ptr(eng, (uint64_t)address, (size_t)size, (uint32_t)perms, (void*)array);
|
||||
uc_err err = uc_mem_map_ptr(eng, (uint64_t)address, (size_t)size,
|
||||
(uint32_t)perms, (void *)array);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
//Need to track address/block/array so that we can ReleaseByteArrayElements when the
|
||||
//block gets unmapped or when uc_close gets called
|
||||
// Need to track address/block/array so that we can ReleaseByteArrayElements
|
||||
// when the block gets unmapped or when uc_close gets called
|
||||
//(*env)->ReleaseByteArrayElements(env, block, array, JNI_ABORT);
|
||||
}
|
||||
|
||||
@@ -663,8 +752,11 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1map_1ptr
|
||||
* Method: mem_unmap
|
||||
* Signature: (JJ)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1unmap
|
||||
(JNIEnv *env, jobject self, jlong address, jlong size) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1unmap(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong address,
|
||||
jlong size)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_err err = uc_mem_unmap(eng, (uint64_t)address, (size_t)size);
|
||||
@@ -672,8 +764,8 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1unmap
|
||||
throwException(env, err);
|
||||
}
|
||||
|
||||
//If a region was mapped using uc_mem_map_ptr, we also need to
|
||||
//ReleaseByteArrayElements for that region
|
||||
// If a region was mapped using uc_mem_map_ptr, we also need to
|
||||
// ReleaseByteArrayElements for that region
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -681,11 +773,15 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1unmap
|
||||
* Method: mem_protect
|
||||
* Signature: (JJI)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1protect
|
||||
(JNIEnv *env, jobject self, jlong address, jlong size, jint perms) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1protect(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong address,
|
||||
jlong size, jint perms)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_err err = uc_mem_protect(eng, (uint64_t)address, (size_t)size, (uint32_t)perms);
|
||||
uc_err err =
|
||||
uc_mem_protect(eng, (uint64_t)address, (size_t)size, (uint32_t)perms);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
@@ -696,8 +792,9 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_mem_1protect
|
||||
* Method: mem_regions
|
||||
* Signature: ()[Lunicorn/MemRegion;
|
||||
*/
|
||||
JNIEXPORT jobjectArray JNICALL Java_unicorn_Unicorn_mem_1regions
|
||||
(JNIEnv *env, jobject self) {
|
||||
JNIEXPORT jobjectArray JNICALL Java_unicorn_Unicorn_mem_1regions(JNIEnv *env,
|
||||
jobject self)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
|
||||
uc_mem_region *regions = NULL;
|
||||
@@ -715,7 +812,8 @@ JNIEXPORT jobjectArray JNICALL Java_unicorn_Unicorn_mem_1regions
|
||||
jobjectArray result = (*env)->NewObjectArray(env, (jsize)count, clz, NULL);
|
||||
jmethodID cons = (*env)->GetMethodID(env, clz, "<init>", "(JJI)V");
|
||||
for (i = 0; i < count; i++) {
|
||||
jobject mr = (*env)->NewObject(env, clz, cons, regions[i].begin, regions[i].end, regions[i].perms);
|
||||
jobject mr = (*env)->NewObject(env, clz, cons, regions[i].begin,
|
||||
regions[i].end, regions[i].perms);
|
||||
(*env)->SetObjectArrayElement(env, result, (jsize)i, mr);
|
||||
}
|
||||
uc_free(regions);
|
||||
@@ -728,8 +826,9 @@ JNIEXPORT jobjectArray JNICALL Java_unicorn_Unicorn_mem_1regions
|
||||
* Method: context_alloc
|
||||
* Signature: ()J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_context_1alloc
|
||||
(JNIEnv *env, jobject self) {
|
||||
JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_context_1alloc(JNIEnv *env,
|
||||
jobject self)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_context *ctx;
|
||||
uc_err err = uc_context_alloc(eng, &ctx);
|
||||
@@ -744,8 +843,9 @@ JNIEXPORT jlong JNICALL Java_unicorn_Unicorn_context_1alloc
|
||||
* Method: free
|
||||
* Signature: (J)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_free
|
||||
(JNIEnv *env, jobject self, jlong ctx) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_free(JNIEnv *env, jobject self,
|
||||
jlong ctx)
|
||||
{
|
||||
uc_err err = uc_free((void *)ctx);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
@@ -757,10 +857,12 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_free
|
||||
* Method: context_save
|
||||
* Signature: (J)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1save
|
||||
(JNIEnv *env, jobject self, jlong ctx) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1save(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong ctx)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_err err = uc_context_save(eng, (uc_context*)ctx);
|
||||
uc_err err = uc_context_save(eng, (uc_context *)ctx);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
@@ -771,10 +873,12 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1save
|
||||
* Method: context_restore
|
||||
* Signature: (J)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1restore
|
||||
(JNIEnv *env, jobject self, jlong ctx) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1restore(JNIEnv *env,
|
||||
jobject self,
|
||||
jlong ctx)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_err err = uc_context_restore(eng, (uc_context*)ctx);
|
||||
uc_err err = uc_context_restore(eng, (uc_context *)ctx);
|
||||
if (err != UC_ERR_OK) {
|
||||
throwException(env, err);
|
||||
}
|
||||
@@ -785,8 +889,10 @@ JNIEXPORT void JNICALL Java_unicorn_Unicorn_context_1restore
|
||||
* Method: ctl_set_cpu_model
|
||||
* Signature: (I)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_ctl_1set_1cpu_1model
|
||||
(JNIEnv *env, jobject self, jint cpu_model) {
|
||||
JNIEXPORT void JNICALL Java_unicorn_Unicorn_ctl_1set_1cpu_1model(JNIEnv *env,
|
||||
jobject self,
|
||||
jint cpu_model)
|
||||
{
|
||||
uc_engine *eng = getEngine(env, self);
|
||||
uc_err err = uc_ctl_set_cpu_model(eng, cpu_model);
|
||||
if (err != UC_ERR_OK) {
|
||||
|
||||
Reference in New Issue
Block a user