Compare commits
39 Commits
asiekierka
...
master
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
67429a7a31 | ||
|
|
139af3f28b | ||
|
|
33d745d667 | ||
|
|
06c74072be | ||
|
|
63edacbb5f | ||
|
|
7aea99d650 | ||
|
|
921606b93f | ||
|
|
5f11997446 | ||
|
|
c735ac67a0 | ||
|
|
7f7185aa08 | ||
|
|
39ff4f204d | ||
|
|
9cb10a390f | ||
|
|
c60991a33c | ||
|
|
c8fdc62495 | ||
|
|
ff4033cad4 | ||
|
|
572fd95692 | ||
|
|
db392c4763 | ||
|
|
98437da1fa | ||
|
|
85ed36de51 | ||
|
|
1d3459e0d3 | ||
|
|
493b055a26 | ||
|
|
01a8bd944e | ||
|
|
4c2add3832 | ||
|
|
364dbecb17 | ||
|
|
86e4d78761 | ||
|
|
7338475ae4 | ||
|
|
01739d4e77 | ||
|
|
37b68d4d85 | ||
|
|
f30c4c3bec | ||
|
|
d0c84972dd | ||
|
|
068451886d | ||
|
|
ba3d1d8ef9 | ||
|
|
405fd633fd | ||
|
|
f087e87806 | ||
|
|
95ea3d84b6 | ||
|
|
f40e89e19c | ||
| 40831d0f2d | |||
| bba6df42fd | |||
| 3df6dc9e96 |
17
.gitignore
vendored
17
.gitignore
vendored
@@ -1,4 +1,15 @@
|
||||
bin/
|
||||
target/
|
||||
.classpath
|
||||
.project
|
||||
.settings/
|
||||
build/
|
||||
lib/
|
||||
jit/
|
||||
*.ser
|
||||
*.gz
|
||||
*.jar
|
||||
*.lua
|
||||
*.out
|
||||
*.tar
|
||||
*.txt
|
||||
*.zip
|
||||
docs
|
||||
*.0
|
||||
|
||||
138
.ide/cleanup.xml
138
.ide/cleanup.xml
@@ -1,138 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<profiles version="2">
|
||||
<profile kind="CleanUpProfile" name="Default" version="2">
|
||||
<setting id="cleanup.array_with_curly" value="true"/>
|
||||
<setting id="cleanup.use_autoboxing" value="true"/>
|
||||
<setting id="cleanup.always_use_this_for_non_static_method_access" value="false"/>
|
||||
<setting id="cleanup.remove_trailing_whitespaces_ignore_empty" value="false"/>
|
||||
<setting id="cleanup.primitive_comparison" value="false"/>
|
||||
<setting id="cleanup.system_property_file_encoding" value="true"/>
|
||||
<setting id="cleanup.format_source_code_changes_only" value="false"/>
|
||||
<setting id="cleanup.remove_redundant_semicolons" value="true"/>
|
||||
<setting id="cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class" value="true"/>
|
||||
<setting id="cleanup.useless_continue" value="true"/>
|
||||
<setting id="cleanup.remove_redundant_type_arguments" value="true"/>
|
||||
<setting id="cleanup.remove_unused_imports" value="true"/>
|
||||
<setting id="cleanup.break_loop" value="false"/>
|
||||
<setting id="cleanup.pull_up_assignment" value="false"/>
|
||||
<setting id="cleanup.stringbuilder" value="false"/>
|
||||
<setting id="cleanup.no_super" value="true"/>
|
||||
<setting id="cleanup.arrays_fill" value="false"/>
|
||||
<setting id="cleanup.use_lambda" value="true"/>
|
||||
<setting id="cleanup.operand_factorization" value="false"/>
|
||||
<setting id="cleanup.simplify_lambda_expression_and_method_ref" value="true"/>
|
||||
<setting id="cleanup.always_use_blocks" value="true"/>
|
||||
<setting id="cleanup.sort_members_all" value="false"/>
|
||||
<setting id="cleanup.system_property_path_separator" value="true"/>
|
||||
<setting id="cleanup.instanceof" value="false"/>
|
||||
<setting id="cleanup.add_missing_annotations" value="true"/>
|
||||
<setting id="cleanup.precompile_regex" value="false"/>
|
||||
<setting id="cleanup.always_use_this_for_non_static_field_access" value="false"/>
|
||||
<setting id="cleanup.boolean_literal" value="true"/>
|
||||
<setting id="cleanup.always_use_parentheses_in_expressions" value="false"/>
|
||||
<setting id="cleanup.sort_members" value="false"/>
|
||||
<setting id="cleanup.remove_unused_local_variables" value="false"/>
|
||||
<setting id="cleanup.add_missing_deprecated_annotations" value="true"/>
|
||||
<setting id="cleanup.no_string_creation" value="true"/>
|
||||
<setting id="cleanup.use_unboxing" value="false"/>
|
||||
<setting id="cleanup.use_blocks_only_for_return_and_throw" value="false"/>
|
||||
<setting id="cleanup.standard_comparison" value="false"/>
|
||||
<setting id="cleanup.if_condition" value="true"/>
|
||||
<setting id="cleanup.system_property_line_separator" value="true"/>
|
||||
<setting id="cleanup.remove_trailing_whitespaces" value="true"/>
|
||||
<setting id="cleanup.map_cloning" value="true"/>
|
||||
<setting id="cleanup.add_serial_version_id" value="false"/>
|
||||
<setting id="cleanup.try_with_resource" value="true"/>
|
||||
<setting id="cleanup.use_this_for_non_static_method_access" value="false"/>
|
||||
<setting id="cleanup.use_this_for_non_static_method_access_only_if_necessary" value="true"/>
|
||||
<setting id="cleanup.single_used_field" value="false"/>
|
||||
<setting id="cleanup.reduce_indentation" value="false"/>
|
||||
<setting id="cleanup.primitive_parsing" value="false"/>
|
||||
<setting id="cleanup.make_local_variable_final" value="false"/>
|
||||
<setting id="cleanup.add_missing_methods" value="false"/>
|
||||
<setting id="cleanup.qualify_static_member_accesses_with_declaring_class" value="true"/>
|
||||
<setting id="cleanup.add_missing_override_annotations" value="true"/>
|
||||
<setting id="cleanup.use_blocks" value="false"/>
|
||||
<setting id="cleanup.multi_catch" value="true"/>
|
||||
<setting id="cleanup.pull_out_if_from_if_else" value="true"/>
|
||||
<setting id="cleanup.collection_cloning" value="true"/>
|
||||
<setting id="cleanup.convert_to_enhanced_for_loop_if_loop_var_used" value="true"/>
|
||||
<setting id="cleanup.make_variable_declarations_final" value="true"/>
|
||||
<setting id="cleanup.redundant_comparator" value="false"/>
|
||||
<setting id="cleanup.remove_unused_private_types" value="true"/>
|
||||
<setting id="cleanup.system_property_boolean" value="true"/>
|
||||
<setting id="cleanup.qualify_static_method_accesses_with_declaring_class" value="false"/>
|
||||
<setting id="cleanup.organize_imports" value="true"/>
|
||||
<setting id="cleanup.lazy_logical_operator" value="true"/>
|
||||
<setting id="cleanup.bitwise_conditional_expression" value="false"/>
|
||||
<setting id="cleanup.use_directly_map_method" value="false"/>
|
||||
<setting id="cleanup.add_all" value="false"/>
|
||||
<setting id="cleanup.system_property_file_separator" value="true"/>
|
||||
<setting id="cleanup.qualify_static_field_accesses_with_declaring_class" value="false"/>
|
||||
<setting id="cleanup.add_generated_serial_version_id" value="false"/>
|
||||
<setting id="cleanup.controlflow_merge" value="false"/>
|
||||
<setting id="cleanup.primitive_serialization" value="false"/>
|
||||
<setting id="cleanup.comparing_on_criteria" value="true"/>
|
||||
<setting id="cleanup.comparison_statement" value="true"/>
|
||||
<setting id="cleanup.extract_increment" value="false"/>
|
||||
<setting id="cleanup.insert_inferred_type_arguments" value="false"/>
|
||||
<setting id="cleanup.make_private_fields_final" value="true"/>
|
||||
<setting id="cleanup.useless_return" value="true"/>
|
||||
<setting id="cleanup.instanceof_keyword" value="true"/>
|
||||
<setting id="cleanup.use_this_for_non_static_field_access_only_if_necessary" value="true"/>
|
||||
<setting id="cleanup.remove_trailing_whitespaces_all" value="true"/>
|
||||
<setting id="cleanup.one_if_rather_than_duplicate_blocks_that_fall_through" value="true"/>
|
||||
<setting id="cleanup.valueof_rather_than_instantiation" value="true"/>
|
||||
<setting id="cleanup.plain_replacement" value="false"/>
|
||||
<setting id="cleanup.remove_unnecessary_array_creation" value="true"/>
|
||||
<setting id="cleanup.remove_private_constructors" value="true"/>
|
||||
<setting id="cleanup.make_parameters_final" value="false"/>
|
||||
<setting id="cleanup.substring" value="false"/>
|
||||
<setting id="cleanup.ternary_operator" value="false"/>
|
||||
<setting id="cleanup.merge_conditional_blocks" value="false"/>
|
||||
<setting id="cleanup.return_expression" value="true"/>
|
||||
<setting id="cleanup.system_property" value="true"/>
|
||||
<setting id="cleanup.unlooped_while" value="true"/>
|
||||
<setting id="cleanup.convert_to_enhanced_for_loop" value="true"/>
|
||||
<setting id="cleanup.remove_unused_private_fields" value="true"/>
|
||||
<setting id="cleanup.never_use_blocks" value="false"/>
|
||||
<setting id="cleanup.remove_redundant_modifiers" value="true"/>
|
||||
<setting id="cleanup.unreachable_block" value="false"/>
|
||||
<setting id="cleanup.redundant_falling_through_block_end" value="false"/>
|
||||
<setting id="cleanup.switch" value="false"/>
|
||||
<setting id="cleanup.number_suffix" value="true"/>
|
||||
<setting id="cleanup.remove_unnecessary_nls_tags" value="true"/>
|
||||
<setting id="cleanup.convert_to_switch_expressions" value="false"/>
|
||||
<setting id="cleanup.use_this_for_non_static_field_access" value="false"/>
|
||||
<setting id="cleanup.static_inner_class" value="false"/>
|
||||
<setting id="cleanup.use_string_is_blank" value="true"/>
|
||||
<setting id="cleanup.add_missing_nls_tags" value="false"/>
|
||||
<setting id="cleanup.qualify_static_member_accesses_through_instances_with_declaring_class" value="true"/>
|
||||
<setting id="cleanup.remove_unnecessary_casts" value="true"/>
|
||||
<setting id="cleanup.objects_equals" value="false"/>
|
||||
<setting id="cleanup.convert_functional_interfaces" value="true"/>
|
||||
<setting id="cleanup.format_source_code" value="true"/>
|
||||
<setting id="cleanup.else_if" value="false"/>
|
||||
<setting id="cleanup.boolean_value_rather_than_comparison" value="true"/>
|
||||
<setting id="cleanup.add_default_serial_version_id" value="true"/>
|
||||
<setting id="cleanup.remove_unused_private_methods" value="true"/>
|
||||
<setting id="cleanup.make_type_abstract_if_missing_method" value="false"/>
|
||||
<setting id="cleanup.join" value="false"/>
|
||||
<setting id="cleanup.embedded_if" value="false"/>
|
||||
<setting id="cleanup.use_anonymous_class_creation" value="false"/>
|
||||
<setting id="cleanup.invert_equals" value="false"/>
|
||||
<setting id="cleanup.add_missing_override_annotations_interface_methods" value="true"/>
|
||||
<setting id="cleanup.remove_unused_private_members" value="false"/>
|
||||
<setting id="cleanup.strictly_equal_or_different" value="true"/>
|
||||
<setting id="cleanup.never_use_parentheses_in_expressions" value="true"/>
|
||||
<setting id="cleanup.push_down_negation" value="false"/>
|
||||
<setting id="cleanup.evaluate_nullable" value="false"/>
|
||||
<setting id="cleanup.use_parentheses_in_expressions" value="true"/>
|
||||
<setting id="cleanup.hash" value="false"/>
|
||||
<setting id="cleanup.double_negation" value="true"/>
|
||||
<setting id="cleanup.overridden_assignment" value="true"/>
|
||||
<setting id="cleanup.primitive_rather_than_wrapper" value="true"/>
|
||||
<setting id="cleanup.correct_indentation" value="false"/>
|
||||
<setting id="cleanup.use_var" value="false"/>
|
||||
</profile>
|
||||
</profiles>
|
||||
@@ -1,390 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<profiles version="21">
|
||||
<profile kind="CodeFormatterProfile" name="LuaJ" version="21">
|
||||
<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="do not 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="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="true"/>
|
||||
<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="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="1"/>
|
||||
<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="16"/>
|
||||
<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="false"/>
|
||||
<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="true"/>
|
||||
<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="16"/>
|
||||
<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="do not 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="false"/>
|
||||
<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="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiplicative_operator" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_anonymous_type_declaration_on_one_line" value="one_line_never"/>
|
||||
<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="insert"/>
|
||||
<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="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_annotation" value="common_lines"/>
|
||||
<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="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="0"/>
|
||||
<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.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="16"/>
|
||||
<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="1"/>
|
||||
<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="16"/>
|
||||
<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="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="false"/>
|
||||
<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="0"/>
|
||||
<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="do not 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="true"/>
|
||||
<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="16"/>
|
||||
<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="do not 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="do not 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="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_getter_setter_on_one_line" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="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="16"/>
|
||||
<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.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.insert_space_before_opening_brace_in_switch" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped" value="true"/>
|
||||
<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_preserve"/>
|
||||
<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="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_additive_operator" value="16"/>
|
||||
<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_never"/>
|
||||
<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="16"/>
|
||||
<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="do not 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.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.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="do not 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="true"/>
|
||||
<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="2"/>
|
||||
<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="16"/>
|
||||
<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.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="16"/>
|
||||
<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="16"/>
|
||||
<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="true"/>
|
||||
<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_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="do not 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="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="false"/>
|
||||
<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="tab"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_string_concatenation" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="120"/>
|
||||
<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>
|
||||
10
.idea/.gitignore
generated
vendored
Normal file
10
.idea/.gitignore
generated
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
# Default ignored files
|
||||
/shelf/
|
||||
/workspace.xml
|
||||
# Ignored default folder with query files
|
||||
/queries/
|
||||
# Datasource local storage ignored files
|
||||
/dataSources/
|
||||
/dataSources.local.xml
|
||||
# Editor-based HTTP Client requests
|
||||
/httpRequests/
|
||||
16
.idea/compiler.xml
generated
Normal file
16
.idea/compiler.xml
generated
Normal file
@@ -0,0 +1,16 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="CompilerConfiguration">
|
||||
<annotationProcessing>
|
||||
<profile name="Maven default annotation processors profile" enabled="true">
|
||||
<sourceOutputDir name="target/generated-sources/annotations" />
|
||||
<sourceTestOutputDir name="target/generated-test-sources/test-annotations" />
|
||||
<outputRelativeToContentRoot value="true" />
|
||||
<module name="core" />
|
||||
<module name="jme" />
|
||||
<module name="jse" />
|
||||
<module name="maven-example" />
|
||||
</profile>
|
||||
</annotationProcessing>
|
||||
</component>
|
||||
</project>
|
||||
7
.idea/discord.xml
generated
Normal file
7
.idea/discord.xml
generated
Normal file
@@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="DiscordProjectSettings">
|
||||
<option name="show" value="PROJECT_FILES" />
|
||||
<option name="description" value="" />
|
||||
</component>
|
||||
</project>
|
||||
13
.idea/encodings.xml
generated
Normal file
13
.idea/encodings.xml
generated
Normal file
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="Encoding">
|
||||
<file url="file://$PROJECT_DIR$/core/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/core/src/main/resources" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/jme/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/jme/src/main/resources" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/jse/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/jse/src/main/resources" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/src/main/resources" charset="UTF-8" />
|
||||
</component>
|
||||
</project>
|
||||
25
.idea/jarRepositories.xml
generated
Normal file
25
.idea/jarRepositories.xml
generated
Normal file
@@ -0,0 +1,25 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="RemoteRepositoriesConfiguration">
|
||||
<remote-repository>
|
||||
<option name="id" value="central" />
|
||||
<option name="name" value="Central Repository" />
|
||||
<option name="url" value="https://repo.maven.apache.org/maven2" />
|
||||
</remote-repository>
|
||||
<remote-repository>
|
||||
<option name="id" value="oac" />
|
||||
<option name="name" value="oac" />
|
||||
<option name="url" value="https://repo.open-autonomous-connection.org/api/packages/open-autonomous-connection/maven" />
|
||||
</remote-repository>
|
||||
<remote-repository>
|
||||
<option name="id" value="central" />
|
||||
<option name="name" value="Maven Central repository" />
|
||||
<option name="url" value="https://repo1.maven.org/maven2" />
|
||||
</remote-repository>
|
||||
<remote-repository>
|
||||
<option name="id" value="jboss.community" />
|
||||
<option name="name" value="JBoss Community repository" />
|
||||
<option name="url" value="https://repository.jboss.org/nexus/content/repositories/public/" />
|
||||
</remote-repository>
|
||||
</component>
|
||||
</project>
|
||||
9
.idea/luaj.iml
generated
Normal file
9
.idea/luaj.iml
generated
Normal file
@@ -0,0 +1,9 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<module type="JAVA_MODULE" version="4">
|
||||
<component name="NewModuleRootManager" inherit-compiler-output="true">
|
||||
<exclude-output />
|
||||
<content url="file://$MODULE_DIR$" />
|
||||
<orderEntry type="inheritedJdk" />
|
||||
<orderEntry type="sourceFolder" forTests="false" />
|
||||
</component>
|
||||
</module>
|
||||
18
.idea/misc.xml
generated
Normal file
18
.idea/misc.xml
generated
Normal file
@@ -0,0 +1,18 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ExternalStorageConfigurationManager" enabled="true" />
|
||||
<component name="MavenProjectsManager">
|
||||
<option name="originalFiles">
|
||||
<list>
|
||||
<option value="$PROJECT_DIR$/examples/maven/pom.xml" />
|
||||
<option value="$PROJECT_DIR$/core/pom.xml" />
|
||||
<option value="$PROJECT_DIR$/jme/pom.xml" />
|
||||
<option value="$PROJECT_DIR$/jse/pom.xml" />
|
||||
<option value="$PROJECT_DIR$/pom.xml" />
|
||||
</list>
|
||||
</option>
|
||||
</component>
|
||||
<component name="ProjectRootManager" version="2" project-jdk-name="25" project-jdk-type="JavaSDK">
|
||||
<output url="file://$PROJECT_DIR$/out" />
|
||||
</component>
|
||||
</project>
|
||||
6
.idea/vcs.xml
generated
Normal file
6
.idea/vcs.xml
generated
Normal file
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
||||
75
README.md
75
README.md
@@ -1,6 +1,12 @@
|
||||
# This is a fork!
|
||||
<div style="border: 1px dotted red; margin: 1.em 0.5em; font-weight: bold; color: red;">
|
||||
This repository has been forked from the original CVS sources of Luaj.
|
||||
This repository has been forked from https://github.com/luaj/luaj.<br />
|
||||
The commit history has been converted to make sure that the original work of
|
||||
James Roseborough and Ian Farmer and fork work of luaj/luaj is not lost.
|
||||
</div>
|
||||
<h3>Original repository fork notice:</h3>
|
||||
<div style="border: 1px dotted red; margin: 1.em 0.5em; font-weight: bold; color: red;">
|
||||
The original repository has been forked from the original CVS sources of Luaj.
|
||||
The commit history has been converted to make sure that the original work of
|
||||
James Roseborough and Ian Farmer is not lost.
|
||||
Unfortunately, I was not able to contact either James or Ian to hand over
|
||||
@@ -248,7 +254,7 @@ A simple hello, world example in luaj is:
|
||||
|
||||
<pre>
|
||||
import org.luaj.vm2.*;
|
||||
import org.luaj.vm2.lib.jse.*;
|
||||
import org.luaj.vm2.libs.jse.*;
|
||||
|
||||
Globals globals = JsePlatform.standardGlobals();
|
||||
LuaValue chunk = globals.load("print 'hello, world'");
|
||||
@@ -290,7 +296,7 @@ For MIDlets the <em>JmePlatform</em> is used instead:
|
||||
|
||||
<pre>
|
||||
import org.luaj.vm2.*;
|
||||
import org.luaj.vm2.lib.jme.*;
|
||||
import org.luaj.vm2.libs.jme.*;
|
||||
|
||||
Globals globals = JmePlatform.standardGlobals();
|
||||
LuaValue chunk = globals.loadfile("examples/lua/hello.lua");
|
||||
@@ -311,10 +317,6 @@ A simple example may be found in
|
||||
You must include the library <b>luaj-jme-3.0.2.jar</b> in your midlet jar.
|
||||
|
||||
<p>
|
||||
An ant script to build and run the midlet is in
|
||||
<pre>
|
||||
<a href="build-midlet.xml">build-midlet.xml</a>
|
||||
</pre>
|
||||
|
||||
<p>
|
||||
You must install the wireless toolkit and define <em>WTK_HOME</em> for this script to work.
|
||||
@@ -422,7 +424,6 @@ Applets in browsers should use the JsePlatform. The permissions model in applet
|
||||
highly restrictive, so a specialization of the <a href="#luajava">Luajava</a> library must be used that
|
||||
uses default class loading. This is illustrated in the sample Applet
|
||||
<a href="examples/jse/SampleApplet.java">examples/jse/SampleApplet.java</a>,
|
||||
which can be built using <a href="build-applet.xml">build-applet.xml</a>.
|
||||
|
||||
|
||||
<h3>JmePlatform</h3>
|
||||
@@ -441,7 +442,6 @@ In particular Globals.finder is overridden to load as resources, so scripts shou
|
||||
colocated with class files in the MIDlet jar file. <a href="#luajava">Luajava</a> cannot be used.
|
||||
Camples code is in
|
||||
<a href="examples/jme/SampleMIDlet.java">examples/jme/SampleMIDlet.java</a>,
|
||||
which can be built using <a href="build-midlet.xml">build-midlet.xml</a>.
|
||||
|
||||
|
||||
<h2>Thread Safety</h2>
|
||||
@@ -566,7 +566,7 @@ create globals that contain the debug library in addition to the other standard
|
||||
|
||||
To install dynamically from lua use java-class-based require:</em>:
|
||||
<pre>
|
||||
require 'org.luaj.vm2.lib.DebugLib'
|
||||
require 'org.luaj.vm2.libs.DebugLib'
|
||||
</pre>
|
||||
|
||||
The <em>lua</em> command line utility includes the <em>debug</em> library by default.
|
||||
@@ -666,11 +666,11 @@ The simplest way to implement a function is to choose a base class based on the
|
||||
LuaJ provides 5 base classes for this purpose, depending if the function has 0, 1, 2, 3 or variable arguments,
|
||||
and if it provide multiple return values.
|
||||
<pre>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/ZeroArgFunction.html">org.luaj.vm2.lib.ZeroArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/OneArgFunction.html">org.luaj.vm2.lib.OneArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/TwoArgFunction.html">org.luaj.vm2.lib.TwoArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/ThreeArgFunction.html">org.luaj.vm2.lib.ThreeArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/VarArgFunction.html">org.luaj.vm2.lib.VarArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/ZeroArgFunction.html">org.luaj.vm2.libs.ZeroArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/OneArgFunction.html">org.luaj.vm2.libs.OneArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/TwoArgFunction.html">org.luaj.vm2.libs.TwoArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/ThreeArgFunction.html">org.luaj.vm2.libs.ThreeArgFunction</a>
|
||||
<a href="http://luaj.org/luaj/3.0/api/org/luaj/vm2/lib/VarArgFunction.html">org.luaj.vm2.libs.VarArgFunction</a>
|
||||
</pre>
|
||||
|
||||
Each of these functions has an abstract method that must be implemented,
|
||||
@@ -724,7 +724,7 @@ in the environment that can be called from lua.
|
||||
A complete example of Java code for a simple toy library is in <a href="examples/jse/hyperbolic.java">examples/jse/hyperbolic.java</a>
|
||||
<pre>
|
||||
import org.luaj.vm2.LuaValue;
|
||||
import org.luaj.vm2.lib.*;
|
||||
import org.luaj.vm2.libs.*;
|
||||
|
||||
public class hyperbolic extends TwoArgFunction {
|
||||
|
||||
@@ -858,30 +858,33 @@ An example skelton maven pom file for a skeleton project is in
|
||||
|
||||
|
||||
<h2>Building the jars</h2>
|
||||
Build the jars with maven.
|
||||
<pre>
|
||||
mvn clean verify
|
||||
</pre>
|
||||
An ant file is included in the root directory which builds the libraries by default.
|
||||
|
||||
<p>
|
||||
Other targets exist for creating distribution file an measuring code coverage of unit tests.
|
||||
|
||||
<h2>Unit tests</h2>
|
||||
|
||||
<p>
|
||||
All unit tests are executed during the build.
|
||||
The main luaj JUnit tests are organized into a JUnit 3 suite:
|
||||
<pre>
|
||||
test/junit/org/luaj/vm2/AllTests.lua
|
||||
</pre>
|
||||
|
||||
<p>
|
||||
Test scripts can be found in these locations
|
||||
Unit test scripts can be found in these locations
|
||||
<pre>
|
||||
luaj-test/src/test/resources
|
||||
test/lua/*.lua
|
||||
test/lua/errors/*.lua
|
||||
test/lua/perf/*.lua
|
||||
test/lua/luaj3.0.2-tests.zip
|
||||
</pre>
|
||||
Executon is included in the build of luaj-test.
|
||||
|
||||
<h2>Code coverage</h2>
|
||||
|
||||
<p>
|
||||
The maven build creates the coverage report in the luaj-test/target/site folder
|
||||
during the verify phase.
|
||||
|
||||
It relies on the cobertura code coverage library.
|
||||
|
||||
<h1>8 - <a name="8">Downloads</a></h1>
|
||||
|
||||
@@ -938,7 +941,6 @@ and at <a href="http://luaj.sourceforge.net/api/2.0/index.html">http://luaj.sour
|
||||
<li>Add explicit Globals object to manage global state, especially to imrpove thread safety </li>
|
||||
<li>Drop support for lua source to java surce (lua2java) in favor of direct java bytecode output (luajc) </li>
|
||||
<li>Remove compatibility functions like table.getn(), table.maxn(), table.foreach(), and math.log10() </li>
|
||||
<li>Add ability to create runnable jar file from lua script with sample build file build-app.xml </li>
|
||||
<li>Supply environment as second argument to LibFunction when loading via require() </li>
|
||||
<li>Fix bug 3597515 memory leak due to string caching by simplifying caching logic.</li>
|
||||
<li>Fix bug 3565008 so that short substrings are backed by short arrays.</li>
|
||||
@@ -1021,7 +1023,10 @@ and at <a href="http://luaj.sourceforge.net/api/2.0/index.html">http://luaj.sour
|
||||
<li>debug code may not be completely removed by some obfuscators
|
||||
<li>tail calls are not tracked in debug information
|
||||
<li>mixing different versions of luaj in the same java vm is not supported
|
||||
<li>LuaJ runs on the host VM garbage collector, so object lifetime, weak reference timing, and finalization behavior are not identical to native Lua
|
||||
<li>the <code>__gc</code> metamethod is not supported as a reliable Lua finalization mechanism
|
||||
<li>values associated with weak keys may linger longer than expected
|
||||
<li>cascading weak-table collection can require multiple host GC cycles
|
||||
<li>behavior of luaj when a SecurityManager is used has not been fully characterized
|
||||
<li>negative zero is treated as identical to integer value zero throughout luaj
|
||||
<li>lua compiled into java bytecode using luajc cannot use string.dump() or xpcall()
|
||||
@@ -1029,6 +1034,22 @@ and at <a href="http://luaj.sourceforge.net/api/2.0/index.html">http://luaj.sour
|
||||
<li>shared metatables for string, bool, etc are shared across Globals instances in the same class loader
|
||||
<li>orphaned threads will not be collected unless garbage collection is run and sufficient time elapses
|
||||
</ul>
|
||||
<h3>Garbage Collection And Resources</h3>
|
||||
LuaJ does not implement the same garbage collector semantics as native Lua. Garbage collection is delegated to the host JVM or CLDC runtime, so <code>collectgarbage()</code> is only a hint and should not be used as a resource-management primitive.
|
||||
<p>
|
||||
In particular:
|
||||
<ul>
|
||||
<li>Do not rely on garbage collection to close files, sockets, database handles, or other resources.
|
||||
<li>Always call <code>close()</code> explicitly on files and iterators that own files.
|
||||
<li><code>io.lines(filename)</code> opens a file implicitly. If iteration is abandoned early, that file may remain open until explicitly collected by the host runtime.
|
||||
<li>Prefer <code>local f = assert(io.open(...))</code> together with <code>f:lines()</code> and an explicit <code>f:close()</code> when deterministic cleanup matters.
|
||||
<li>For implicit line iterators that need deterministic early cleanup, use <code>io.linesx(filename)</code> and call <code>iterator:close()</code>.
|
||||
<li><code>file:linesx()</code> provides the same closable iterator API for already-open files.
|
||||
<li>On Windows, leaked file handles can prevent rename or delete operations until the process exits.
|
||||
<li>On JME/CLDC, finalization support may be absent, so explicit close is mandatory.
|
||||
</ul>
|
||||
<p>
|
||||
Short-lived locals may also remain reachable longer than expected because host stack/register reuse is implementation-dependent. If prompt reclamation matters, isolate temporary allocations in functions and clear large references explicitly instead of assuming block exit is enough.
|
||||
<h3>File Character Encoding</h3>
|
||||
Source files can be considered encoded in UTF-8 or ISO-8859-1 and results should be as expected,
|
||||
with literal string contianing quoted characters compiling to the same byte sequences as the input.
|
||||
|
||||
36
core/pom.xml
Normal file
36
core/pom.xml
Normal file
@@ -0,0 +1,36 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<parent>
|
||||
<groupId>org.openautonomousconnection.luaj</groupId>
|
||||
<artifactId>parent</artifactId>
|
||||
<version>3.0.2</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>core</artifactId>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-source-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-sources</id>
|
||||
<goals><goal>jar</goal></goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<configuration>
|
||||
<source>${maven.compiler.release}</source>
|
||||
<target>${maven.compiler.release}</target>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
||||
BIN
core/src/main/java/org/luaj/vm2/Buffer.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Buffer.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,64 +21,61 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
/**
|
||||
* String buffer for use in string library methods, optimized for production of
|
||||
* StrValue instances.
|
||||
* String buffer for use in string library methods, optimized for production
|
||||
* of StrValue instances.
|
||||
* <p>
|
||||
* The buffer can begin initially as a wrapped {@link LuaValue} and only when
|
||||
* concatenation actually occurs are the bytes first copied.
|
||||
* <p>
|
||||
* To convert back to a {@link LuaValue} again, the function
|
||||
* {@link Buffer#value()} is used.
|
||||
*
|
||||
* The buffer can begin initially as a wrapped {@link LuaValue}
|
||||
* and only when concatenation actually occurs are the bytes first copied.
|
||||
* <p>
|
||||
* To convert back to a {@link LuaValue} again,
|
||||
* the function {@link Buffer#value()} is used.
|
||||
* @see LuaValue
|
||||
* @see LuaValue#buffer()
|
||||
* @see LuaString
|
||||
*/
|
||||
public final class Buffer {
|
||||
|
||||
|
||||
/** Default capacity for a buffer: 64 */
|
||||
private static final int DEFAULT_CAPACITY = 64;
|
||||
|
||||
|
||||
/** Shared static array with no bytes */
|
||||
private static final byte[] NOBYTES = {};
|
||||
|
||||
/** Bytes in this buffer */
|
||||
private byte[] bytes;
|
||||
|
||||
|
||||
/** Length of this buffer */
|
||||
private int length;
|
||||
|
||||
|
||||
/** Offset into the byte array */
|
||||
private int offset;
|
||||
|
||||
|
||||
/** Value of this buffer, when not represented in bytes */
|
||||
private LuaValue value;
|
||||
|
||||
|
||||
/**
|
||||
* Create buffer with default capacity
|
||||
*
|
||||
* @see #DEFAULT_CAPACITY
|
||||
*/
|
||||
public Buffer() {
|
||||
this(DEFAULT_CAPACITY);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create buffer with specified initial capacity
|
||||
*
|
||||
* @param initialCapacity the initial capacity
|
||||
*/
|
||||
public Buffer(int initialCapacity) {
|
||||
bytes = new byte[initialCapacity];
|
||||
public Buffer( int initialCapacity ) {
|
||||
bytes = new byte[ initialCapacity ];
|
||||
length = 0;
|
||||
offset = 0;
|
||||
value = null;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create buffer with specified initial value
|
||||
*
|
||||
* @param value the initial value
|
||||
*/
|
||||
public Buffer(LuaValue value) {
|
||||
@@ -87,18 +84,16 @@ public final class Buffer {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Get buffer contents as a {@link LuaValue}
|
||||
*
|
||||
* @return value as a {@link LuaValue}, converting as necessary
|
||||
*/
|
||||
public LuaValue value() {
|
||||
return value != null? value: this.tostring();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Set buffer contents as a {@link LuaValue}
|
||||
*
|
||||
* @param value value to set
|
||||
*/
|
||||
public Buffer setvalue(LuaValue value) {
|
||||
@@ -107,171 +102,145 @@ public final class Buffer {
|
||||
this.value = value;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Convert the buffer to a {@link LuaString}
|
||||
*
|
||||
* @return the value as a {@link LuaString}
|
||||
*/
|
||||
public LuaString tostring() {
|
||||
realloc(length, 0);
|
||||
return LuaString.valueOf(bytes, offset, length);
|
||||
public final LuaString tostring() {
|
||||
realloc( length, 0 );
|
||||
return LuaString.valueOf( bytes, offset, length );
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Convert the buffer to a Java String
|
||||
*
|
||||
* @return the value as a Java String
|
||||
*/
|
||||
public String tojstring() {
|
||||
return value().tojstring();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Convert the buffer to a Java String
|
||||
*
|
||||
* @return the value as a Java String
|
||||
*/
|
||||
@Override
|
||||
public String toString() {
|
||||
return tojstring();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Append a single byte to the buffer.
|
||||
*
|
||||
* @return {@code this} to allow call chaining
|
||||
*/
|
||||
public Buffer append(byte b) {
|
||||
makeroom(0, 1);
|
||||
bytes[offset+length++] = b;
|
||||
public final Buffer append( byte b ) {
|
||||
makeroom( 0, 1 );
|
||||
bytes[ offset + length++ ] = b;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Append a {@link LuaValue} to the buffer.
|
||||
*
|
||||
* @return {@code this} to allow call chaining
|
||||
*/
|
||||
public Buffer append(LuaValue val) {
|
||||
append(val.strvalue());
|
||||
public final Buffer append( LuaValue val ) {
|
||||
append( val.strvalue() );
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Append a {@link LuaString} to the buffer.
|
||||
*
|
||||
* @return {@code this} to allow call chaining
|
||||
*/
|
||||
public Buffer append(LuaString str) {
|
||||
public final Buffer append( LuaString str ) {
|
||||
final int n = str.m_length;
|
||||
makeroom(0, n);
|
||||
str.copyInto(0, bytes, offset+length, n);
|
||||
makeroom( 0, n );
|
||||
str.copyInto( 0, bytes, offset + length, n );
|
||||
length += n;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Append a Java String to the buffer. The Java string will be converted to
|
||||
* bytes using the UTF8 encoding.
|
||||
*
|
||||
|
||||
/**
|
||||
* Append a Java String to the buffer.
|
||||
* The Java string will be converted to bytes using the UTF8 encoding.
|
||||
* @return {@code this} to allow call chaining
|
||||
* @see LuaString#encodeToUtf8(char[], int, byte[], int)
|
||||
*/
|
||||
public Buffer append(String str) {
|
||||
public final Buffer append( String str ) {
|
||||
char[] c = str.toCharArray();
|
||||
final int n = LuaString.lengthAsUtf8(c);
|
||||
makeroom(0, n);
|
||||
LuaString.encodeToUtf8(c, c.length, bytes, offset+length);
|
||||
final int n = LuaString.lengthAsUtf8( c );
|
||||
makeroom( 0, n );
|
||||
LuaString.encodeToUtf8( c, c.length, bytes, offset + length );
|
||||
length += n;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Concatenate this buffer onto a {@link LuaValue}
|
||||
*
|
||||
* @param lhs the left-hand-side value onto which we are concatenating
|
||||
* {@code this}
|
||||
/** Concatenate this buffer onto a {@link LuaValue}
|
||||
* @param lhs the left-hand-side value onto which we are concatenating {@code this}
|
||||
* @return {@link Buffer} for use in call chaining.
|
||||
*/
|
||||
public Buffer concatTo(LuaValue lhs) {
|
||||
return setvalue(lhs.concat(value()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Concatenate this buffer onto a {@link LuaString}
|
||||
*
|
||||
* @param lhs the left-hand-side value onto which we are concatenating
|
||||
* {@code this}
|
||||
/** Concatenate this buffer onto a {@link LuaString}
|
||||
* @param lhs the left-hand-side value onto which we are concatenating {@code this}
|
||||
* @return {@link Buffer} for use in call chaining.
|
||||
*/
|
||||
public Buffer concatTo(LuaString lhs) {
|
||||
return value != null && !value.isstring()? setvalue(lhs.concat(value)): prepend(lhs);
|
||||
return value!=null&&!value.isstring()? setvalue(lhs.concat(value)): prepend(lhs);
|
||||
}
|
||||
|
||||
/**
|
||||
* Concatenate this buffer onto a {@link LuaNumber}
|
||||
/** Concatenate this buffer onto a {@link LuaNumber}
|
||||
* <p>
|
||||
* The {@link LuaNumber} will be converted to a string before concatenating.
|
||||
*
|
||||
* @param lhs the left-hand-side value onto which we are concatenating
|
||||
* {@code this}
|
||||
* The {@link LuaNumber} will be converted to a string before concatenating.
|
||||
* @param lhs the left-hand-side value onto which we are concatenating {@code this}
|
||||
* @return {@link Buffer} for use in call chaining.
|
||||
*/
|
||||
public Buffer concatTo(LuaNumber lhs) {
|
||||
return value != null && !value.isstring()? setvalue(lhs.concat(value)): prepend(lhs.strvalue());
|
||||
return value!=null&&!value.isstring()? setvalue(lhs.concat(value)): prepend(lhs.strvalue());
|
||||
}
|
||||
|
||||
/**
|
||||
* Concatenate bytes from a {@link LuaString} onto the front of this buffer
|
||||
*
|
||||
* @param s the left-hand-side value which we will concatenate onto the
|
||||
* front of {@code this}
|
||||
/** Concatenate bytes from a {@link LuaString} onto the front of this buffer
|
||||
* @param s the left-hand-side value which we will concatenate onto the front of {@code this}
|
||||
* @return {@link Buffer} for use in call chaining.
|
||||
*/
|
||||
public Buffer prepend(LuaString s) {
|
||||
int n = s.m_length;
|
||||
makeroom(n, 0);
|
||||
System.arraycopy(s.m_bytes, s.m_offset, bytes, offset-n, n);
|
||||
makeroom( n, 0 );
|
||||
System.arraycopy( s.m_bytes, s.m_offset, bytes, offset-n, n );
|
||||
offset -= n;
|
||||
length += n;
|
||||
value = null;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Ensure there is enough room before and after the bytes.
|
||||
*
|
||||
* @param nbefore number of unused bytes which must precede the data after
|
||||
* this completes
|
||||
* @param nafter number of unused bytes which must follow the data after
|
||||
* this completes
|
||||
/** Ensure there is enough room before and after the bytes.
|
||||
* @param nbefore number of unused bytes which must precede the data after this completes
|
||||
* @param nafter number of unused bytes which must follow the data after this completes
|
||||
*/
|
||||
public void makeroom(int nbefore, int nafter) {
|
||||
if (value != null) {
|
||||
public final void makeroom( int nbefore, int nafter ) {
|
||||
if ( value != null ) {
|
||||
LuaString s = value.strvalue();
|
||||
value = null;
|
||||
length = s.m_length;
|
||||
offset = nbefore;
|
||||
bytes = new byte[nbefore+length+nafter];
|
||||
System.arraycopy(s.m_bytes, s.m_offset, bytes, offset, length);
|
||||
} else if (offset+length+nafter > bytes.length || offset < nbefore) {
|
||||
} else if ( offset+length+nafter > bytes.length || offset<nbefore ) {
|
||||
int n = nbefore+length+nafter;
|
||||
int m = n < 32? 32: n < length*2? length*2: n;
|
||||
realloc(m, nbefore == 0? 0: m-length-nafter);
|
||||
int m = n<32? 32: n<length*2? length*2: n;
|
||||
realloc( m, nbefore==0? 0: m-length-nafter );
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reallocate the internal storage for the buffer
|
||||
*
|
||||
* @param newSize the size of the buffer to use
|
||||
* @param newOffset the offset to use
|
||||
|
||||
/** Reallocate the internal storage for the buffer
|
||||
* @param newSize the size of the buffer to use
|
||||
* @param newOffset the offset to use
|
||||
*/
|
||||
private void realloc(int newSize, int newOffset) {
|
||||
if (newSize != bytes.length) {
|
||||
byte[] newBytes = new byte[newSize];
|
||||
System.arraycopy(bytes, offset, newBytes, newOffset, length);
|
||||
private final void realloc( int newSize, int newOffset ) {
|
||||
if ( newSize != bytes.length ) {
|
||||
byte[] newBytes = new byte[ newSize ];
|
||||
System.arraycopy( bytes, offset, newBytes, newOffset, length );
|
||||
bytes = newBytes;
|
||||
offset = newOffset;
|
||||
}
|
||||
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$BufferedStream.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$BufferedStream.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$Compiler.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$Compiler.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$Loader.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$Loader.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$StrReader.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$StrReader.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$UTF8Stream.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$UTF8Stream.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals$Undumper.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals$Undumper.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Globals.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Globals.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -26,105 +26,84 @@ import java.io.InputStream;
|
||||
import java.io.PrintStream;
|
||||
import java.io.Reader;
|
||||
|
||||
import org.luaj.vm2.lib.BaseLib;
|
||||
import org.luaj.vm2.lib.DebugLib;
|
||||
import org.luaj.vm2.lib.IoLib;
|
||||
import org.luaj.vm2.lib.PackageLib;
|
||||
import org.luaj.vm2.lib.ResourceFinder;
|
||||
import org.luaj.vm2.libs.BaseLib;
|
||||
import org.luaj.vm2.libs.DebugLib;
|
||||
import org.luaj.vm2.libs.IoLib;
|
||||
import org.luaj.vm2.libs.PackageLib;
|
||||
import org.luaj.vm2.libs.ResourceFinder;
|
||||
|
||||
/**
|
||||
* Global environment used by luaj. Contains global variables referenced by
|
||||
* executing lua.
|
||||
* Global environment used by luaj. Contains global variables referenced by executing lua.
|
||||
* <p>
|
||||
*
|
||||
* <h3>Constructing and Initializing Instances</h3> Typically, this is
|
||||
* constructed indirectly by a call to
|
||||
* {@link org.luaj.vm2.lib.jse.JsePlatform#standardGlobals()} or
|
||||
* {@link org.luaj.vm2.lib.jme.JmePlatform#standardGlobals()}, and then used to
|
||||
* load lua scripts for execution as in the following example.
|
||||
*
|
||||
* <pre>
|
||||
* {
|
||||
* @code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* globals.load(new StringReader("print 'hello'"), "main.lua").call();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
*
|
||||
* <h3>Constructing and Initializing Instances</h3>
|
||||
* Typically, this is constructed indirectly by a call to
|
||||
* {@link org.luaj.vm2.libs.jse.JsePlatform#standardGlobals()} or
|
||||
* {@link org.luaj.vm2.libs.jme.JmePlatform#standardGlobals()},
|
||||
* and then used to load lua scripts for execution as in the following example.
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* globals.load( new StringReader("print 'hello'"), "main.lua" ).call();
|
||||
* } </pre>
|
||||
* The creates a complete global environment with the standard libraries loaded.
|
||||
* <p>
|
||||
* For specialized circumstances, the Globals may be constructed directly and
|
||||
* loaded with only those libraries that are needed, for example.
|
||||
*
|
||||
* <pre>
|
||||
* {
|
||||
* @code
|
||||
* Globals globals = new Globals();
|
||||
* globals.load(new BaseLib());
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* <h3>Loading and Executing Lua Code</h3> Globals contains convenience
|
||||
* functions to load and execute lua source code given a Reader. A simple
|
||||
* example is:
|
||||
*
|
||||
* <pre>
|
||||
* {@code
|
||||
* globals.load( new StringReader("print 'hello'"), "main.lua" ).call();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* <h3>Fine-Grained Control of Compiling and Loading Lua</h3> Executable
|
||||
* LuaFunctions are created from lua code in several steps
|
||||
* For specialized circumstances, the Globals may be constructed directly and loaded
|
||||
* with only those libraries that are needed, for example.
|
||||
* <pre> {@code
|
||||
* Globals globals = new Globals();
|
||||
* globals.load( new BaseLib() );
|
||||
* } </pre>
|
||||
*
|
||||
* <h3>Loading and Executing Lua Code</h3>
|
||||
* Globals contains convenience functions to load and execute lua source code given a Reader.
|
||||
* A simple example is:
|
||||
* <pre> {@code
|
||||
* globals.load( new StringReader("print 'hello'"), "main.lua" ).call();
|
||||
* } </pre>
|
||||
*
|
||||
* <h3>Fine-Grained Control of Compiling and Loading Lua</h3>
|
||||
* Executable LuaFunctions are created from lua code in several steps
|
||||
* <ul>
|
||||
* <li>find the resource using the platform's {@link ResourceFinder}
|
||||
* <li>compile lua to lua bytecode using {@link Compiler}
|
||||
* <li>load lua bytecode to a {@link Prototype} using {@link Undumper}
|
||||
* <li>construct {@link LuaClosure} from {@link Prototype} with {@link Globals}
|
||||
* using {@link Loader}
|
||||
* <li>construct {@link LuaClosure} from {@link Prototype} with {@link Globals} using {@link Loader}
|
||||
* </ul>
|
||||
* <p>
|
||||
* There are alternate flows when the direct lua-to-Java bytecode compiling
|
||||
* {@link org.luaj.vm2.luajc.LuaJC} is used.
|
||||
* There are alternate flows when the direct lua-to-Java bytecode compiling {@link org.luaj.vm2.luajc.LuaJC} is used.
|
||||
* <ul>
|
||||
* <li>compile lua to lua bytecode using {@link Compiler} or load precompiled
|
||||
* code using {@link Undumper}
|
||||
* <li>convert lua bytecode to equivalent Java bytecode using
|
||||
* {@link org.luaj.vm2.luajc.LuaJC} that implements {@link Loader} directly
|
||||
* <li>compile lua to lua bytecode using {@link Compiler} or load precompiled code using {@link Undumper}
|
||||
* <li>convert lua bytecode to equivalent Java bytecode using {@link org.luaj.vm2.luajc.LuaJC} that implements {@link Loader} directly
|
||||
* </ul>
|
||||
*
|
||||
* <h3>Java Field</h3> Certain public fields are provided that contain the
|
||||
* current values of important global state:
|
||||
*
|
||||
* <h3>Java Field</h3>
|
||||
* Certain public fields are provided that contain the current values of important global state:
|
||||
* <ul>
|
||||
* <li>{@link #STDIN} Current value for standard input in the laaded
|
||||
* {@link IoLib}, if any.
|
||||
* <li>{@link #STDOUT} Current value for standard output in the loaded
|
||||
* {@link IoLib}, if any.
|
||||
* <li>{@link #STDERR} Current value for standard error in the loaded
|
||||
* {@link IoLib}, if any.
|
||||
* <li>{@link #STDIN} Current value for standard input in the laaded {@link IoLib}, if any.
|
||||
* <li>{@link #STDOUT} Current value for standard output in the loaded {@link IoLib}, if any.
|
||||
* <li>{@link #STDERR} Current value for standard error in the loaded {@link IoLib}, if any.
|
||||
* <li>{@link #finder} Current loaded {@link ResourceFinder}, if any.
|
||||
* <li>{@link #compiler} Current loaded {@link Compiler}, if any.
|
||||
* <li>{@link #undumper} Current loaded {@link Undumper}, if any.
|
||||
* <li>{@link #loader} Current loaded {@link Loader}, if any.
|
||||
* </ul>
|
||||
*
|
||||
* <h3>Lua Environment Variables</h3> When using
|
||||
* {@link org.luaj.vm2.lib.jse.JsePlatform} or
|
||||
* {@link org.luaj.vm2.lib.jme.JmePlatform}, these environment variables are
|
||||
* created within the Globals.
|
||||
*
|
||||
* <h3>Lua Environment Variables</h3>
|
||||
* When using {@link org.luaj.vm2.libs.jse.JsePlatform} or {@link org.luaj.vm2.libs.jme.JmePlatform},
|
||||
* these environment variables are created within the Globals.
|
||||
* <ul>
|
||||
* <li>"_G" Pointer to this Globals.
|
||||
* <li>"_VERSION" String containing the version of luaj.
|
||||
* </ul>
|
||||
*
|
||||
* <h3>Use in Multithreaded Environments</h3> In a multi-threaded server
|
||||
* environment, each server thread should create one Globals instance, which
|
||||
* will be logically distinct and not interfere with each other, but share
|
||||
* certain static immutable resources such as class data and string data.
|
||||
*
|
||||
* <h3>Use in Multithreaded Environments</h3>
|
||||
* In a multi-threaded server environment, each server thread should create one Globals instance,
|
||||
* which will be logically distinct and not interfere with each other, but share certain
|
||||
* static immutable resources such as class data and string data.
|
||||
* <p>
|
||||
*
|
||||
* @see org.luaj.vm2.lib.jse.JsePlatform
|
||||
* @see org.luaj.vm2.lib.jme.JmePlatform
|
||||
*
|
||||
* @see org.luaj.vm2.libs.jse.JsePlatform
|
||||
* @see org.luaj.vm2.libs.jme.JmePlatform
|
||||
* @see LuaValue
|
||||
* @see Compiler
|
||||
* @see Loader
|
||||
@@ -136,7 +115,7 @@ import org.luaj.vm2.lib.ResourceFinder;
|
||||
public class Globals extends LuaTable {
|
||||
|
||||
/** The current default input stream. */
|
||||
public InputStream STDIN = null;
|
||||
public InputStream STDIN = null;
|
||||
|
||||
/** The current default output stream. */
|
||||
public PrintStream STDOUT = System.out;
|
||||
@@ -146,42 +125,28 @@ public class Globals extends LuaTable {
|
||||
|
||||
/** The installed ResourceFinder for looking files by name. */
|
||||
public ResourceFinder finder;
|
||||
|
||||
/**
|
||||
* The currently running thread. Should not be changed by non-library code.
|
||||
*/
|
||||
|
||||
/** The currently running thread. Should not be changed by non-library code. */
|
||||
public LuaThread running = new LuaThread(this);
|
||||
|
||||
/** The BaseLib instance loaded into this Globals */
|
||||
public BaseLib baselib;
|
||||
|
||||
|
||||
/** The PackageLib instance loaded into this Globals */
|
||||
public PackageLib package_;
|
||||
|
||||
/**
|
||||
* The DebugLib instance loaded into this Globals, or null if debugging is
|
||||
* not enabled
|
||||
*/
|
||||
|
||||
/** The DebugLib instance loaded into this Globals, or null if debugging is not enabled */
|
||||
public DebugLib debuglib;
|
||||
|
||||
/**
|
||||
* Interface for module that converts a Prototype into a LuaFunction with an
|
||||
* environment.
|
||||
*/
|
||||
/** Interface for module that converts a Prototype into a LuaFunction with an environment. */
|
||||
public interface Loader {
|
||||
/**
|
||||
* Convert the prototype into a LuaFunction with the supplied
|
||||
* environment.
|
||||
*/
|
||||
/** Convert the prototype into a LuaFunction with the supplied environment. */
|
||||
LuaFunction load(Prototype prototype, String chunkname, LuaValue env) throws IOException;
|
||||
}
|
||||
|
||||
/** Interface for module that converts lua source text into a prototype. */
|
||||
public interface Compiler {
|
||||
/**
|
||||
* Compile lua source into a Prototype. The InputStream is assumed to be
|
||||
* in UTF-8.
|
||||
*/
|
||||
/** Compile lua source into a Prototype. The InputStream is assumed to be in UTF-8. */
|
||||
Prototype compile(InputStream stream, String chunkname) throws IOException;
|
||||
}
|
||||
|
||||
@@ -190,143 +155,112 @@ public class Globals extends LuaTable {
|
||||
/** Load the supplied input stream into a prototype. */
|
||||
Prototype undump(InputStream stream, String chunkname) throws IOException;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check that this object is a Globals object, and return it, otherwise
|
||||
* throw an error.
|
||||
*/
|
||||
@Override
|
||||
|
||||
/** Check that this object is a Globals object, and return it, otherwise throw an error. */
|
||||
public Globals checkglobals() {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* The installed loader.
|
||||
*
|
||||
* @see Loader
|
||||
*/
|
||||
|
||||
/** The installed loader.
|
||||
* @see Loader */
|
||||
public Loader loader;
|
||||
|
||||
/**
|
||||
* The installed compiler.
|
||||
*
|
||||
* @see Compiler
|
||||
*/
|
||||
/** The installed compiler.
|
||||
* @see Compiler */
|
||||
public Compiler compiler;
|
||||
|
||||
/**
|
||||
* The installed undumper.
|
||||
*
|
||||
* @see Undumper
|
||||
*/
|
||||
/** The installed undumper.
|
||||
* @see Undumper */
|
||||
public Undumper undumper;
|
||||
|
||||
/**
|
||||
* Convenience function for loading a file that is either binary lua or lua
|
||||
* source.
|
||||
*
|
||||
/** Convenience function for loading a file that is either binary lua or lua source.
|
||||
* @param filename Name of the file to load.
|
||||
* @return LuaValue that can be call()'ed or invoke()'ed.
|
||||
* @throws LuaError if the file could not be loaded.
|
||||
*/
|
||||
public LuaValue loadfile(String filename) {
|
||||
InputStream is = null;
|
||||
try {
|
||||
return load(finder.findResource(filename), "@" + filename, "bt", this);
|
||||
is = finder.findResource(filename);
|
||||
if (is == null) {
|
||||
return error("cannot open " + filename + ": No such file or directory");
|
||||
}
|
||||
return load(is, "@"+filename, "bt", this);
|
||||
} catch (Exception e) {
|
||||
return error("load " + filename + ": " + e);
|
||||
return error("load "+filename+": "+e);
|
||||
} finally {
|
||||
if (is != null) {
|
||||
try {
|
||||
is.close();
|
||||
} catch (Exception ignored) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience function to load a string value as a script. Must be lua
|
||||
* source.
|
||||
*
|
||||
* @param script Contents of a lua script, such as "print 'hello,
|
||||
* world.'"
|
||||
/** Convenience function to load a string value as a script. Must be lua source.
|
||||
* @param script Contents of a lua script, such as "print 'hello, world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or
|
||||
* .method() calls.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or .method() calls.
|
||||
* @throws LuaError if the script could not be compiled.
|
||||
*/
|
||||
public LuaValue load(String script, String chunkname) {
|
||||
return load(new StrReader(script), chunkname);
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience function to load a string value as a script. Must be lua
|
||||
* source.
|
||||
*
|
||||
|
||||
/** Convenience function to load a string value as a script. Must be lua source.
|
||||
* @param script Contents of a lua script, such as "print 'hello, world.'"
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or
|
||||
* .method() calls.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or .method() calls.
|
||||
* @throws LuaError if the script could not be compiled.
|
||||
*/
|
||||
public LuaValue load(String script) {
|
||||
return load(new StrReader(script), script);
|
||||
}
|
||||
|
||||
/**
|
||||
* Convenience function to load a string value as a script with a custom
|
||||
* environment. Must be lua source.
|
||||
*
|
||||
* @param script Contents of a lua script, such as "print 'hello,
|
||||
* world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param environment LuaTable to be used as the environment for the loaded
|
||||
* function.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or
|
||||
* .method() calls.
|
||||
/** Convenience function to load a string value as a script with a custom environment.
|
||||
* Must be lua source.
|
||||
* @param script Contents of a lua script, such as "print 'hello, world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param environment LuaTable to be used as the environment for the loaded function.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or .method() calls.
|
||||
* @throws LuaError if the script could not be compiled.
|
||||
*/
|
||||
public LuaValue load(String script, String chunkname, LuaTable environment) {
|
||||
return load(new StrReader(script), chunkname, environment);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load the content form a reader as a text file. Must be lua source. The
|
||||
* source is converted to UTF-8, so any characters appearing in quoted
|
||||
* literals above the range 128 will be converted into multiple bytes.
|
||||
*
|
||||
* @param reader Reader containing text of a lua script, such as "print
|
||||
* 'hello, world.'"
|
||||
/** Load the content form a reader as a text file. Must be lua source.
|
||||
* The source is converted to UTF-8, so any characters appearing in quoted literals
|
||||
* above the range 128 will be converted into multiple bytes.
|
||||
* @param reader Reader containing text of a lua script, such as "print 'hello, world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or
|
||||
* .method() calls.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or .method() calls.
|
||||
* @throws LuaError if the script could not be compiled.
|
||||
*/
|
||||
*/
|
||||
public LuaValue load(Reader reader, String chunkname) {
|
||||
return load(new UTF8Stream(reader), chunkname, "t", this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load the content form a reader as a text file, supplying a custom
|
||||
* environment. Must be lua source. The source is converted to UTF-8, so any
|
||||
* characters appearing in quoted literals above the range 128 will be
|
||||
* converted into multiple bytes.
|
||||
*
|
||||
* @param reader Reader containing text of a lua script, such as "print
|
||||
* 'hello, world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param environment LuaTable to be used as the environment for the loaded
|
||||
* function.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or
|
||||
* .method() calls.
|
||||
/** Load the content form a reader as a text file, supplying a custom environment.
|
||||
* Must be lua source. The source is converted to UTF-8, so any characters
|
||||
* appearing in quoted literals above the range 128 will be converted into
|
||||
* multiple bytes.
|
||||
* @param reader Reader containing text of a lua script, such as "print 'hello, world.'"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param environment LuaTable to be used as the environment for the loaded function.
|
||||
* @return LuaValue that may be executed via .call(), .invoke(), or .method() calls.
|
||||
* @throws LuaError if the script could not be compiled.
|
||||
*/
|
||||
*/
|
||||
public LuaValue load(Reader reader, String chunkname, LuaTable environment) {
|
||||
return load(new UTF8Stream(reader), chunkname, "t", environment);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Load the content form an input stream as a binary chunk or text file.
|
||||
*
|
||||
* @param is InputStream containing a lua script or compiled lua"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param mode String containing 'b' or 't' or both to control
|
||||
* loading as binary or text or either.
|
||||
* @param environment LuaTable to be used as the environment for the loaded
|
||||
* function.
|
||||
*/
|
||||
/** Load the content form an input stream as a binary chunk or text file.
|
||||
* @param is InputStream containing a lua script or compiled lua"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param mode String containing 'b' or 't' or both to control loading as binary or text or either.
|
||||
* @param environment LuaTable to be used as the environment for the loaded function.
|
||||
* */
|
||||
public LuaValue load(InputStream is, String chunkname, String mode, LuaValue environment) {
|
||||
try {
|
||||
Prototype p = loadPrototype(is, chunkname, mode);
|
||||
@@ -334,20 +268,16 @@ public class Globals extends LuaTable {
|
||||
} catch (LuaError l) {
|
||||
throw l;
|
||||
} catch (Exception e) {
|
||||
return error("load " + chunkname + ": " + e);
|
||||
return error("load "+chunkname+": "+e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Load lua source or lua binary from an input stream into a Prototype. The
|
||||
* InputStream is either a binary lua chunk starting with the lua binary
|
||||
* chunk signature, or a text input file. If it is a text input file, it is
|
||||
* interpreted as a UTF-8 byte sequence.
|
||||
*
|
||||
* @param is Input stream containing a lua script or compiled lua"
|
||||
/** Load lua source or lua binary from an input stream into a Prototype.
|
||||
* The InputStream is either a binary lua chunk starting with the lua binary chunk signature,
|
||||
* or a text input file. If it is a text input file, it is interpreted as a UTF-8 byte sequence.
|
||||
* @param is Input stream containing a lua script or compiled lua"
|
||||
* @param chunkname Name that will be used within the chunk as the source.
|
||||
* @param mode String containing 'b' or 't' or both to control loading
|
||||
* as binary or text or either.
|
||||
* @param mode String containing 'b' or 't' or both to control loading as binary or text or either.
|
||||
*/
|
||||
public Prototype loadPrototype(InputStream is, String chunkname, String mode) throws IOException {
|
||||
if (mode.indexOf('b') >= 0) {
|
||||
@@ -364,25 +294,21 @@ public class Globals extends LuaTable {
|
||||
if (mode.indexOf('t') >= 0) {
|
||||
return compilePrototype(is, chunkname);
|
||||
}
|
||||
error("Failed to load prototype " + chunkname + " using mode '" + mode + "'");
|
||||
error("Failed to load prototype "+chunkname+" using mode '"+mode+"'");
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compile lua source from a Reader into a Prototype. The characters in the
|
||||
* reader are converted to bytes using the UTF-8 encoding, so a string
|
||||
* literal containing characters with codepoints 128 or above will be
|
||||
* converted into multiple bytes.
|
||||
|
||||
/** Compile lua source from a Reader into a Prototype. The characters in the reader
|
||||
* are converted to bytes using the UTF-8 encoding, so a string literal containing
|
||||
* characters with codepoints 128 or above will be converted into multiple bytes.
|
||||
*/
|
||||
public Prototype compilePrototype(Reader reader, String chunkname) throws IOException {
|
||||
return compilePrototype(new UTF8Stream(reader), chunkname);
|
||||
}
|
||||
|
||||
/**
|
||||
* Compile lua source from an InputStream into a Prototype. The input is
|
||||
* assumed to be UTf-8, but since bytes in the range 128-255 are passed
|
||||
* along as literal bytes, any ASCII-compatible encoding such as ISO 8859-1
|
||||
* may also be used.
|
||||
|
||||
/** Compile lua source from an InputStream into a Prototype.
|
||||
* The input is assumed to be UTf-8, but since bytes in the range 128-255 are passed along as
|
||||
* literal bytes, any ASCII-compatible encoding such as ISO 8859-1 may also be used.
|
||||
*/
|
||||
public Prototype compilePrototype(InputStream stream, String chunkname) throws IOException {
|
||||
if (compiler == null)
|
||||
@@ -390,13 +316,9 @@ public class Globals extends LuaTable {
|
||||
return compiler.compile(stream, chunkname);
|
||||
}
|
||||
|
||||
/**
|
||||
* Function which yields the current thread.
|
||||
*
|
||||
* @param args Arguments to supply as return values in the resume function
|
||||
* of the resuming thread.
|
||||
* @return Values supplied as arguments to the resume() call that
|
||||
* reactivates this thread.
|
||||
/** Function which yields the current thread.
|
||||
* @param args Arguments to supply as return values in the resume function of the resuming thread.
|
||||
* @return Values supplied as arguments to the resume() call that reactivates this thread.
|
||||
*/
|
||||
public Varargs yield(Varargs args) {
|
||||
if (running == null || running.isMainThread())
|
||||
@@ -408,30 +330,23 @@ public class Globals extends LuaTable {
|
||||
/** Reader implementation to read chars from a String in JME or JSE. */
|
||||
static class StrReader extends Reader {
|
||||
final String s;
|
||||
int i = 0;
|
||||
final int n;
|
||||
|
||||
int i = 0;
|
||||
final int n;
|
||||
StrReader(String s) {
|
||||
this.s = s;
|
||||
n = s.length();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() throws IOException {
|
||||
i = n;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int read() throws IOException {
|
||||
return i < n? s.charAt(i++): -1;
|
||||
return i < n ? s.charAt(i++) : -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int read(char[] cbuf, int off, int len) throws IOException {
|
||||
int j = 0;
|
||||
for (; j < len && i < n; ++j, ++i)
|
||||
cbuf[off+j] = s.charAt(i);
|
||||
return j > 0 || len == 0? j: -1;
|
||||
return j > 0 || len == 0 ? j : -1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -440,67 +355,49 @@ public class Globals extends LuaTable {
|
||||
*/
|
||||
abstract static class AbstractBufferedStream extends InputStream {
|
||||
protected byte[] b;
|
||||
protected int i = 0, j = 0;
|
||||
|
||||
protected int i = 0, j = 0;
|
||||
protected AbstractBufferedStream(int buflen) {
|
||||
this.b = new byte[buflen];
|
||||
}
|
||||
|
||||
abstract protected int avail() throws IOException;
|
||||
|
||||
@Override
|
||||
public int read() throws IOException {
|
||||
int a = avail();
|
||||
return a <= 0? -1: 0xff & b[i++];
|
||||
return (a <= 0 ? -1 : 0xff & b[i++]);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int read(byte[] b) throws IOException {
|
||||
return read(b, 0, b.length);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int read(byte[] b, int i0, int n) throws IOException {
|
||||
int a = avail();
|
||||
if (a <= 0)
|
||||
return -1;
|
||||
if (a <= 0) return -1;
|
||||
final int n_read = Math.min(a, n);
|
||||
System.arraycopy(this.b, i, b, i0, n_read);
|
||||
System.arraycopy(this.b, i, b, i0, n_read);
|
||||
i += n_read;
|
||||
return n_read;
|
||||
}
|
||||
|
||||
@Override
|
||||
public long skip(long n) throws IOException {
|
||||
final long k = Math.min(n, j-i);
|
||||
final long k = Math.min(n, j - i);
|
||||
i += k;
|
||||
return k;
|
||||
}
|
||||
|
||||
@Override
|
||||
}
|
||||
public int available() throws IOException {
|
||||
return j-i;
|
||||
return j - i;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Simple converter from Reader to InputStream using UTF8 encoding that will
|
||||
* work on both JME and JSE. This class may be moved to its own package in
|
||||
* the future.
|
||||
/** Simple converter from Reader to InputStream using UTF8 encoding that will work
|
||||
* on both JME and JSE.
|
||||
* This class may be moved to its own package in the future.
|
||||
*/
|
||||
static class UTF8Stream extends AbstractBufferedStream {
|
||||
private final char[] c = new char[32];
|
||||
private final Reader r;
|
||||
|
||||
UTF8Stream(Reader r) {
|
||||
super(96);
|
||||
this.r = r;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected int avail() throws IOException {
|
||||
if (i < j)
|
||||
return j-i;
|
||||
if (i < j) return j - i;
|
||||
int n = r.read(c);
|
||||
if (n < 0)
|
||||
return -1;
|
||||
@@ -514,40 +411,31 @@ public class Globals extends LuaTable {
|
||||
j = LuaString.encodeToUtf8(c, n, b, i = 0);
|
||||
return j;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() throws IOException {
|
||||
r.close();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Simple buffered InputStream that supports mark. Used to examine an
|
||||
* InputStream for a 4-byte binary lua signature, and fall back to text
|
||||
* input when the signature is not found, as well as speed up normal
|
||||
* compilation and reading of lua scripts. This class may be moved to its
|
||||
* own package in the future.
|
||||
|
||||
/** Simple buffered InputStream that supports mark.
|
||||
* Used to examine an InputStream for a 4-byte binary lua signature,
|
||||
* and fall back to text input when the signature is not found,
|
||||
* as well as speed up normal compilation and reading of lua scripts.
|
||||
* This class may be moved to its own package in the future.
|
||||
*/
|
||||
static class BufferedStream extends AbstractBufferedStream {
|
||||
private final InputStream s;
|
||||
|
||||
public BufferedStream(InputStream s) {
|
||||
this(128, s);
|
||||
}
|
||||
|
||||
BufferedStream(int buflen, InputStream s) {
|
||||
super(buflen);
|
||||
this.s = s;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected int avail() throws IOException {
|
||||
if (i < j)
|
||||
return j-i;
|
||||
if (j >= b.length)
|
||||
i = j = 0;
|
||||
if (i < j) return j - i;
|
||||
if (j >= b.length) i = j = 0;
|
||||
// leave previous bytes in place to implement mark()/reset().
|
||||
int n = s.read(b, j, b.length-j);
|
||||
int n = s.read(b, j, b.length - j);
|
||||
if (n < 0)
|
||||
return -1;
|
||||
if (n == 0) {
|
||||
@@ -560,29 +448,21 @@ public class Globals extends LuaTable {
|
||||
j += n;
|
||||
return n;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() throws IOException {
|
||||
s.close();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void mark(int n) {
|
||||
if (i > 0 || n > b.length) {
|
||||
byte[] dest = n > b.length? new byte[n]: b;
|
||||
System.arraycopy(b, i, dest, 0, j-i);
|
||||
byte[] dest = n > b.length ? new byte[n] : b;
|
||||
System.arraycopy(b, i, dest, 0, j - i);
|
||||
j -= i;
|
||||
i = 0;
|
||||
b = dest;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean markSupported() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void reset() throws IOException {
|
||||
i = 0;
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LoadState$GlobalsUndumper.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LoadState$GlobalsUndumper.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LoadState.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LoadState.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -25,141 +25,116 @@ import java.io.DataInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
|
||||
/**
|
||||
* Class to undump compiled lua bytecode into a {@link Prototype} instances.
|
||||
* <p>
|
||||
* The {@link LoadState} class provides the default {@link Globals.Undumper}
|
||||
* which is used to undump a string of bytes that represent a lua binary file
|
||||
* using either the C-based lua compiler, or luaj's
|
||||
* {@link org.luaj.vm2.compiler.LuaC} compiler.
|
||||
* <p>
|
||||
* The canonical method to load and execute code is done indirectly using the
|
||||
* Globals:
|
||||
*
|
||||
* <pre>
|
||||
* {
|
||||
* @code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* LuaValue chunk = globasl.load("print('hello, world')", "main.lua");
|
||||
* chunk.call();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* This should work regardless of which {@link Globals.Compiler} or
|
||||
* {@link Globals.Undumper} have been installed.
|
||||
* <p>
|
||||
* By default, when using {@link org.luaj.vm2.lib.jse.JsePlatform} or
|
||||
* {@link org.luaj.vm2.lib.jme.JmePlatform} to construct globals, the
|
||||
* {@link LoadState} default undumper is installed as the default
|
||||
* {@link Globals.Undumper}.
|
||||
* <p>
|
||||
*
|
||||
* A lua binary file is created via the {@link org.luaj.vm2.compiler.DumpState}
|
||||
* class :
|
||||
*
|
||||
* <pre>
|
||||
* {
|
||||
* @code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* Prototype p = globals.compilePrototype(new StringReader("print('hello, world')"), "main.lua");
|
||||
* ByteArrayOutputStream o = new ByteArrayOutputStream();
|
||||
* org.luaj.vm2.compiler.DumpState.dump(p, o, false);
|
||||
* byte[] lua_binary_file_bytes = o.toByteArray();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* The {@link LoadState}'s default undumper {@link #instance} may be used
|
||||
* directly to undump these bytes:
|
||||
*
|
||||
* <pre>
|
||||
* {@code
|
||||
* Class to undump compiled lua bytecode into a {@link Prototype} instances.
|
||||
* <p>
|
||||
* The {@link LoadState} class provides the default {@link Globals.Undumper}
|
||||
* which is used to undump a string of bytes that represent a lua binary file
|
||||
* using either the C-based lua compiler, or luaj's
|
||||
* {@link org.luaj.vm2.compiler.LuaC} compiler.
|
||||
* <p>
|
||||
* The canonical method to load and execute code is done
|
||||
* indirectly using the Globals:
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* LuaValue chunk = globasl.load("print('hello, world')", "main.lua");
|
||||
* chunk.call();
|
||||
* } </pre>
|
||||
* This should work regardless of which {@link Globals.Compiler} or {@link Globals.Undumper}
|
||||
* have been installed.
|
||||
* <p>
|
||||
* By default, when using {@link org.luaj.vm2.libs.jse.JsePlatform} or
|
||||
* {@link org.luaj.vm2.libs.jme.JmePlatform}
|
||||
* to construct globals, the {@link LoadState} default undumper is installed
|
||||
* as the default {@link Globals.Undumper}.
|
||||
* <p>
|
||||
*
|
||||
* A lua binary file is created via the {@link org.luaj.vm2.compiler.DumpState} class
|
||||
:
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* Prototype p = globals.compilePrototype(new StringReader("print('hello, world')"), "main.lua");
|
||||
* ByteArrayOutputStream o = new ByteArrayOutputStream();
|
||||
* org.luaj.vm2.compiler.DumpState.dump(p, o, false);
|
||||
* byte[] lua_binary_file_bytes = o.toByteArray();
|
||||
* } </pre>
|
||||
*
|
||||
* The {@link LoadState}'s default undumper {@link #instance}
|
||||
* may be used directly to undump these bytes:
|
||||
* <pre> {@code
|
||||
* Prototypep = LoadState.instance.undump(new ByteArrayInputStream(lua_binary_file_bytes), "main.lua");
|
||||
* LuaClosure c = new LuaClosure(p, globals);
|
||||
* c.call();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
*
|
||||
* More commonly, the {@link Globals.Undumper} may be used to undump them:
|
||||
*
|
||||
* <pre>
|
||||
* {
|
||||
* @code
|
||||
* Prototype p = globals.loadPrototype(new ByteArrayInputStream(lua_binary_file_bytes), "main.lua", "b");
|
||||
* LuaClosure c = new LuaClosure(p, globals);
|
||||
* c.call();
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* @see Globals.Compiler
|
||||
* @see Globals.Undumper
|
||||
* @see LuaClosure
|
||||
* @see LuaFunction
|
||||
* @see org.luaj.vm2.compiler.LuaC
|
||||
* @see org.luaj.vm2.luajc.LuaJC
|
||||
* @see Globals#compiler
|
||||
* @see Globals#load(InputStream, String, LuaValue)
|
||||
*/
|
||||
* } </pre>
|
||||
*
|
||||
*
|
||||
* More commonly, the {@link Globals.Undumper} may be used to undump them:
|
||||
* <pre> {@code
|
||||
* Prototype p = globals.loadPrototype(new ByteArrayInputStream(lua_binary_file_bytes), "main.lua", "b");
|
||||
* LuaClosure c = new LuaClosure(p, globals);
|
||||
* c.call();
|
||||
* } </pre>
|
||||
*
|
||||
* @see Globals.Compiler
|
||||
* @see Globals.Undumper
|
||||
* @see LuaClosure
|
||||
* @see LuaFunction
|
||||
* @see org.luaj.vm2.compiler.LuaC
|
||||
* @see org.luaj.vm2.luajc.LuaJC
|
||||
* @see Globals#compiler
|
||||
* @see Globals#load(InputStream, String, LuaValue)
|
||||
*/
|
||||
public class LoadState {
|
||||
|
||||
/**
|
||||
* Shared instance of Globals.Undumper to use loading prototypes from binary
|
||||
* lua files
|
||||
*/
|
||||
/** Shared instance of Globals.Undumper to use loading prototypes from binary lua files */
|
||||
public static final Globals.Undumper instance = new GlobalsUndumper();
|
||||
|
||||
/**
|
||||
* format corresponding to non-number-patched lua, all numbers are floats or
|
||||
* doubles
|
||||
*/
|
||||
public static final int NUMBER_FORMAT_FLOATS_OR_DOUBLES = 0;
|
||||
|
||||
/** format corresponding to non-number-patched lua, all numbers are floats or doubles */
|
||||
public static final int NUMBER_FORMAT_FLOATS_OR_DOUBLES = 0;
|
||||
|
||||
/** format corresponding to non-number-patched lua, all numbers are ints */
|
||||
public static final int NUMBER_FORMAT_INTS_ONLY = 1;
|
||||
|
||||
/**
|
||||
* format corresponding to number-patched lua, all numbers are 32-bit (4
|
||||
* byte) ints
|
||||
*/
|
||||
public static final int NUMBER_FORMAT_NUM_PATCH_INT32 = 4;
|
||||
|
||||
public static final int NUMBER_FORMAT_INTS_ONLY = 1;
|
||||
|
||||
/** format corresponding to number-patched lua, all numbers are 32-bit (4 byte) ints */
|
||||
public static final int NUMBER_FORMAT_NUM_PATCH_INT32 = 4;
|
||||
|
||||
// type constants
|
||||
public static final int LUA_TINT = -2;
|
||||
public static final int LUA_TNONE = -1;
|
||||
public static final int LUA_TNIL = 0;
|
||||
public static final int LUA_TBOOLEAN = 1;
|
||||
public static final int LUA_TLIGHTUSERDATA = 2;
|
||||
public static final int LUA_TNUMBER = 3;
|
||||
public static final int LUA_TSTRING = 4;
|
||||
public static final int LUA_TTABLE = 5;
|
||||
public static final int LUA_TFUNCTION = 6;
|
||||
public static final int LUA_TUSERDATA = 7;
|
||||
public static final int LUA_TTHREAD = 8;
|
||||
public static final int LUA_TVALUE = 9;
|
||||
|
||||
/**
|
||||
* The character encoding to use for file encoding. Null means the default
|
||||
* encoding
|
||||
*/
|
||||
public static final int LUA_TINT = (-2);
|
||||
public static final int LUA_TNONE = (-1);
|
||||
public static final int LUA_TNIL = 0;
|
||||
public static final int LUA_TBOOLEAN = 1;
|
||||
public static final int LUA_TLIGHTUSERDATA = 2;
|
||||
public static final int LUA_TNUMBER = 3;
|
||||
public static final int LUA_TSTRING = 4;
|
||||
public static final int LUA_TTABLE = 5;
|
||||
public static final int LUA_TFUNCTION = 6;
|
||||
public static final int LUA_TUSERDATA = 7;
|
||||
public static final int LUA_TTHREAD = 8;
|
||||
public static final int LUA_TVALUE = 9;
|
||||
|
||||
/** The character encoding to use for file encoding. Null means the default encoding */
|
||||
public static String encoding = null;
|
||||
|
||||
|
||||
/** Signature byte indicating the file is a compiled binary chunk */
|
||||
public static final byte[] LUA_SIGNATURE = { '\033', 'L', 'u', 'a' };
|
||||
public static final byte[] LUA_SIGNATURE = { '\033', 'L', 'u', 'a' };
|
||||
|
||||
/** Data to catch conversion errors */
|
||||
public static final byte[] LUAC_TAIL = { (byte) 0x19, (byte) 0x93, '\r', '\n', (byte) 0x1a, '\n', };
|
||||
|
||||
|
||||
/** Name for compiled chunks */
|
||||
public static final String SOURCE_BINARY_STRING = "binary string";
|
||||
|
||||
|
||||
/** for header of binary files -- this is Lua 5.2 */
|
||||
public static final int LUAC_VERSION = 0x52;
|
||||
public static final int LUAC_VERSION = 0x52;
|
||||
|
||||
/** for header of binary files -- this is the official format */
|
||||
public static final int LUAC_FORMAT = 0;
|
||||
public static final int LUAC_FORMAT = 0;
|
||||
|
||||
/** size of header of binary files */
|
||||
public static final int LUAC_HEADERSIZE = 12;
|
||||
public static final int LUAC_HEADERSIZE = 12;
|
||||
|
||||
// values read from the header
|
||||
private int luacVersion;
|
||||
@@ -169,7 +144,7 @@ public class LoadState {
|
||||
private int luacSizeofSizeT;
|
||||
private int luacSizeofInstruction;
|
||||
private int luacSizeofLuaNumber;
|
||||
private int luacNumberFormat;
|
||||
private int luacNumberFormat;
|
||||
|
||||
/** input stream from which we are loading */
|
||||
public final DataInputStream is;
|
||||
@@ -177,148 +152,135 @@ public class LoadState {
|
||||
/** Name of what is being loaded? */
|
||||
String name;
|
||||
|
||||
private static final LuaValue[] NOVALUES = {};
|
||||
private static final Prototype[] NOPROTOS = {};
|
||||
private static final LocVars[] NOLOCVARS = {};
|
||||
private static final Upvaldesc[] NOUPVALDESCS = {};
|
||||
private static final int[] NOINTS = {};
|
||||
|
||||
private static final LuaValue[] NOVALUES = {};
|
||||
private static final Prototype[] NOPROTOS = {};
|
||||
private static final LocVars[] NOLOCVARS = {};
|
||||
private static final Upvaldesc[] NOUPVALDESCS = {};
|
||||
private static final int[] NOINTS = {};
|
||||
|
||||
/** Read buffer */
|
||||
private byte[] buf = new byte[512];
|
||||
|
||||
/**
|
||||
* Install this class as the standard Globals.Undumper for the supplied
|
||||
* Globals
|
||||
*/
|
||||
/** Install this class as the standard Globals.Undumper for the supplied Globals */
|
||||
public static void install(Globals globals) {
|
||||
globals.undumper = instance;
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a 4-byte int value from the input stream
|
||||
*
|
||||
|
||||
/** Load a 4-byte int value from the input stream
|
||||
* @return the int value laoded.
|
||||
**/
|
||||
int loadInt() throws IOException {
|
||||
is.readFully(buf, 0, 4);
|
||||
return luacLittleEndian? buf[3]<<24 | (0xff & buf[2])<<16 | (0xff & buf[1])<<8 | 0xff & buf[0]
|
||||
: buf[0]<<24 | (0xff & buf[1])<<16 | (0xff & buf[2])<<8 | 0xff & buf[3];
|
||||
is.readFully(buf,0,4);
|
||||
return luacLittleEndian?
|
||||
(buf[3] << 24) | ((0xff & buf[2]) << 16) | ((0xff & buf[1]) << 8) | (0xff & buf[0]):
|
||||
(buf[0] << 24) | ((0xff & buf[1]) << 16) | ((0xff & buf[2]) << 8) | (0xff & buf[3]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load an array of int values from the input stream
|
||||
*
|
||||
|
||||
/** Load an array of int values from the input stream
|
||||
* @return the array of int values laoded.
|
||||
**/
|
||||
int[] loadIntArray() throws IOException {
|
||||
int n = loadInt();
|
||||
if (n == 0)
|
||||
if ( n == 0 )
|
||||
return NOINTS;
|
||||
|
||||
|
||||
// read all data at once
|
||||
int m = n<<2;
|
||||
if (buf.length < m)
|
||||
int m = n << 2;
|
||||
if ( buf.length < m )
|
||||
buf = new byte[m];
|
||||
is.readFully(buf, 0, m);
|
||||
is.readFully(buf,0,m);
|
||||
int[] array = new int[n];
|
||||
for (int i = 0, j = 0; i < n; ++i, j += 4)
|
||||
array[i] = luacLittleEndian? buf[j+3]<<24 | (0xff & buf[j+2])<<16 | (0xff & buf[j+1])<<8 | 0xff & buf[j+0]
|
||||
: buf[j+0]<<24 | (0xff & buf[j+1])<<16 | (0xff & buf[j+2])<<8 | 0xff & buf[j+3];
|
||||
for ( int i=0, j=0; i<n; ++i, j+=4 )
|
||||
array[i] = luacLittleEndian?
|
||||
(buf[j+3] << 24) | ((0xff & buf[j+2]) << 16) | ((0xff & buf[j+1]) << 8) | (0xff & buf[j+0]):
|
||||
(buf[j+0] << 24) | ((0xff & buf[j+1]) << 16) | ((0xff & buf[j+2]) << 8) | (0xff & buf[j+3]);
|
||||
|
||||
return array;
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a long value from the input stream
|
||||
*
|
||||
|
||||
/** Load a long value from the input stream
|
||||
* @return the long value laoded.
|
||||
**/
|
||||
long loadInt64() throws IOException {
|
||||
int a, b;
|
||||
if (this.luacLittleEndian) {
|
||||
int a,b;
|
||||
if ( this.luacLittleEndian ) {
|
||||
a = loadInt();
|
||||
b = loadInt();
|
||||
} else {
|
||||
b = loadInt();
|
||||
a = loadInt();
|
||||
}
|
||||
return (long) b<<32 | a & 0xffffffffL;
|
||||
return (((long)b)<<32) | (((long)a)&0xffffffffL);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a lua strin gvalue from the input stream
|
||||
*
|
||||
/** Load a lua strin gvalue from the input stream
|
||||
* @return the {@link LuaString} value laoded.
|
||||
**/
|
||||
LuaString loadString() throws IOException {
|
||||
int size = this.luacSizeofSizeT == 8? (int) loadInt64(): loadInt();
|
||||
if (size == 0)
|
||||
if ( size == 0 )
|
||||
return null;
|
||||
byte[] bytes = new byte[size];
|
||||
is.readFully(bytes, 0, size);
|
||||
return LuaString.valueUsing(bytes, 0, bytes.length-1);
|
||||
is.readFully( bytes, 0, size );
|
||||
return LuaString.valueUsing( bytes, 0, bytes.length - 1 );
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Convert bits in a long value to a {@link LuaValue}.
|
||||
*
|
||||
* @param bits long value containing the bits
|
||||
* @return {@link LuaInteger} or {@link LuaDouble} whose value corresponds
|
||||
* to the bits provided.
|
||||
* @return {@link LuaInteger} or {@link LuaDouble} whose value corresponds to the bits provided.
|
||||
*/
|
||||
public static LuaValue longBitsToLuaNumber(long bits) {
|
||||
if ((bits & (1L<<63)-1) == 0L) {
|
||||
public static LuaValue longBitsToLuaNumber( long bits ) {
|
||||
if ( ( bits & ( ( 1L << 63 ) - 1 ) ) == 0L ) {
|
||||
return LuaValue.ZERO;
|
||||
}
|
||||
|
||||
int e = (int) (bits>>52 & 0x7ffL)-1023;
|
||||
|
||||
if (e >= 0 && e < 31) {
|
||||
|
||||
int e = (int)((bits >> 52) & 0x7ffL) - 1023;
|
||||
|
||||
if ( e >= 0 && e < 63 ) {
|
||||
long f = bits & 0xFFFFFFFFFFFFFL;
|
||||
int shift = 52-e;
|
||||
long intPrecMask = (1L<<shift)-1;
|
||||
if ((f & intPrecMask) == 0) {
|
||||
int intValue = (int) (f>>shift) | 1<<e;
|
||||
return LuaInteger.valueOf(bits>>63 != 0? -intValue: intValue);
|
||||
int shift = 52 - e;
|
||||
long intPrecMask = shift > 0 ? ( 1L << shift ) - 1 : 0;
|
||||
if ( shift <= 52 && ( f & intPrecMask ) == 0 ) {
|
||||
long intValue = shift >= 0 ? (f >> shift) | (1L << e) : (f << (-shift)) | (1L << e);
|
||||
return LuaInteger.valueOf( ( ( bits >> 63 ) != 0 ) ? -intValue : intValue );
|
||||
}
|
||||
}
|
||||
|
||||
return LuaValue.valueOf(Double.longBitsToDouble(bits));
|
||||
|
||||
return LuaValue.valueOf( Double.longBitsToDouble(bits) );
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Load a number from a binary chunk
|
||||
*
|
||||
* @return the {@link LuaValue} loaded
|
||||
* @throws IOException if an i/o exception occurs
|
||||
*/
|
||||
LuaValue loadNumber() throws IOException {
|
||||
if (luacNumberFormat == NUMBER_FORMAT_INTS_ONLY) {
|
||||
return LuaInteger.valueOf(loadInt());
|
||||
if ( luacNumberFormat == NUMBER_FORMAT_INTS_ONLY ) {
|
||||
return LuaInteger.valueOf( loadInt() );
|
||||
} else {
|
||||
return longBitsToLuaNumber(loadInt64());
|
||||
return longBitsToLuaNumber( loadInt64() );
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a list of constants from a binary chunk
|
||||
*
|
||||
* @param f the function prototype
|
||||
* @throws IOException if an i/o exception occurs
|
||||
*/
|
||||
void loadConstants(Prototype f) throws IOException {
|
||||
int n = loadInt();
|
||||
LuaValue[] values = n > 0? new LuaValue[n]: NOVALUES;
|
||||
for (int i = 0; i < n; i++) {
|
||||
switch (is.readByte()) {
|
||||
LuaValue[] values = n>0? new LuaValue[n]: NOVALUES;
|
||||
for ( int i=0; i<n; i++ ) {
|
||||
switch ( is.readByte() ) {
|
||||
case LUA_TNIL:
|
||||
values[i] = LuaValue.NIL;
|
||||
break;
|
||||
case LUA_TBOOLEAN:
|
||||
values[i] = 0 != is.readUnsignedByte()? LuaValue.TRUE: LuaValue.FALSE;
|
||||
values[i] = (0 != is.readUnsignedByte()? LuaValue.TRUE: LuaValue.FALSE);
|
||||
break;
|
||||
case LUA_TINT:
|
||||
values[i] = LuaInteger.valueOf(loadInt());
|
||||
values[i] = LuaInteger.valueOf( loadInt() );
|
||||
break;
|
||||
case LUA_TNUMBER:
|
||||
values[i] = loadNumber();
|
||||
@@ -331,50 +293,49 @@ public class LoadState {
|
||||
}
|
||||
}
|
||||
f.k = values;
|
||||
|
||||
|
||||
n = loadInt();
|
||||
Prototype[] protos = n > 0? new Prototype[n]: NOPROTOS;
|
||||
for (int i = 0; i < n; i++)
|
||||
Prototype[] protos = n>0? new Prototype[n]: NOPROTOS;
|
||||
for ( int i=0; i<n; i++ )
|
||||
protos[i] = loadFunction(f.source);
|
||||
f.p = protos;
|
||||
}
|
||||
|
||||
|
||||
void loadUpvalues(Prototype f) throws IOException {
|
||||
int n = loadInt();
|
||||
f.upvalues = n > 0? new Upvaldesc[n]: NOUPVALDESCS;
|
||||
for (int i = 0; i < n; i++) {
|
||||
f.upvalues = n>0? new Upvaldesc[n]: NOUPVALDESCS;
|
||||
for (int i=0; i<n; i++) {
|
||||
boolean instack = is.readByte() != 0;
|
||||
int idx = is.readByte() & 0xff;
|
||||
int idx = ((int) is.readByte()) & 0xff;
|
||||
f.upvalues[i] = new Upvaldesc(null, instack, idx);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Load the debug info for a function prototype
|
||||
*
|
||||
* @param f the function Prototype
|
||||
* @throws IOException if there is an i/o exception
|
||||
*/
|
||||
void loadDebug(Prototype f) throws IOException {
|
||||
void loadDebug( Prototype f ) throws IOException {
|
||||
f.source = loadString();
|
||||
f.lineinfo = loadIntArray();
|
||||
int n = loadInt();
|
||||
f.locvars = n > 0? new LocVars[n]: NOLOCVARS;
|
||||
for (int i = 0; i < n; i++) {
|
||||
f.locvars = n>0? new LocVars[n]: NOLOCVARS;
|
||||
for ( int i=0; i<n; i++ ) {
|
||||
LuaString varname = loadString();
|
||||
int startpc = loadInt();
|
||||
int endpc = loadInt();
|
||||
f.locvars[i] = new LocVars(varname, startpc, endpc);
|
||||
}
|
||||
|
||||
|
||||
n = loadInt();
|
||||
for (int i = 0; i < n; i++)
|
||||
for ( int i=0; i<n; i++ )
|
||||
f.upvalues[i].name = loadString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a function prototype from the input stream
|
||||
*
|
||||
* @param p name of the source
|
||||
* @return {@link Prototype} instance that was loaded
|
||||
* @throws IOException
|
||||
@@ -394,58 +355,55 @@ public class LoadState {
|
||||
loadConstants(f);
|
||||
loadUpvalues(f);
|
||||
loadDebug(f);
|
||||
|
||||
|
||||
// TODO: add check here, for debugging purposes, I believe
|
||||
// see ldebug.c
|
||||
// IF (!luaG_checkcode(f), "bad code");
|
||||
|
||||
|
||||
// this.L.pop();
|
||||
return f;
|
||||
return f;
|
||||
}
|
||||
|
||||
/**
|
||||
* Load the lua chunk header values.
|
||||
*
|
||||
* @throws IOException if an i/o exception occurs.
|
||||
*/
|
||||
public void loadHeader() throws IOException {
|
||||
luacVersion = is.readByte();
|
||||
luacFormat = is.readByte();
|
||||
luacLittleEndian = 0 != is.readByte();
|
||||
luacLittleEndian = (0 != is.readByte());
|
||||
luacSizeofInt = is.readByte();
|
||||
luacSizeofSizeT = is.readByte();
|
||||
luacSizeofInstruction = is.readByte();
|
||||
luacSizeofLuaNumber = is.readByte();
|
||||
luacNumberFormat = is.readByte();
|
||||
for (int i = 0; i < LUAC_TAIL.length; ++i)
|
||||
for (int i=0; i < LUAC_TAIL.length; ++i)
|
||||
if (is.readByte() != LUAC_TAIL[i])
|
||||
throw new LuaError("Unexpeted byte in luac tail of header, index=" + i);
|
||||
throw new LuaError("Unexpeted byte in luac tail of header, index="+i);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load input stream as a lua binary chunk if the first 4 bytes are the lua
|
||||
* binary signature.
|
||||
*
|
||||
* @param stream InputStream to read, after having read the first byte
|
||||
* already
|
||||
* Load input stream as a lua binary chunk if the first 4 bytes are the lua binary signature.
|
||||
* @param stream InputStream to read, after having read the first byte already
|
||||
* @param chunkname Name to apply to the loaded chunk
|
||||
* @return {@link Prototype} that was loaded, or null if the first 4 bytes
|
||||
* were not the lua signature.
|
||||
* @return {@link Prototype} that was loaded, or null if the first 4 bytes were not the lua signature.
|
||||
* @throws IOException if an IOException occurs
|
||||
*/
|
||||
public static Prototype undump(InputStream stream, String chunkname) throws IOException {
|
||||
// check rest of signature
|
||||
if (stream.read() != LUA_SIGNATURE[0] || stream.read() != LUA_SIGNATURE[1] || stream.read() != LUA_SIGNATURE[2]
|
||||
|| stream.read() != LUA_SIGNATURE[3])
|
||||
if ( stream.read() != LUA_SIGNATURE[0]
|
||||
|| stream.read() != LUA_SIGNATURE[1]
|
||||
|| stream.read() != LUA_SIGNATURE[2]
|
||||
|| stream.read() != LUA_SIGNATURE[3] )
|
||||
return null;
|
||||
|
||||
|
||||
// load file as a compiled chunk
|
||||
String sname = getSourceName(chunkname);
|
||||
LoadState s = new LoadState(stream, sname);
|
||||
LoadState s = new LoadState( stream, sname );
|
||||
s.loadHeader();
|
||||
|
||||
// check format
|
||||
switch (s.luacNumberFormat) {
|
||||
switch ( s.luacNumberFormat ) {
|
||||
case NUMBER_FORMAT_FLOATS_OR_DOUBLES:
|
||||
case NUMBER_FORMAT_INTS_ONLY:
|
||||
case NUMBER_FORMAT_NUM_PATCH_INT32:
|
||||
@@ -453,34 +411,33 @@ public class LoadState {
|
||||
default:
|
||||
throw new LuaError("unsupported int size");
|
||||
}
|
||||
return s.loadFunction(LuaString.valueOf(sname));
|
||||
return s.loadFunction( LuaString.valueOf(sname) );
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Construct a source name from a supplied chunk name
|
||||
*
|
||||
* @param name String name that appears in the chunk
|
||||
* @return source file name
|
||||
*/
|
||||
public static String getSourceName(String name) {
|
||||
String sname = name;
|
||||
if (name.startsWith("@") || name.startsWith("="))
|
||||
public static String getSourceName(String name) {
|
||||
String sname = name;
|
||||
if ( name.startsWith("@") || name.startsWith("=") )
|
||||
sname = name.substring(1);
|
||||
else if (name.startsWith("\033"))
|
||||
else if ( name.startsWith("\033") )
|
||||
sname = SOURCE_BINARY_STRING;
|
||||
return sname;
|
||||
}
|
||||
return sname;
|
||||
}
|
||||
|
||||
/** Private constructor for create a load state */
|
||||
private LoadState(InputStream stream, String name) {
|
||||
private LoadState( InputStream stream, String name ) {
|
||||
this.name = name;
|
||||
this.is = new DataInputStream(stream);
|
||||
this.is = new DataInputStream( stream );
|
||||
}
|
||||
|
||||
|
||||
private static final class GlobalsUndumper implements Globals.Undumper {
|
||||
@Override
|
||||
public Prototype undump(InputStream stream, String chunkname) throws IOException {
|
||||
return LoadState.undump(stream, chunkname);
|
||||
public Prototype undump(InputStream stream, String chunkname)
|
||||
throws IOException {
|
||||
return LoadState.undump(stream, chunkname);
|
||||
}
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LocVars.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LocVars.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -22,33 +22,31 @@
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Data class to hold debug information relating to local variables for a
|
||||
* {@link Prototype}
|
||||
* Data class to hold debug information relating to local variables for a {@link Prototype}
|
||||
*/
|
||||
public class LocVars {
|
||||
/** The local variable name */
|
||||
public LuaString varname;
|
||||
|
||||
/** The instruction offset when the variable comes into scope */
|
||||
|
||||
/** The instruction offset when the variable comes into scope */
|
||||
public int startpc;
|
||||
|
||||
/** The instruction offset when the variable goes out of scope */
|
||||
|
||||
/** The instruction offset when the variable goes out of scope */
|
||||
public int endpc;
|
||||
|
||||
|
||||
/**
|
||||
* Construct a LocVars instance.
|
||||
*
|
||||
* Construct a LocVars instance.
|
||||
* @param varname The local variable name
|
||||
* @param startpc The instruction offset when the variable comes into scope
|
||||
* @param endpc The instruction offset when the variable goes out of scope
|
||||
* @param endpc The instruction offset when the variable goes out of scope
|
||||
*/
|
||||
public LocVars(LuaString varname, int startpc, int endpc) {
|
||||
this.varname = varname;
|
||||
this.startpc = startpc;
|
||||
this.endpc = endpc;
|
||||
}
|
||||
|
||||
|
||||
public String tojstring() {
|
||||
return varname + " " + startpc + "-" + endpc;
|
||||
return varname+" "+startpc+"-"+endpc;
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/Lua.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Lua.class
Normal file
Binary file not shown.
375
core/src/main/java/org/luaj/vm2/Lua.java
Normal file
375
core/src/main/java/org/luaj/vm2/Lua.java
Normal file
@@ -0,0 +1,375 @@
|
||||
/*******************************************************************************
|
||||
* Copyright (c) 2009-2011 Luaj.org. All rights reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
/**
|
||||
* Constants for lua limits and opcodes.
|
||||
* <p>
|
||||
* This is a direct translation of C lua distribution header file constants
|
||||
* for bytecode creation and processing.
|
||||
*/
|
||||
public class Lua {
|
||||
/** version is supplied by ant build task */
|
||||
public static final String _VERSION = "Lua 5.3";
|
||||
|
||||
/** use return values from previous op */
|
||||
public static final int LUA_MULTRET = -1;
|
||||
|
||||
// from lopcodes.h
|
||||
|
||||
/*===========================================================================
|
||||
We assume that instructions are unsigned numbers.
|
||||
All instructions have an opcode in the first 6 bits.
|
||||
Instructions can have the following fields:
|
||||
`A' : 8 bits
|
||||
`B' : 9 bits
|
||||
`C' : 9 bits
|
||||
`Bx' : 18 bits (`B' and `C' together)
|
||||
`sBx' : signed Bx
|
||||
|
||||
A signed argument is represented in excess K; that is, the number
|
||||
value is the unsigned value minus K. K is exactly the maximum value
|
||||
for that argument (so that -max is represented by 0, and +max is
|
||||
represented by 2*max), which is half the maximum for the corresponding
|
||||
unsigned argument.
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
/* basic instruction format */
|
||||
public static final int iABC = 0;
|
||||
public static final int iABx = 1;
|
||||
public static final int iAsBx = 2;
|
||||
public static final int iAx = 3;
|
||||
|
||||
|
||||
/*
|
||||
** size and position of opcode arguments.
|
||||
*/
|
||||
public static final int SIZE_C = 9;
|
||||
public static final int SIZE_B = 9;
|
||||
public static final int SIZE_Bx = (SIZE_C + SIZE_B);
|
||||
public static final int SIZE_A = 8;
|
||||
public static final int SIZE_Ax = (SIZE_C + SIZE_B + SIZE_A);
|
||||
|
||||
public static final int SIZE_OP = 6;
|
||||
|
||||
public static final int POS_OP = 0;
|
||||
public static final int POS_A = (POS_OP + SIZE_OP);
|
||||
public static final int POS_C = (POS_A + SIZE_A);
|
||||
public static final int POS_B = (POS_C + SIZE_C);
|
||||
public static final int POS_Bx = POS_C;
|
||||
public static final int POS_Ax = POS_A;
|
||||
|
||||
public static final int MAX_OP = ((1<<SIZE_OP)-1);
|
||||
public static final int MAXARG_A = ((1<<SIZE_A)-1);
|
||||
public static final int MAXARG_B = ((1<<SIZE_B)-1);
|
||||
public static final int MAXARG_C = ((1<<SIZE_C)-1);
|
||||
public static final int MAXARG_Bx = ((1<<SIZE_Bx)-1);
|
||||
public static final int MAXARG_sBx = (MAXARG_Bx>>1); /* `sBx' is signed */
|
||||
public static final int MAXARG_Ax = ((1<<SIZE_Ax)-1);
|
||||
|
||||
public static final int MASK_OP = ((1<<SIZE_OP)-1)<<POS_OP;
|
||||
public static final int MASK_A = ((1<<SIZE_A)-1)<<POS_A;
|
||||
public static final int MASK_B = ((1<<SIZE_B)-1)<<POS_B;
|
||||
public static final int MASK_C = ((1<<SIZE_C)-1)<<POS_C;
|
||||
public static final int MASK_Bx = ((1<<SIZE_Bx)-1)<<POS_Bx;
|
||||
public static final int MASK_Ax = ((1<<SIZE_Ax)-1)<<POS_Ax;
|
||||
|
||||
public static final int MASK_NOT_OP = ~MASK_OP;
|
||||
public static final int MASK_NOT_A = ~MASK_A;
|
||||
public static final int MASK_NOT_B = ~MASK_B;
|
||||
public static final int MASK_NOT_C = ~MASK_C;
|
||||
public static final int MASK_NOT_Bx = ~MASK_Bx;
|
||||
|
||||
/*
|
||||
** the following macros help to manipulate instructions
|
||||
*/
|
||||
public static int GET_OPCODE(int i) {
|
||||
return (i >> POS_OP) & MAX_OP;
|
||||
}
|
||||
|
||||
public static int GETARG_A(int i) {
|
||||
return (i >> POS_A) & MAXARG_A;
|
||||
}
|
||||
|
||||
public static int GETARG_Ax(int i) {
|
||||
return (i >> POS_Ax) & MAXARG_Ax;
|
||||
}
|
||||
|
||||
public static int GETARG_B(int i) {
|
||||
return (i >> POS_B) & MAXARG_B;
|
||||
}
|
||||
|
||||
public static int GETARG_C(int i) {
|
||||
return (i >> POS_C) & MAXARG_C;
|
||||
}
|
||||
|
||||
public static int GETARG_Bx(int i) {
|
||||
return (i >> POS_Bx) & MAXARG_Bx;
|
||||
}
|
||||
|
||||
public static int GETARG_sBx(int i) {
|
||||
return ((i >> POS_Bx) & MAXARG_Bx) - MAXARG_sBx;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Macros to operate RK indices
|
||||
*/
|
||||
|
||||
/** this bit 1 means constant (0 means register) */
|
||||
public static final int BITRK = (1 << (SIZE_B - 1));
|
||||
|
||||
/** test whether value is a constant */
|
||||
public static boolean ISK(int x) {
|
||||
return 0 != ((x) & BITRK);
|
||||
}
|
||||
|
||||
/** gets the index of the constant */
|
||||
public static int INDEXK(int r) {
|
||||
return ((int)(r) & ~BITRK);
|
||||
}
|
||||
|
||||
public static final int MAXINDEXRK = (BITRK - 1);
|
||||
|
||||
/** code a constant index as a RK value */
|
||||
public static int RKASK(int x) {
|
||||
return ((x) | BITRK);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
** invalid register that fits in 8 bits
|
||||
*/
|
||||
public static final int NO_REG = MAXARG_A;
|
||||
|
||||
|
||||
/*
|
||||
** R(x) - register
|
||||
** Kst(x) - constant (in constant table)
|
||||
** RK(x) == if ISK(x) then Kst(INDEXK(x)) else R(x)
|
||||
*/
|
||||
|
||||
|
||||
/*
|
||||
** grep "ORDER OP" if you change these enums
|
||||
*/
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
name args description
|
||||
------------------------------------------------------------------------*/
|
||||
public static final int OP_MOVE = 0;/* A B R(A) := R(B) */
|
||||
public static final int OP_LOADK = 1;/* A Bx R(A) := Kst(Bx) */
|
||||
public static final int OP_LOADKX = 2;/* A R(A) := Kst(extra arg) */
|
||||
public static final int OP_LOADBOOL = 3;/* A B C R(A) := (Bool)B; if (C) pc++ */
|
||||
public static final int OP_LOADNIL = 4; /* A B R(A) := ... := R(A+B) := nil */
|
||||
public static final int OP_GETUPVAL = 5; /* A B R(A) := UpValue[B] */
|
||||
|
||||
public static final int OP_GETTABUP = 6; /* A B C R(A) := UpValue[B][RK(C)] */
|
||||
public static final int OP_GETTABLE = 7; /* A B C R(A) := R(B)[RK(C)] */
|
||||
|
||||
public static final int OP_SETTABUP = 8; /* A B C UpValue[A][RK(B)] := RK(C) */
|
||||
public static final int OP_SETUPVAL = 9; /* A B UpValue[B] := R(A) */
|
||||
public static final int OP_SETTABLE = 10; /* A B C R(A)[RK(B)] := RK(C) */
|
||||
|
||||
public static final int OP_NEWTABLE = 11; /* A B C R(A) := {} (size = B,C) */
|
||||
|
||||
public static final int OP_SELF = 12; /* A B C R(A+1) := R(B); R(A) := R(B)[RK(C)] */
|
||||
|
||||
public static final int OP_ADD = 13; /* A B C R(A) := RK(B) + RK(C) */
|
||||
public static final int OP_SUB = 14; /* A B C R(A) := RK(B) - RK(C) */
|
||||
public static final int OP_MUL = 15; /* A B C R(A) := RK(B) * RK(C) */
|
||||
public static final int OP_DIV = 16; /* A B C R(A) := RK(B) / RK(C) */
|
||||
public static final int OP_IDIV = 17; /* A B C R(A) := RK(B) // RK(C) */
|
||||
public static final int OP_BAND = 18; /* A B C R(A) := RK(B) & RK(C) */
|
||||
public static final int OP_BOR = 19; /* A B C R(A) := RK(B) | RK(C) */
|
||||
public static final int OP_BXOR = 20; /* A B C R(A) := RK(B) ~ RK(C) */
|
||||
public static final int OP_SHL = 21; /* A B C R(A) := RK(B) << RK(C) */
|
||||
public static final int OP_SHR = 22; /* A B C R(A) := RK(B) >> RK(C) */
|
||||
public static final int OP_MOD = 23; /* A B C R(A) := RK(B) % RK(C) */
|
||||
public static final int OP_POW = 24; /* A B C R(A) := RK(B) ^ RK(C) */
|
||||
public static final int OP_UNM = 25; /* A B R(A) := -R(B) */
|
||||
public static final int OP_BNOT = 26; /* A B R(A) := ~R(B) */
|
||||
public static final int OP_NOT = 27; /* A B R(A) := not R(B) */
|
||||
public static final int OP_LEN = 28; /* A B R(A) := length of R(B) */
|
||||
|
||||
public static final int OP_CONCAT = 29; /* A B C R(A) := R(B).. ... ..R(C) */
|
||||
|
||||
public static final int OP_JMP = 30; /* A sBx pc+=sBx; if (A) close all upvalues >= R(A - 1) */
|
||||
public static final int OP_EQ = 31; /* A B C if ((RK(B) == RK(C)) ~= A) then pc++ */
|
||||
public static final int OP_LT = 32; /* A B C if ((RK(B) < RK(C)) ~= A) then pc++ */
|
||||
public static final int OP_LE = 33; /* A B C if ((RK(B) <= RK(C)) ~= A) then pc++ */
|
||||
|
||||
public static final int OP_TEST = 34; /* A C if not (R(A) <=> C) then pc++ */
|
||||
public static final int OP_TESTSET = 35; /* A B C if (R(B) <=> C) then R(A) := R(B) else pc++ */
|
||||
|
||||
public static final int OP_CALL = 36; /* A B C R(A), ... ,R(A+C-2) := R(A)(R(A+1), ... ,R(A+B-1)) */
|
||||
public static final int OP_TAILCALL = 37; /* A B C return R(A)(R(A+1), ... ,R(A+B-1)) */
|
||||
public static final int OP_RETURN = 38; /* A B return R(A), ... ,R(A+B-2) (see note) */
|
||||
|
||||
public static final int OP_FORLOOP = 39; /* A sBx R(A)+=R(A+2);
|
||||
if R(A) <?= R(A+1) then { pc+=sBx; R(A+3)=R(A) }*/
|
||||
public static final int OP_FORPREP = 40; /* A sBx R(A)-=R(A+2); pc+=sBx */
|
||||
|
||||
public static final int OP_TFORCALL = 41; /* A C R(A+3), ... ,R(A+2+C) := R(A)(R(A+1), R(A+2)); */
|
||||
public static final int OP_TFORLOOP = 42; /* A sBx if R(A+1) ~= nil then { R(A)=R(A+1); pc += sBx } */
|
||||
public static final int OP_SETLIST = 43; /* A B C R(A)[(C-1)*FPF+i] := R(A+i), 1 <= i <= B */
|
||||
|
||||
public static final int OP_CLOSURE = 44; /* A Bx R(A) := closure(KPROTO[Bx], R(A), ... ,R(A+n)) */
|
||||
|
||||
public static final int OP_VARARG = 45; /* A B R(A), R(A+1), ..., R(A+B-1) = vararg */
|
||||
|
||||
public static final int OP_EXTRAARG = 46; /* Ax extra (larger) argument for previous opcode */
|
||||
|
||||
public static final int NUM_OPCODES = OP_EXTRAARG + 1;
|
||||
|
||||
/* pseudo-opcodes used in parsing only. */
|
||||
public static final int OP_GT = 63; // >
|
||||
public static final int OP_GE = 62; // >=
|
||||
public static final int OP_NEQ = 61; // ~=
|
||||
public static final int OP_AND = 60; // and
|
||||
public static final int OP_OR = 59; // or
|
||||
|
||||
/*===========================================================================
|
||||
Notes:
|
||||
(*) In OP_CALL, if (B == 0) then B = top. C is the number of returns - 1,
|
||||
and can be 0: OP_CALL then sets `top' to last_result+1, so
|
||||
next open instruction (OP_CALL, OP_RETURN, OP_SETLIST) may use `top'.
|
||||
|
||||
(*) In OP_VARARG, if (B == 0) then use actual number of varargs and
|
||||
set top (like in OP_CALL with C == 0).
|
||||
|
||||
(*) In OP_RETURN, if (B == 0) then return up to `top'
|
||||
|
||||
(*) In OP_SETLIST, if (B == 0) then B = `top';
|
||||
if (C == 0) then next `instruction' is real C
|
||||
|
||||
(*) For comparisons, A specifies what condition the test should accept
|
||||
(true or false).
|
||||
|
||||
(*) All `skips' (pc++) assume that next instruction is a jump
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
/*
|
||||
** masks for instruction properties. The format is:
|
||||
** bits 0-1: op mode
|
||||
** bits 2-3: C arg mode
|
||||
** bits 4-5: B arg mode
|
||||
** bit 6: instruction set register A
|
||||
** bit 7: operator is a test
|
||||
*/
|
||||
|
||||
public static final int OpArgN = 0; /* argument is not used */
|
||||
public static final int OpArgU = 1; /* argument is used */
|
||||
public static final int OpArgR = 2; /* argument is a register or a jump offset */
|
||||
public static final int OpArgK = 3; /* argument is a constant or register/constant */
|
||||
|
||||
public static final int[] luaP_opmodes = {
|
||||
/* T A B C mode opcode */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iABC), /* OP_MOVE */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgN<<2) | (iABx), /* OP_LOADK */
|
||||
(0<<7) | (1<<6) | (OpArgN<<4) | (OpArgN<<2) | (iABx), /* OP_LOADKX */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgU<<2) | (iABC), /* OP_LOADBOOL */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABC), /* OP_LOADNIL */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABC), /* OP_GETUPVAL */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgK<<2) | (iABC), /* OP_GETTABUP */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgK<<2) | (iABC), /* OP_GETTABLE */
|
||||
(0<<7) | (0<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_SETTABUP */
|
||||
(0<<7) | (0<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABC), /* OP_SETUPVAL */
|
||||
(0<<7) | (0<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_SETTABLE */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgU<<2) | (iABC), /* OP_NEWTABLE */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgK<<2) | (iABC), /* OP_SELF */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_ADD */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_SUB */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_MUL */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_DIV */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_IDIV */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_BAND */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_BOR */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_BXOR */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_SHL */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_SHR */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_MOD */
|
||||
(0<<7) | (1<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_POW */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iABC), /* OP_UNM */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iABC), /* OP_BNOT */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iABC), /* OP_NOT */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iABC), /* OP_LEN */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgR<<2) | (iABC), /* OP_CONCAT */
|
||||
(0<<7) | (0<<6) | (OpArgR<<4) | (OpArgN<<2) | (iAsBx), /* OP_JMP */
|
||||
(1<<7) | (0<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_EQ */
|
||||
(1<<7) | (0<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_LT */
|
||||
(1<<7) | (0<<6) | (OpArgK<<4) | (OpArgK<<2) | (iABC), /* OP_LE */
|
||||
(1<<7) | (0<<6) | (OpArgN<<4) | (OpArgU<<2) | (iABC), /* OP_TEST */
|
||||
(1<<7) | (1<<6) | (OpArgR<<4) | (OpArgU<<2) | (iABC), /* OP_TESTSET */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgU<<2) | (iABC), /* OP_CALL */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgU<<2) | (iABC), /* OP_TAILCALL */
|
||||
(0<<7) | (0<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABC), /* OP_RETURN */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iAsBx), /* OP_FORLOOP */
|
||||
(0<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iAsBx), /* OP_FORPREP */
|
||||
(0<<7) | (0<<6) | (OpArgN<<4) | (OpArgU<<2) | (iABC), /* OP_TFORCALL */
|
||||
(1<<7) | (1<<6) | (OpArgR<<4) | (OpArgN<<2) | (iAsBx), /* OP_TFORLOOP */
|
||||
(0<<7) | (0<<6) | (OpArgU<<4) | (OpArgU<<2) | (iABC), /* OP_SETLIST */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABx), /* OP_CLOSURE */
|
||||
(0<<7) | (1<<6) | (OpArgU<<4) | (OpArgN<<2) | (iABC), /* OP_VARARG */
|
||||
(0<<7) | (0<<6) | (OpArgU<<4) | (OpArgU<<2) | (iAx), /* OP_EXTRAARG */
|
||||
};
|
||||
|
||||
public static int getOpMode(int m) {
|
||||
return luaP_opmodes[m] & 3;
|
||||
}
|
||||
public static int getBMode(int m) {
|
||||
return (luaP_opmodes[m] >> 4) & 3;
|
||||
}
|
||||
public static int getCMode(int m) {
|
||||
return (luaP_opmodes[m] >> 2) & 3;
|
||||
}
|
||||
public static boolean testAMode(int m) {
|
||||
return 0 != (luaP_opmodes[m] & (1 << 6));
|
||||
}
|
||||
public static boolean testTMode(int m) {
|
||||
return 0 != (luaP_opmodes[m] & (1 << 7));
|
||||
}
|
||||
|
||||
/* number of list items to accumulate before a SETLIST instruction */
|
||||
public static final int LFIELDS_PER_FLUSH = 50;
|
||||
|
||||
private static final int MAXSRC = 80;
|
||||
|
||||
public static String chunkid( String source ) {
|
||||
if ( source.startsWith("=") )
|
||||
return source.substring(1);
|
||||
String end = "";
|
||||
if ( source.startsWith("@") ) {
|
||||
source = source.substring(1);
|
||||
} else {
|
||||
source = "[string \""+source;
|
||||
end = "\"]";
|
||||
}
|
||||
int n = source.length() + end.length();
|
||||
if ( n > MAXSRC )
|
||||
source = source.substring(0,MAXSRC-end.length()-3) + "...";
|
||||
return source + end;
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaBoolean.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaBoolean.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -22,18 +22,18 @@
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Extension of {@link LuaValue} which can hold a Java boolean as its value.
|
||||
* Extension of {@link LuaValue} which can hold a Java boolean as its value.
|
||||
* <p>
|
||||
* These instance are not instantiated directly by clients. Instead, there are
|
||||
* exactly twon instances of this class, {@link LuaValue#TRUE} and
|
||||
* {@link LuaValue#FALSE} representing the lua values {@code true} and
|
||||
* {@code false}. The function {@link LuaValue#valueOf(boolean)} will always
|
||||
* return one of these two values.
|
||||
* These instance are not instantiated directly by clients.
|
||||
* Instead, there are exactly twon instances of this class,
|
||||
* {@link LuaValue#TRUE} and {@link LuaValue#FALSE}
|
||||
* representing the lua values {@code true} and {@code false}.
|
||||
* The function {@link LuaValue#valueOf(boolean)} will always
|
||||
* return one of these two values.
|
||||
* <p>
|
||||
* Any {@link LuaValue} can be converted to its equivalent boolean
|
||||
* representation using {@link LuaValue#toboolean()}
|
||||
* Any {@link LuaValue} can be converted to its equivalent
|
||||
* boolean representation using {@link LuaValue#toboolean()}
|
||||
* <p>
|
||||
*
|
||||
* @see LuaValue
|
||||
* @see LuaValue#valueOf(boolean)
|
||||
* @see LuaValue#TRUE
|
||||
@@ -43,10 +43,10 @@ public final class LuaBoolean extends LuaValue {
|
||||
|
||||
/** The singleton instance representing lua {@code true} */
|
||||
static final LuaBoolean _TRUE = new LuaBoolean(true);
|
||||
|
||||
|
||||
/** The singleton instance representing lua {@code false} */
|
||||
static final LuaBoolean _FALSE = new LuaBoolean(false);
|
||||
|
||||
|
||||
/** Shared static metatable for boolean values represented in lua. */
|
||||
public static LuaValue s_metatable;
|
||||
|
||||
@@ -57,57 +57,47 @@ public final class LuaBoolean extends LuaValue {
|
||||
this.v = b;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int type() {
|
||||
return LuaValue.TBOOLEAN;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String typename() {
|
||||
return "boolean";
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isboolean() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue not() {
|
||||
return v? FALSE: LuaValue.TRUE;
|
||||
return v ? FALSE : LuaValue.TRUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the boolean value for this boolean
|
||||
*
|
||||
* @return value as a Java boolean
|
||||
*/
|
||||
public boolean booleanValue() {
|
||||
return v;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean toboolean() {
|
||||
return v;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String tojstring() {
|
||||
return v? "true": "false";
|
||||
return v ? "true" : "false";
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean optboolean(boolean defval) {
|
||||
return this.v;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean checkboolean() {
|
||||
return v;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaClosure.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaClosure.class
Normal file
Binary file not shown.
692
core/src/main/java/org/luaj/vm2/LuaClosure.java
Normal file
692
core/src/main/java/org/luaj/vm2/LuaClosure.java
Normal file
@@ -0,0 +1,692 @@
|
||||
/*******************************************************************************
|
||||
* Copyright (c) 2009 Luaj.org. All rights reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
import org.luaj.vm2.libs.DebugLib.CallFrame;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Extension of {@link LuaFunction} which executes lua bytecode.
|
||||
* <p>
|
||||
* A {@link LuaClosure} is a combination of a {@link Prototype}
|
||||
* and a {@link LuaValue} to use as an environment for execution.
|
||||
* Normally the {@link LuaValue} is a {@link Globals} in which case the environment
|
||||
* will contain standard lua libraries.
|
||||
*
|
||||
* <p>
|
||||
* There are three main ways {@link LuaClosure} instances are created:
|
||||
* <ul>
|
||||
* <li>Construct an instance using {@link #LuaClosure(Prototype, LuaValue)}</li>
|
||||
* <li>Construct it indirectly by loading a chunk via {@link Globals#load(java.io.Reader, String)}
|
||||
* <li>Execute the lua bytecode {@link Lua#OP_CLOSURE} as part of bytecode processing
|
||||
* </ul>
|
||||
* <p>
|
||||
* To construct it directly, the {@link Prototype} is typically created via a compiler such as
|
||||
* {@link org.luaj.vm2.compiler.LuaC}:
|
||||
* <pre> {@code
|
||||
* String script = "print( 'hello, world' )";
|
||||
* InputStream is = new ByteArrayInputStream(script.getBytes());
|
||||
* Prototype p = LuaC.instance.compile(is, "script");
|
||||
* LuaValue globals = JsePlatform.standardGlobals();
|
||||
* LuaClosure f = new LuaClosure(p, globals);
|
||||
* f.call();
|
||||
* }</pre>
|
||||
* <p>
|
||||
* To construct it indirectly, the {@link Globals#load(java.io.Reader, String)} method may be used:
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* LuaFunction f = globals.load(new StringReader(script), "script");
|
||||
* LuaClosure c = f.checkclosure(); // This may fail if LuaJC is installed.
|
||||
* c.call();
|
||||
* }</pre>
|
||||
* <p>
|
||||
* In this example, the "checkclosure()" may fail if direct lua-to-java-bytecode
|
||||
* compiling using LuaJC is installed, because no LuaClosure is created in that case
|
||||
* and the value returned is a {@link LuaFunction} but not a {@link LuaClosure}.
|
||||
* <p>
|
||||
* Since a {@link LuaClosure} is a {@link LuaFunction} which is a {@link LuaValue},
|
||||
* all the value operations can be used directly such as:
|
||||
* <ul>
|
||||
* <li>{@link LuaValue#call()}</li>
|
||||
* <li>{@link LuaValue#call(LuaValue)}</li>
|
||||
* <li>{@link LuaValue#invoke()}</li>
|
||||
* <li>{@link LuaValue#invoke(Varargs)}</li>
|
||||
* <li>{@link LuaValue#method(String)}</li>
|
||||
* <li>{@link LuaValue#method(String,LuaValue)}</li>
|
||||
* <li>{@link LuaValue#invokemethod(String)}</li>
|
||||
* <li>{@link LuaValue#invokemethod(String,Varargs)}</li>
|
||||
* <li> ...</li>
|
||||
* </ul>
|
||||
* @see LuaValue
|
||||
* @see LuaFunction
|
||||
* @see LuaValue#isclosure()
|
||||
* @see LuaValue#checkclosure()
|
||||
* @see LuaValue#optclosure(LuaClosure)
|
||||
* @see LoadState
|
||||
* @see Globals#compiler
|
||||
*/
|
||||
public class LuaClosure extends LuaFunction {
|
||||
private static final UpValue[] NOUPVALUES = new UpValue[0];
|
||||
|
||||
public final Prototype p;
|
||||
|
||||
public UpValue[] upValues;
|
||||
|
||||
final Globals globals;
|
||||
|
||||
/** Create a closure around a Prototype with a specific environment.
|
||||
* If the prototype has upvalues, the environment will be written into the first upvalue.
|
||||
* @param p the Prototype to construct this Closure for.
|
||||
* @param env the environment to associate with the closure.
|
||||
*/
|
||||
public LuaClosure(Prototype p, LuaValue env) {
|
||||
this.p = p;
|
||||
this.initupvalue1(env);
|
||||
globals = env instanceof Globals? (Globals) env: null;
|
||||
}
|
||||
|
||||
public void initupvalue1(LuaValue env) {
|
||||
if (p.upvalues == null || p.upvalues.length == 0)
|
||||
this.upValues = NOUPVALUES;
|
||||
else {
|
||||
this.upValues = new UpValue[p.upvalues.length];
|
||||
this.upValues[0] = new UpValue(new LuaValue[] {env}, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public boolean isclosure() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public LuaClosure optclosure(LuaClosure defval) {
|
||||
return this;
|
||||
}
|
||||
|
||||
public LuaClosure checkclosure() {
|
||||
return this;
|
||||
}
|
||||
|
||||
public String tojstring() {
|
||||
return "function: " + p.toString();
|
||||
}
|
||||
|
||||
|
||||
private List<LuaValue[]> stackPool = new ArrayList<>();
|
||||
private LuaValue[] getNewStack() {
|
||||
if (stackPool.isEmpty()) {
|
||||
return getNewStackRaw();
|
||||
} else {
|
||||
return stackPool.remove(stackPool.size() - 1);
|
||||
}
|
||||
}
|
||||
|
||||
private LuaValue[] getNewStackRaw() {
|
||||
int max = p.maxstacksize;
|
||||
LuaValue[] stack = new LuaValue[max];
|
||||
System.arraycopy(NILS, 0, stack, 0, max);
|
||||
return stack;
|
||||
}
|
||||
|
||||
private void releaseStack(LuaValue[] stack) {
|
||||
System.arraycopy(NILS, 0, stack, 0, stack.length);
|
||||
stackPool.add(stack);
|
||||
}
|
||||
|
||||
public final LuaValue call() {
|
||||
LuaValue[] stack = getNewStack();
|
||||
LuaValue result = execute(stack,NONE).arg1();
|
||||
releaseStack(stack);
|
||||
return result;
|
||||
}
|
||||
|
||||
public final LuaValue call(LuaValue arg) {
|
||||
LuaValue[] stack = getNewStack();
|
||||
LuaValue result;
|
||||
switch ( p.numparams ) {
|
||||
default:
|
||||
stack[0]=arg;
|
||||
result = execute(stack,NONE).arg1();
|
||||
break;
|
||||
case 0:
|
||||
result = execute(stack,arg).arg1();
|
||||
break;
|
||||
}
|
||||
releaseStack(stack);
|
||||
return result;
|
||||
}
|
||||
|
||||
public final LuaValue call(LuaValue arg1, LuaValue arg2) {
|
||||
LuaValue[] stack = getNewStack();
|
||||
LuaValue result;
|
||||
switch ( p.numparams ) {
|
||||
default:
|
||||
stack[0]=arg1;
|
||||
stack[1]=arg2;
|
||||
result = execute(stack,NONE).arg1();
|
||||
break;
|
||||
case 1:
|
||||
stack[0]=arg1;
|
||||
result = execute(stack,arg2).arg1();
|
||||
break;
|
||||
case 0:
|
||||
result = execute(stack,p.is_vararg!=0 ? varargsOf(arg1,arg2) : NONE).arg1();
|
||||
break;
|
||||
}
|
||||
releaseStack(stack);
|
||||
return result;
|
||||
}
|
||||
|
||||
public final LuaValue call(LuaValue arg1, LuaValue arg2, LuaValue arg3) {
|
||||
LuaValue[] stack = getNewStack();
|
||||
LuaValue result;
|
||||
switch ( p.numparams ) {
|
||||
default:
|
||||
stack[0]=arg1;
|
||||
stack[1]=arg2;
|
||||
stack[2]=arg3;
|
||||
result = execute(stack,NONE).arg1();
|
||||
break;
|
||||
case 2:
|
||||
stack[0]=arg1;
|
||||
stack[1]=arg2;
|
||||
result = execute(stack,arg3).arg1();
|
||||
break;
|
||||
case 1:
|
||||
stack[0]=arg1;
|
||||
result = execute(stack,p.is_vararg!=0 ? varargsOf(arg2,arg3) : NONE).arg1();
|
||||
break;
|
||||
case 0:
|
||||
result = execute(stack,p.is_vararg!=0 ? varargsOf(arg1,arg2,arg3) : NONE).arg1();
|
||||
break;
|
||||
}
|
||||
releaseStack(stack);
|
||||
return result;
|
||||
}
|
||||
|
||||
public final Varargs invoke(Varargs varargs) {
|
||||
return onInvoke(varargs).eval();
|
||||
}
|
||||
|
||||
public final Varargs onInvoke(Varargs varargs) {
|
||||
LuaValue[] stack = getNewStack();
|
||||
for ( int i=0; i<p.numparams; i++ )
|
||||
stack[i] = varargs.arg(i+1);
|
||||
Varargs result = execute(stack,p.is_vararg!=0 ? varargs.subargs(p.numparams+1) : NONE);
|
||||
if (result instanceof LuaValue) {
|
||||
releaseStack(stack);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
protected Varargs execute( LuaValue[] stack, Varargs varargs ) {
|
||||
// loop through instructions
|
||||
int i,a,b,c,pc=0,top=0;
|
||||
LuaValue o;
|
||||
Varargs v = NONE;
|
||||
int[] code = p.code;
|
||||
LuaValue[] k = p.k;
|
||||
|
||||
// upvalues are only possible when closures create closures
|
||||
// TODO: use linked list.
|
||||
UpValue[] openups = p.p.length>0? new UpValue[stack.length]: null;
|
||||
|
||||
// allow for debug hooks
|
||||
if (globals != null && globals.debuglib != null)
|
||||
globals.debuglib.onCall( this, varargs, stack );
|
||||
|
||||
// process instructions
|
||||
try {
|
||||
for (; true; ++pc) {
|
||||
if (Thread.currentThread().isInterrupted()) {
|
||||
throw new LuaError("interrupted");
|
||||
}
|
||||
if (globals != null && globals.debuglib != null)
|
||||
globals.debuglib.onInstruction( pc, v, top );
|
||||
|
||||
// pull out instruction
|
||||
i = code[pc];
|
||||
a = ((i>>6) & 0xff);
|
||||
|
||||
// process the op code
|
||||
switch ( i & 0x3f ) {
|
||||
|
||||
case Lua.OP_MOVE:/* A B R(A):= R(B) */
|
||||
stack[a] = stack[i>>>23];
|
||||
continue;
|
||||
|
||||
case Lua.OP_LOADK:/* A Bx R(A):= Kst(Bx) */
|
||||
stack[a] = k[i>>>14];
|
||||
continue;
|
||||
|
||||
case Lua.OP_LOADKX:/* A R(A) := Kst(extra arg) */
|
||||
++pc;
|
||||
i = code[pc];
|
||||
if ((i & 0x3f) != Lua.OP_EXTRAARG) {
|
||||
int op = i & 0x3f;
|
||||
throw new LuaError("OP_EXTRAARG expected after OP_LOADKX, got " +
|
||||
(op < Print.OPNAMES.length - 1 ? Print.OPNAMES[op] : "UNKNOWN_OP_" + op));
|
||||
}
|
||||
stack[a] = k[i>>>6];
|
||||
continue;
|
||||
|
||||
case Lua.OP_LOADBOOL:/* A B C R(A):= (Bool)B: if (C) pc++ */
|
||||
stack[a] = (i>>>23!=0)? LuaValue.TRUE: LuaValue.FALSE;
|
||||
if ((i&(0x1ff<<14)) != 0)
|
||||
++pc; /* skip next instruction (if C) */
|
||||
continue;
|
||||
|
||||
case Lua.OP_LOADNIL: /* A B R(A):= ...:= R(A+B):= nil */
|
||||
for ( b=i>>>23; b-->=0; )
|
||||
stack[a++] = LuaValue.NIL;
|
||||
continue;
|
||||
|
||||
case Lua.OP_GETUPVAL: /* A B R(A):= UpValue[B] */
|
||||
stack[a] = upValues[i>>>23].getValue();
|
||||
continue;
|
||||
|
||||
case Lua.OP_GETTABUP: /* A B C R(A) := UpValue[B][RK(C)] */
|
||||
stack[a] = upValues[i>>>23].getValue().get((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_GETTABLE: /* A B C R(A):= R(B)[RK(C)] */
|
||||
stack[a] = stack[i>>>23].get((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SETTABUP: /* A B C UpValue[A][RK(B)] := RK(C) */
|
||||
upValues[a].getValue().set(((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]), (c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SETUPVAL: /* A B UpValue[B]:= R(A) */
|
||||
upValues[i>>>23].setValue(stack[a]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SETTABLE: /* A B C R(A)[RK(B)]:= RK(C) */
|
||||
stack[a].set(((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]), (c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_NEWTABLE: /* A B C R(A):= {} (size = B,C) */
|
||||
stack[a] = new LuaTable(i>>>23,(i>>14)&0x1ff);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SELF: /* A B C R(A+1):= R(B): R(A):= R(B)[RK(C)] */
|
||||
stack[a+1] = (o = stack[i>>>23]);
|
||||
stack[a] = o.get((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_ADD: /* A B C R(A):= RK(B) + RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).add((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SUB: /* A B C R(A):= RK(B) - RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).sub((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_MUL: /* A B C R(A):= RK(B) * RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).mul((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_DIV: /* A B C R(A):= RK(B) / RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).div((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_IDIV: /* A B C R(A):= RK(B) // RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).idiv((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_BAND: /* A B C R(A):= RK(B) & RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).band((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_BOR: /* A B C R(A):= RK(B) | RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).bor((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_BXOR: /* A B C R(A):= RK(B) ~ RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).bxor((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SHL: /* A B C R(A):= RK(B) << RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).shl((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_SHR: /* A B C R(A):= RK(B) >> RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).shr((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_MOD: /* A B C R(A):= RK(B) % RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).mod((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_POW: /* A B C R(A):= RK(B) ^ RK(C) */
|
||||
stack[a] = ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).pow((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]);
|
||||
continue;
|
||||
|
||||
case Lua.OP_UNM: /* A B R(A):= -R(B) */
|
||||
stack[a] = stack[i>>>23].neg();
|
||||
continue;
|
||||
|
||||
case Lua.OP_BNOT: /* A B R(A):= ~R(B) */
|
||||
stack[a] = stack[i>>>23].bnot();
|
||||
continue;
|
||||
|
||||
case Lua.OP_NOT: /* A B R(A):= not R(B) */
|
||||
stack[a] = stack[i>>>23].not();
|
||||
continue;
|
||||
|
||||
case Lua.OP_LEN: /* A B R(A):= length of R(B) */
|
||||
stack[a] = stack[i>>>23].len();
|
||||
continue;
|
||||
|
||||
case Lua.OP_CONCAT: /* A B C R(A):= R(B).. ... ..R(C) */
|
||||
b = i>>>23;
|
||||
c = (i>>14)&0x1ff;
|
||||
{
|
||||
if ( c > b+1 ) {
|
||||
Buffer sb = stack[c].buffer();
|
||||
while ( --c>=b )
|
||||
sb.concatTo(stack[c]);
|
||||
stack[a] = sb.value();
|
||||
} else {
|
||||
stack[a] = stack[c-1].concat(stack[c]);
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_JMP: /* A sBx pc+=sBx; if (A) close all upvalues >= R(A - 1) */
|
||||
pc += (i>>>14)-0x1ffff;
|
||||
if (a > 0) {
|
||||
for (--a, b = openups.length; --b>=0; )
|
||||
if (openups[b] != null && openups[b].index >= a) {
|
||||
openups[b].close();
|
||||
openups[b] = null;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_EQ: /* A B C if ((RK(B) == RK(C)) ~= A) then pc++ */
|
||||
if ( ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).eq_b((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]) != (a!=0) )
|
||||
++pc;
|
||||
continue;
|
||||
|
||||
case Lua.OP_LT: /* A B C if ((RK(B) < RK(C)) ~= A) then pc++ */
|
||||
if ( ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).lt_b((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]) != (a!=0) )
|
||||
++pc;
|
||||
continue;
|
||||
|
||||
case Lua.OP_LE: /* A B C if ((RK(B) <= RK(C)) ~= A) then pc++ */
|
||||
if ( ((b=i>>>23)>0xff? k[b&0x0ff]: stack[b]).lteq_b((c=(i>>14)&0x1ff)>0xff? k[c&0x0ff]: stack[c]) != (a!=0) )
|
||||
++pc;
|
||||
continue;
|
||||
|
||||
case Lua.OP_TEST: /* A C if not (R(A) <=> C) then pc++ */
|
||||
if ( stack[a].toboolean() != ((i&(0x1ff<<14))!=0) )
|
||||
++pc;
|
||||
continue;
|
||||
|
||||
case Lua.OP_TESTSET: /* A B C if (R(B) <=> C) then R(A):= R(B) else pc++ */
|
||||
/* note: doc appears to be reversed */
|
||||
if ( (o=stack[i>>>23]).toboolean() != ((i&(0x1ff<<14))!=0) )
|
||||
++pc;
|
||||
else
|
||||
stack[a] = o; // TODO: should be sBx?
|
||||
continue;
|
||||
|
||||
case Lua.OP_CALL: /* A B C R(A), ... ,R(A+C-2):= R(A)(R(A+1), ... ,R(A+B-1)) */
|
||||
switch ( i & (Lua.MASK_B | Lua.MASK_C) ) {
|
||||
case (1<<Lua.POS_B) | (0<<Lua.POS_C): v=stack[a].invoke(NONE); top=a+v.narg(); continue;
|
||||
case (2<<Lua.POS_B) | (0<<Lua.POS_C): v=stack[a].invoke(stack[a+1]); top=a+v.narg(); continue;
|
||||
case (1<<Lua.POS_B) | (1<<Lua.POS_C): stack[a].call(); continue;
|
||||
case (2<<Lua.POS_B) | (1<<Lua.POS_C): stack[a].call(stack[a+1]); continue;
|
||||
case (3<<Lua.POS_B) | (1<<Lua.POS_C): stack[a].call(stack[a+1],stack[a+2]); continue;
|
||||
case (4<<Lua.POS_B) | (1<<Lua.POS_C): stack[a].call(stack[a+1],stack[a+2],stack[a+3]); continue;
|
||||
case (1<<Lua.POS_B) | (2<<Lua.POS_C): stack[a] = stack[a].call(); continue;
|
||||
case (2<<Lua.POS_B) | (2<<Lua.POS_C): stack[a] = stack[a].call(stack[a+1]); continue;
|
||||
case (3<<Lua.POS_B) | (2<<Lua.POS_C): stack[a] = stack[a].call(stack[a+1],stack[a+2]); continue;
|
||||
case (4<<Lua.POS_B) | (2<<Lua.POS_C): stack[a] = stack[a].call(stack[a+1],stack[a+2],stack[a+3]); continue;
|
||||
default:
|
||||
b = i>>>23;
|
||||
c = (i>>14)&0x1ff;
|
||||
v = stack[a].invoke(b>0?
|
||||
varargsOf(stack, a+1, b-1): // exact arg count
|
||||
varargsOf(stack, a+1, top-v.narg()-(a+1), v)); // from prev top
|
||||
if ( c > 0 ) {
|
||||
v.copyto(stack, a, c-1);
|
||||
v = NONE;
|
||||
} else {
|
||||
top = a + v.narg();
|
||||
v = v.dealias();
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
case Lua.OP_TAILCALL: /* A B C return R(A)(R(A+1), ... ,R(A+B-1)) */
|
||||
switch ( i & Lua.MASK_B ) {
|
||||
case (1<<Lua.POS_B): return new TailcallVarargs(stack[a], NONE);
|
||||
case (2<<Lua.POS_B): return new TailcallVarargs(stack[a], stack[a+1]);
|
||||
case (3<<Lua.POS_B): return new TailcallVarargs(stack[a], varargsOf(stack[a+1],stack[a+2]));
|
||||
case (4<<Lua.POS_B): return new TailcallVarargs(stack[a], varargsOf(stack[a+1],stack[a+2],stack[a+3]));
|
||||
default:
|
||||
b = i>>>23;
|
||||
v = b>0?
|
||||
varargsOf(stack,a+1,b-1): // exact arg count
|
||||
varargsOf(stack, a+1, top-v.narg()-(a+1), v); // from prev top
|
||||
return new TailcallVarargs( stack[a], v );
|
||||
}
|
||||
|
||||
case Lua.OP_RETURN: /* A B return R(A), ... ,R(A+B-2) (see note) */
|
||||
b = i>>>23;
|
||||
switch ( b ) {
|
||||
case 0: return varargsOf(stack, a, top-v.narg()-a, v);
|
||||
case 1: return NONE;
|
||||
case 2: return stack[a];
|
||||
default:
|
||||
return varargsOf(stack, a, b-1);
|
||||
}
|
||||
|
||||
case Lua.OP_FORLOOP: /* A sBx R(A)+=R(A+2): if R(A) <?= R(A+1) then { pc+=sBx: R(A+3)=R(A) }*/
|
||||
{
|
||||
LuaValue limit = stack[a + 1];
|
||||
LuaValue step = stack[a + 2];
|
||||
LuaValue idx = stack[a].add(step);
|
||||
if (step.gt_b(0)? idx.lteq_b(limit): idx.gteq_b(limit)) {
|
||||
stack[a] = idx;
|
||||
stack[a + 3] = idx;
|
||||
pc += (i>>>14)-0x1ffff;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_FORPREP: /* A sBx R(A)-=R(A+2): pc+=sBx */
|
||||
{
|
||||
LuaValue init = stack[a].checknumber("'for' initial value must be a number");
|
||||
LuaValue limit = stack[a + 1].checknumber("'for' limit must be a number");
|
||||
LuaValue step = stack[a + 2].checknumber("'for' step must be a number");
|
||||
stack[a] = init.sub(step);
|
||||
stack[a + 1] = limit;
|
||||
stack[a + 2] = step;
|
||||
pc += (i>>>14)-0x1ffff;
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_TFORCALL: /* A C R(A+3), ... ,R(A+2+C) := R(A)(R(A+1), R(A+2)); */
|
||||
v = stack[a].invoke(varargsOf(stack[a+1],stack[a+2]));
|
||||
c = (i>>14) & 0x1ff;
|
||||
while (--c >= 0)
|
||||
stack[a+3+c] = v.arg(c+1);
|
||||
v = NONE;
|
||||
continue;
|
||||
|
||||
case Lua.OP_TFORLOOP: /* A sBx if R(A+1) ~= nil then { R(A)=R(A+1); pc += sBx */
|
||||
if (!stack[a+1].isnil()) { /* continue loop? */
|
||||
stack[a] = stack[a+1]; /* save control varible. */
|
||||
pc += (i>>>14)-0x1ffff;
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_SETLIST: /* A B C R(A)[(C-1)*FPF+i]:= R(A+i), 1 <= i <= B */
|
||||
{
|
||||
if ( (c=(i>>14)&0x1ff) == 0 )
|
||||
c = code[++pc];
|
||||
int offset = (c-1) * Lua.LFIELDS_PER_FLUSH;
|
||||
o = stack[a];
|
||||
if ( (b=i>>>23) == 0 ) {
|
||||
b = top - a - 1;
|
||||
int m = b - v.narg();
|
||||
int j=1;
|
||||
for ( ;j<=m; j++ )
|
||||
o.set(offset+j, stack[a + j]);
|
||||
for ( ;j<=b; j++ )
|
||||
o.set(offset+j, v.arg(j-m));
|
||||
} else {
|
||||
o.presize( offset + b );
|
||||
for (int j=1; j<=b; j++)
|
||||
o.set(offset+j, stack[a + j]);
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_CLOSURE: /* A Bx R(A):= closure(KPROTO[Bx]) */
|
||||
{
|
||||
Prototype newp = p.p[i>>>14];
|
||||
LuaClosure ncl = new LuaClosure(newp, globals);
|
||||
Upvaldesc[] uv = newp.upvalues;
|
||||
for ( int j=0, nup=uv.length; j<nup; ++j ) {
|
||||
if (uv[j].instack) /* upvalue refes to local variable? */
|
||||
ncl.upValues[j] = findupval(stack, uv[j].idx, openups);
|
||||
else /* get upvalue from enclosing function */
|
||||
ncl.upValues[j] = upValues[uv[j].idx];
|
||||
}
|
||||
stack[a] = ncl;
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_VARARG: /* A B R(A), R(A+1), ..., R(A+B-1) = vararg */
|
||||
b = i>>>23;
|
||||
if ( b == 0 ) {
|
||||
top = a + (b = varargs.narg());
|
||||
v = varargs;
|
||||
} else {
|
||||
for ( int j=1; j<b; ++j )
|
||||
stack[a+j-1] = varargs.arg(j);
|
||||
}
|
||||
continue;
|
||||
|
||||
case Lua.OP_EXTRAARG:
|
||||
throw new java.lang.IllegalArgumentException("Uexecutable opcode: OP_EXTRAARG");
|
||||
|
||||
default:
|
||||
throw new java.lang.IllegalArgumentException("Illegal opcode: " + (i & 0x3f));
|
||||
}
|
||||
}
|
||||
} catch ( LuaError le ) {
|
||||
if (le.traceback == null)
|
||||
processErrorHooks(le, p, pc);
|
||||
throw le;
|
||||
} catch ( Exception e ) {
|
||||
LuaError le = new LuaError(e);
|
||||
processErrorHooks(le, p, pc);
|
||||
throw le;
|
||||
} finally {
|
||||
if ( openups != null )
|
||||
for ( int u=openups.length; --u>=0; )
|
||||
if ( openups[u] != null )
|
||||
openups[u].close();
|
||||
if (globals != null && globals.debuglib != null)
|
||||
globals.debuglib.onReturn();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Run the error hook if there is one
|
||||
* @param msg the message to use in error hook processing.
|
||||
* */
|
||||
LuaValue errorHook(LuaValue msgobj, String msg, int level) {
|
||||
if (globals == null ) return LuaValue.valueOf(msg);
|
||||
final LuaThread r = globals.running;
|
||||
if (r.errorfunc == null)
|
||||
return LuaValue.valueOf(globals.debuglib != null?
|
||||
msg + "\n" + globals.debuglib.traceback(level):
|
||||
msg);
|
||||
final LuaValue e = r.errorfunc;
|
||||
r.errorfunc = null;
|
||||
try {
|
||||
return e.call(msgobj != null ? msgobj : LuaValue.NIL);
|
||||
} catch ( Throwable t ) {
|
||||
return LuaValue.valueOf("error in error handling");
|
||||
} finally {
|
||||
r.errorfunc = e;
|
||||
}
|
||||
}
|
||||
|
||||
private void processErrorHooks(LuaError le, Prototype p, int pc) {
|
||||
String file = "?";
|
||||
int line = -1;
|
||||
{
|
||||
CallFrame frame = null;
|
||||
if (globals != null && globals.debuglib != null) {
|
||||
frame = globals.debuglib.getCallFrame(le.level);
|
||||
if (frame != null) {
|
||||
String src = frame.shortsource();
|
||||
file = src != null ? src : "?";
|
||||
line = frame.currentline();
|
||||
}
|
||||
}
|
||||
if (frame == null) {
|
||||
file = p.source != null? p.source.tojstring(): "?";
|
||||
line = p.lineinfo != null && pc >= 0 && pc < p.lineinfo.length ? p.lineinfo[pc] : -1;
|
||||
}
|
||||
}
|
||||
le.fileline = file + ":" + line;
|
||||
LuaValue error = errorHook(le.getMessageObject(), le.getMessage(), le.level);
|
||||
le.setMessageObject(error);
|
||||
le.traceback = error != null ? error.tojstring() : null;
|
||||
}
|
||||
|
||||
private UpValue findupval(LuaValue[] stack, short idx, UpValue[] openups) {
|
||||
final int n = openups.length;
|
||||
for (int i = 0; i < n; ++i)
|
||||
if (openups[i] != null && openups[i].index == idx)
|
||||
return openups[i];
|
||||
for (int i = 0; i < n; ++i)
|
||||
if (openups[i] == null)
|
||||
return openups[i] = new UpValue(stack, idx);
|
||||
error("No space for upvalue");
|
||||
return null;
|
||||
}
|
||||
|
||||
protected LuaValue getUpvalue(int i) {
|
||||
return upValues[i].getValue();
|
||||
}
|
||||
|
||||
protected void setUpvalue(int i, LuaValue v) {
|
||||
upValues[i].setValue(v);
|
||||
}
|
||||
|
||||
public String name() {
|
||||
return "<"+p.shortsource()+":"+p.linedefined+">";
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaDouble.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaDouble.class
Normal file
Binary file not shown.
@@ -21,8 +21,7 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
import org.luaj.vm2.compat.JavaCompat;
|
||||
import org.luaj.vm2.lib.MathLib;
|
||||
import org.luaj.vm2.libs.MathLib;
|
||||
|
||||
/**
|
||||
* Extension of {@link LuaNumber} which can hold a Java double as its value.
|
||||
@@ -34,9 +33,9 @@ import org.luaj.vm2.lib.MathLib;
|
||||
* <p>
|
||||
* Almost all API's implemented in LuaDouble are defined and documented in {@link LuaValue}.
|
||||
* <p>
|
||||
* However the constants {@link #NAN}, {@link #NEGNAN}, {@link #POSINF}, {@link #NEGINF},
|
||||
* {@link #JSTR_NAN}, {@link #JSTR_NEGNAN}, {@link #JSTR_POSINF}, and {@link #JSTR_NEGINF} may be useful
|
||||
* when dealing with Nan or Infinite values.
|
||||
* However the constants {@link #NAN}, {@link #POSINF}, {@link #NEGINF},
|
||||
* {@link #JSTR_NAN}, {@link #JSTR_POSINF}, and {@link #JSTR_NEGINF} may be useful
|
||||
* when dealing with Nan or Infinite values.
|
||||
* <p>
|
||||
* LuaDouble also defines functions for handling the unique math rules of lua devision and modulo in
|
||||
* <ul>
|
||||
@@ -56,10 +55,7 @@ public class LuaDouble extends LuaNumber {
|
||||
|
||||
/** Constant LuaDouble representing NaN (not a number) */
|
||||
public static final LuaDouble NAN = new LuaDouble( Double.NaN );
|
||||
|
||||
/** Constant LuaDouble representing negative NaN (not a number) */
|
||||
public static final LuaDouble NEGNAN = new LuaDouble( -Double.NaN );
|
||||
|
||||
|
||||
/** Constant LuaDouble representing positive infinity */
|
||||
public static final LuaDouble POSINF = new LuaDouble( Double.POSITIVE_INFINITY );
|
||||
|
||||
@@ -68,10 +64,7 @@ public class LuaDouble extends LuaNumber {
|
||||
|
||||
/** Constant String representation for NaN (not a number), "nan" */
|
||||
public static final String JSTR_NAN = "nan";
|
||||
|
||||
/** Constant String representation for negative NaN (not a number), "-nan" */
|
||||
public static final String JSTR_NEGNAN = "-nan";
|
||||
|
||||
|
||||
/** Constant String representation for positive infinity, "inf" */
|
||||
public static final String JSTR_POSINF = "inf";
|
||||
|
||||
@@ -82,8 +75,13 @@ public class LuaDouble extends LuaNumber {
|
||||
final double v;
|
||||
|
||||
public static LuaNumber valueOf(double d) {
|
||||
int id = (int) d;
|
||||
return d==id? (LuaNumber) LuaInteger.valueOf(id): (LuaNumber) new LuaDouble(d);
|
||||
if (!Double.isNaN(d) && !Double.isInfinite(d) && d >= Long.MIN_VALUE && d <= Long.MAX_VALUE) {
|
||||
long ld = (long) d;
|
||||
if (d == ld) {
|
||||
return LuaInteger.valueOf(ld);
|
||||
}
|
||||
}
|
||||
return new LuaDouble(d);
|
||||
}
|
||||
|
||||
/** Don't allow ints to be boxed by DoubleValues */
|
||||
@@ -110,13 +108,14 @@ public class LuaDouble extends LuaNumber {
|
||||
|
||||
public double optdouble(double defval) { return v; }
|
||||
public int optint(int defval) { return (int) (long) v; }
|
||||
public LuaInteger optinteger(LuaInteger defval) { return LuaInteger.valueOf((int) (long)v); }
|
||||
public LuaInteger optinteger(LuaInteger defval) { return islong()? LuaInteger.valueOf((long) v): defval; }
|
||||
public long optlong(long defval) { return (long) v; }
|
||||
|
||||
public LuaInteger checkinteger() { return LuaInteger.valueOf( (int) (long) v ); }
|
||||
public LuaInteger checkinteger() { if (!islong()) argerror("integer"); return LuaInteger.valueOf((long) v); }
|
||||
|
||||
// unary operators
|
||||
public LuaValue neg() { return valueOf(-v); }
|
||||
public LuaValue bnot() { if (!islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(~((long) v)); }
|
||||
|
||||
// object equality, used for key comparison
|
||||
public boolean equals(Object o) { return o instanceof LuaDouble? ((LuaDouble)o).v == v: false; }
|
||||
@@ -129,6 +128,7 @@ public class LuaDouble extends LuaNumber {
|
||||
public boolean raweq( LuaValue val ) { return val.raweq(v); }
|
||||
public boolean raweq( double val ) { return v == val; }
|
||||
public boolean raweq( int val ) { return v == val; }
|
||||
public boolean raweq( long val ) { return v == val; }
|
||||
|
||||
// basic binary arithmetic
|
||||
public LuaValue add( LuaValue rhs ) { return rhs.add(v); }
|
||||
@@ -146,9 +146,18 @@ public class LuaDouble extends LuaNumber {
|
||||
public LuaValue powWith( double lhs ) { return MathLib.dpow(lhs,v); }
|
||||
public LuaValue powWith( int lhs ) { return MathLib.dpow(lhs,v); }
|
||||
public LuaValue div( LuaValue rhs ) { return rhs.divInto(v); }
|
||||
public LuaValue idiv( LuaValue rhs ) { return rhs.idivInto(v); }
|
||||
public LuaValue div( double rhs ) { return LuaDouble.ddiv(v,rhs); }
|
||||
public LuaValue div( int rhs ) { return LuaDouble.ddiv(v,rhs); }
|
||||
public LuaValue divInto( double lhs ) { return LuaDouble.ddiv(lhs,v); }
|
||||
public LuaValue idiv( double rhs ) { return LuaDouble.didiv(v,rhs); }
|
||||
public LuaValue idiv( int rhs ) { return LuaDouble.didiv(v,rhs); }
|
||||
public LuaValue idivInto( double lhs ) { return LuaDouble.didiv(lhs,v); }
|
||||
public LuaValue band( LuaValue rhs ) { if (!islong()) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.band(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) v) & n.tolong()); }
|
||||
public LuaValue bor( LuaValue rhs ) { if (!islong()) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bor(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) v) | n.tolong()); }
|
||||
public LuaValue bxor( LuaValue rhs ) { if (!islong()) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bxor(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) v) ^ n.tolong()); }
|
||||
public LuaValue shl( LuaValue rhs ) { if (!islong()) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shl(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(LuaInteger.luaShiftLeft((long) v, n.tolong())); }
|
||||
public LuaValue shr( LuaValue rhs ) { if (!islong()) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shr(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(LuaInteger.luaShiftRight((long) v, n.tolong())); }
|
||||
public LuaValue mod( LuaValue rhs ) { return rhs.modFrom(v); }
|
||||
public LuaValue mod( double rhs ) { return LuaDouble.dmod(v,rhs); }
|
||||
public LuaValue mod( int rhs ) { return LuaDouble.dmod(v,rhs); }
|
||||
@@ -165,6 +174,10 @@ public class LuaDouble extends LuaNumber {
|
||||
public static LuaValue ddiv(double lhs, double rhs) {
|
||||
return rhs!=0? valueOf( lhs / rhs ): lhs>0? POSINF: lhs==0? NAN: NEGINF;
|
||||
}
|
||||
|
||||
public static LuaValue didiv(double lhs, double rhs) {
|
||||
return valueOf(Math.floor(ddiv_d(lhs, rhs)));
|
||||
}
|
||||
|
||||
/** Divide two double numbers according to lua math, and return a double result.
|
||||
* @param lhs Left-hand-side of the division.
|
||||
@@ -242,14 +255,18 @@ public class LuaDouble extends LuaNumber {
|
||||
public int strcmp( LuaString rhs ) { typerror("attempt to compare number with string"); return 0; }
|
||||
|
||||
public String tojstring() {
|
||||
if ( v == 0.0 ) // never occurs on J2ME
|
||||
return (JavaCompat.INSTANCE.doubleToRawLongBits(v)<0? "-0": "0");
|
||||
/*
|
||||
if ( v == 0.0 ) { // never occurs in J2me
|
||||
long bits = Double.doubleToLongBits( v );
|
||||
return ( bits >> 63 == 0 ) ? "0" : "-0";
|
||||
}
|
||||
*/
|
||||
long l = (long) v;
|
||||
if ( l == v )
|
||||
return Long.toString(l);
|
||||
if ( Double.isNaN(v) )
|
||||
return (JavaCompat.INSTANCE.doubleToRawLongBits(v)<0? JSTR_NEGNAN: JSTR_NAN);
|
||||
if ( Double.isInfinite(v) )
|
||||
return JSTR_NAN;
|
||||
if ( Double.isInfinite(v) )
|
||||
return (v<0? JSTR_NEGINF: JSTR_POSINF);
|
||||
return Float.toString((float)v);
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaError.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaError.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,40 +21,39 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
/**
|
||||
* RuntimeException that is thrown and caught in response to a lua error.
|
||||
* RuntimeException that is thrown and caught in response to a lua error.
|
||||
* <p>
|
||||
* {@link LuaError} is used wherever a lua call to {@code error()} would be used
|
||||
* within a script.
|
||||
* {@link LuaError} is used wherever a lua call to {@code error()}
|
||||
* would be used within a script.
|
||||
* <p>
|
||||
* Since it is an unchecked exception inheriting from {@link RuntimeException},
|
||||
* Java method signatures do notdeclare this exception, althoug it can be thrown
|
||||
* on almost any luaj Java operation. This is analagous to the fact that any lua
|
||||
* script can throw a lua error at any time.
|
||||
* <p>
|
||||
* The LuaError may be constructed with a message object, in which case the
|
||||
* message is the string representation of that object. getMessageObject will
|
||||
* get the object supplied at construct time, or a LuaString containing the
|
||||
* message of an object was not supplied.
|
||||
* Java method signatures do notdeclare this exception, althoug it can
|
||||
* be thrown on almost any luaj Java operation.
|
||||
* This is analagous to the fact that any lua script can throw a lua error at any time.
|
||||
* <p>
|
||||
* The LuaError may be constructed with a message object, in which case the message
|
||||
* is the string representation of that object. getMessageObject will get the object
|
||||
* supplied at construct time, or a LuaString containing the message of an object
|
||||
* was not supplied.
|
||||
*/
|
||||
public class LuaError extends RuntimeException {
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
|
||||
protected int level;
|
||||
|
||||
|
||||
protected String fileline;
|
||||
|
||||
|
||||
protected String traceback;
|
||||
|
||||
|
||||
protected Throwable cause;
|
||||
|
||||
private LuaValue object;
|
||||
|
||||
/**
|
||||
* Get the string message if it was supplied, or a string representation of
|
||||
* the message object if that was supplied.
|
||||
|
||||
/** Get the string message if it was supplied, or a string
|
||||
* representation of the message object if that was supplied.
|
||||
*/
|
||||
@Override
|
||||
public String getMessage() {
|
||||
if (traceback != null)
|
||||
return traceback;
|
||||
@@ -62,75 +61,74 @@ public class LuaError extends RuntimeException {
|
||||
if (m == null)
|
||||
return null;
|
||||
if (fileline != null)
|
||||
return fileline + m;
|
||||
return fileline + " " + m;
|
||||
return m;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the LuaValue that was provided in the constructor, or a LuaString
|
||||
* containing the message if it was a string error argument.
|
||||
*
|
||||
/** Get the LuaValue that was provided in the constructor, or
|
||||
* a LuaString containing the message if it was a string error argument.
|
||||
* @return LuaValue which was used in the constructor, or a LuaString
|
||||
* containing the message.
|
||||
* containing the message.
|
||||
*/
|
||||
public LuaValue getMessageObject() {
|
||||
if (object != null)
|
||||
return object;
|
||||
if (object != null) return object;
|
||||
String m = getMessage();
|
||||
return m != null? LuaValue.valueOf(m): null;
|
||||
return m != null ? LuaValue.valueOf(m): null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct LuaError when a program exception occurs.
|
||||
* <p>
|
||||
public void setMessageObject(LuaValue messageObject) {
|
||||
this.object = messageObject;
|
||||
}
|
||||
|
||||
/** Construct LuaError when a program exception occurs.
|
||||
* <p>
|
||||
* All errors generated from lua code should throw LuaError(String) instead.
|
||||
*
|
||||
* @param cause the Throwable that caused the error, if known.
|
||||
* @param cause the Throwable that caused the error, if known.
|
||||
*/
|
||||
public LuaError(Throwable cause) {
|
||||
super("vm error: " + cause);
|
||||
super( "vm error: "+cause );
|
||||
this.cause = cause;
|
||||
this.level = 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a LuaError with a specific message.
|
||||
*
|
||||
* Construct a LuaError with a specific message.
|
||||
*
|
||||
* @param message message to supply
|
||||
*/
|
||||
public LuaError(String message) {
|
||||
super(message);
|
||||
super( message );
|
||||
this.level = 1;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a LuaError with a message, and level to draw line number
|
||||
* information from.
|
||||
*
|
||||
* Construct a LuaError with a message, and level to draw line number information from.
|
||||
* @param message message to supply
|
||||
* @param level where to supply line info from in call stack
|
||||
* @param level where to supply line info from in call stack
|
||||
*/
|
||||
public LuaError(String message, int level) {
|
||||
super(message);
|
||||
super( message );
|
||||
this.level = level;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a LuaError with a LuaValue as the message object, and level to
|
||||
* draw line number information from.
|
||||
*
|
||||
* Construct a LuaError with a LuaValue as the message object,
|
||||
* and level to draw line number information from.
|
||||
* @param message_object message string or object to supply
|
||||
*/
|
||||
public LuaError(LuaValue message_object) {
|
||||
super(message_object.tojstring());
|
||||
super( message_object.tojstring() );
|
||||
this.object = message_object;
|
||||
this.level = 1;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Get the cause, if any.
|
||||
*/
|
||||
@Override
|
||||
public Throwable getCause() { return cause; }
|
||||
public Throwable getCause() {
|
||||
return cause;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaFunction.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaFunction.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,86 +21,71 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
/**
|
||||
* Base class for functions implemented in Java.
|
||||
* <p>
|
||||
* Direct subclass include {@link org.luaj.vm2.lib.LibFunction} which is the
|
||||
* base class for all built-in library functions coded in Java, and
|
||||
* {@link LuaClosure}, which represents a lua closure whose bytecode is
|
||||
* interpreted when the function is invoked.
|
||||
*
|
||||
* Direct subclass include {@link org.luaj.vm2.libs.LibFunction}
|
||||
* which is the base class for
|
||||
* all built-in library functions coded in Java,
|
||||
* and {@link LuaClosure}, which represents a lua closure
|
||||
* whose bytecode is interpreted when the function is invoked.
|
||||
* @see LuaValue
|
||||
* @see LuaClosure
|
||||
* @see org.luaj.vm2.lib.LibFunction
|
||||
* @see org.luaj.vm2.libs.LibFunction
|
||||
*/
|
||||
abstract public class LuaFunction extends LuaValue {
|
||||
|
||||
abstract
|
||||
public class LuaFunction extends LuaValue {
|
||||
|
||||
/** Shared static metatable for all functions and closures. */
|
||||
public static LuaValue s_metatable;
|
||||
|
||||
@Override
|
||||
public int type() {
|
||||
return TFUNCTION;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String typename() {
|
||||
return "function";
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isfunction() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaFunction checkfunction() {
|
||||
public LuaFunction checkfunction() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaFunction optfunction(LuaFunction defval) {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String tojstring() {
|
||||
return "function: " + classnamestub();
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaString strvalue() {
|
||||
return valueOf(tojstring());
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the last part of the class name, to be used as a function name in
|
||||
* tojstring and elsewhere.
|
||||
*
|
||||
* @return String naming the last part of the class name after the last dot
|
||||
* (.) or dollar sign ($). If the first character is '_', it is
|
||||
* skipped.
|
||||
/** Return the last part of the class name, to be used as a function name in tojstring and elsewhere.
|
||||
* @return String naming the last part of the class name after the last dot (.) or dollar sign ($).
|
||||
* If the first character is '_', it is skipped.
|
||||
*/
|
||||
public String classnamestub() {
|
||||
String s = getClass().getName();
|
||||
int offset = Math.max(s.lastIndexOf('.'), s.lastIndexOf('$'))+1;
|
||||
if (s.charAt(offset) == '_')
|
||||
offset++;
|
||||
int offset = Math.max(s.lastIndexOf('.'), s.lastIndexOf('$')) + 1;
|
||||
if (s.charAt(offset) == '_') offset++;
|
||||
return s.substring(offset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a human-readable name for this function. Returns the last part of
|
||||
* the class name by default. Is overridden by LuaClosure to return the
|
||||
* source file and line, and by LibFunctions to return the name.
|
||||
*
|
||||
* @return common name for this function.
|
||||
*/
|
||||
|
||||
/** Return a human-readable name for this function. Returns the last part of the class name by default.
|
||||
* Is overridden by LuaClosure to return the source file and line, and by LibFunctions to return the name.
|
||||
* @return common name for this function. */
|
||||
public String name() {
|
||||
return classnamestub();
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaInteger.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaInteger.class
Normal file
Binary file not shown.
265
core/src/main/java/org/luaj/vm2/LuaInteger.java
Normal file
265
core/src/main/java/org/luaj/vm2/LuaInteger.java
Normal file
@@ -0,0 +1,265 @@
|
||||
/*******************************************************************************
|
||||
* Copyright (c) 2009 Luaj.org. All rights reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
import org.luaj.vm2.libs.MathLib;
|
||||
|
||||
/**
|
||||
* Extension of {@link LuaNumber} which can hold a Java long as its value.
|
||||
* <p>
|
||||
* These instance are not instantiated directly by clients, but indirectly
|
||||
* via the static functions {@link LuaValue#valueOf(int)} or {@link LuaValue#valueOf(double)}
|
||||
* functions. This ensures that policies regarding pooling of instances are
|
||||
* encapsulated.
|
||||
* <p>
|
||||
* There are no API's specific to LuaInteger that are useful beyond what is already
|
||||
* exposed in {@link LuaValue}.
|
||||
*
|
||||
* @see LuaValue
|
||||
* @see LuaNumber
|
||||
* @see LuaDouble
|
||||
* @see LuaValue#valueOf(int)
|
||||
* @see LuaValue#valueOf(double)
|
||||
*/
|
||||
public class LuaInteger extends LuaNumber {
|
||||
|
||||
private static final LuaInteger[] intValues = new LuaInteger[512];
|
||||
static {
|
||||
for ( int i=0; i<512; i++ )
|
||||
intValues[i] = new LuaInteger(i-256);
|
||||
}
|
||||
|
||||
public static LuaInteger valueOf(int i) {
|
||||
return i<=255 && i>=-256? intValues[i+256]: new LuaInteger(i);
|
||||
};
|
||||
|
||||
// TODO consider moving this to LuaValue
|
||||
/** Return a LuaNumber that represents the value provided
|
||||
* @param l long value to represent.
|
||||
* @return LuaNumber that is eithe LuaInteger or LuaDouble representing l
|
||||
* @see LuaValue#valueOf(int)
|
||||
* @see LuaValue#valueOf(double)
|
||||
*/
|
||||
public static LuaInteger valueOf(long l) {
|
||||
int i = (int) l;
|
||||
return l == i && i <= 255 && i >= -256 ? intValues[i+256] : new LuaInteger(l);
|
||||
}
|
||||
|
||||
/** The value being held by this instance. */
|
||||
public final long v;
|
||||
|
||||
/**
|
||||
* Package protected constructor.
|
||||
* @see LuaValue#valueOf(int)
|
||||
**/
|
||||
LuaInteger(long i) {
|
||||
this.v = i;
|
||||
}
|
||||
|
||||
public boolean isint() { return v == (int) v; }
|
||||
public boolean isinttype() { return true; }
|
||||
public boolean islong() { return true; }
|
||||
|
||||
public byte tobyte() { return (byte) v; }
|
||||
public char tochar() { return (char) v; }
|
||||
public double todouble() { return v; }
|
||||
public float tofloat() { return v; }
|
||||
public int toint() { return (int) v; }
|
||||
public long tolong() { return v; }
|
||||
public short toshort() { return (short) v; }
|
||||
|
||||
public double optdouble(double defval) { return v; }
|
||||
public int optint(int defval) { return (int) v; }
|
||||
public LuaInteger optinteger(LuaInteger defval) { return this; }
|
||||
public long optlong(long defval) { return v; }
|
||||
|
||||
public String tojstring() {
|
||||
return Long.toString(v);
|
||||
}
|
||||
|
||||
public LuaString strvalue() {
|
||||
return LuaString.valueOf(Long.toString(v));
|
||||
}
|
||||
|
||||
public LuaString optstring(LuaString defval) {
|
||||
return LuaString.valueOf(Long.toString(v));
|
||||
}
|
||||
|
||||
public LuaValue tostring() {
|
||||
return LuaString.valueOf(Long.toString(v));
|
||||
}
|
||||
|
||||
public String optjstring(String defval) {
|
||||
return Long.toString(v);
|
||||
}
|
||||
|
||||
public LuaInteger checkinteger() {
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean isstring() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public int hashCode() {
|
||||
return hashCode(v);
|
||||
}
|
||||
|
||||
public static int hashCode(long x) {
|
||||
return (int) (x ^ (x >>> 32));
|
||||
}
|
||||
|
||||
// unary operators
|
||||
public LuaValue neg() { return valueOf(-(long)v); }
|
||||
public LuaValue bnot() { return valueOf(~v); }
|
||||
|
||||
// object equality, used for key comparison
|
||||
public boolean equals(Object o) { return o instanceof LuaInteger? ((LuaInteger)o).v == v: false; }
|
||||
|
||||
// equality w/ metatable processing
|
||||
public LuaValue eq( LuaValue val ) { return val.raweq(v)? TRUE: FALSE; }
|
||||
public boolean eq_b( LuaValue val ) { return val.raweq(v); }
|
||||
|
||||
// equality w/o metatable processing
|
||||
public boolean raweq( LuaValue val ) { return val.raweq(v); }
|
||||
public boolean raweq( double val ) { return v == val; }
|
||||
public boolean raweq( int val ) { return v == val; }
|
||||
public boolean raweq( long val ) { return v == val; }
|
||||
|
||||
// arithmetic operators
|
||||
public LuaValue add( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.add(rhs): (n.isinttype()? LuaInteger.valueOf(v + n.tolong()): LuaDouble.valueOf(v + n.todouble())); }
|
||||
public LuaValue add( double lhs ) { return LuaDouble.valueOf(lhs + v); }
|
||||
public LuaValue add( int lhs ) { return LuaInteger.valueOf(lhs + v); }
|
||||
public LuaValue sub( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.sub(rhs): (n.isinttype()? LuaInteger.valueOf(v - n.tolong()): LuaDouble.valueOf(v - n.todouble())); }
|
||||
public LuaValue sub( double rhs ) { return LuaDouble.valueOf(v - rhs); }
|
||||
public LuaValue sub( int rhs ) { return LuaInteger.valueOf(v - rhs); }
|
||||
public LuaValue subFrom( double lhs ) { return LuaDouble.valueOf(lhs - v); }
|
||||
public LuaValue subFrom( int lhs ) { return LuaInteger.valueOf(lhs - v); }
|
||||
public LuaValue mul( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.mul(rhs): (n.isinttype()? LuaInteger.valueOf(v * n.tolong()): LuaDouble.valueOf(v * n.todouble())); }
|
||||
public LuaValue mul( double lhs ) { return LuaDouble.valueOf(lhs * v); }
|
||||
public LuaValue mul( int lhs ) { return LuaInteger.valueOf(lhs * v); }
|
||||
public LuaValue pow( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.pow(rhs): MathLib.dpow(v, n.todouble()); }
|
||||
public LuaValue pow( double rhs ) { return MathLib.dpow(v,rhs); }
|
||||
public LuaValue pow( int rhs ) { return MathLib.dpow(v,rhs); }
|
||||
public LuaValue powWith( double lhs ) { return MathLib.dpow(lhs,v); }
|
||||
public LuaValue powWith( int lhs ) { return MathLib.dpow(lhs,v); }
|
||||
public LuaValue div( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.div(rhs): LuaDouble.ddiv(v, n.todouble()); }
|
||||
public LuaValue idiv( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.idiv(rhs): (n.isinttype()? LuaInteger.valueOf(luaFloorDiv(v, n.tolong())): LuaDouble.didiv(v, n.todouble())); }
|
||||
public LuaValue div( double rhs ) { return LuaDouble.ddiv(v,rhs); }
|
||||
public LuaValue div( int rhs ) { return LuaDouble.ddiv(v,rhs); }
|
||||
public LuaValue divInto( double lhs ) { return LuaDouble.ddiv(lhs,v); }
|
||||
public LuaValue idiv( double rhs ) { return LuaDouble.didiv(v,rhs); }
|
||||
public LuaValue idiv( int rhs ) { return LuaInteger.valueOf(luaFloorDiv(v, rhs)); }
|
||||
public LuaValue idivInto( double lhs ) { return LuaDouble.didiv(lhs,v); }
|
||||
public LuaValue band( LuaValue rhs ) { LuaValue n = rhs.tonumber(); if (n.isnil()) return super.band(rhs); if (!n.islong()) throw bitwiseError(); return LuaInteger.valueOf(v & n.tolong()); }
|
||||
public LuaValue bor( LuaValue rhs ) { LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bor(rhs); if (!n.islong()) throw bitwiseError(); return LuaInteger.valueOf(v | n.tolong()); }
|
||||
public LuaValue bxor( LuaValue rhs ) { LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bxor(rhs); if (!n.islong()) throw bitwiseError(); return LuaInteger.valueOf(v ^ n.tolong()); }
|
||||
public LuaValue shl( LuaValue rhs ) { LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shl(rhs); if (!n.islong()) throw bitwiseError(); return LuaInteger.valueOf(luaShiftLeft(v, n.tolong())); }
|
||||
public LuaValue shr( LuaValue rhs ) { LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shr(rhs); if (!n.islong()) throw bitwiseError(); return LuaInteger.valueOf(luaShiftRight(v, n.tolong())); }
|
||||
public LuaValue mod( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.mod(rhs): (n.isinttype()? LuaInteger.valueOf(luaFloorMod(v, n.tolong())): LuaDouble.dmod(v, n.todouble())); }
|
||||
public LuaValue mod( double rhs ) { return LuaDouble.dmod(v,rhs); }
|
||||
public LuaValue mod( int rhs ) { return LuaInteger.valueOf(luaFloorMod(v, rhs)); }
|
||||
public LuaValue modFrom( double lhs ) { return LuaDouble.dmod(lhs,v); }
|
||||
|
||||
// relational operators
|
||||
public LuaValue lt( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.lt(rhs): (n.isinttype()? (v < n.tolong()? TRUE: FALSE): (v < n.todouble()? TRUE: FALSE)); }
|
||||
public LuaValue lt( double rhs ) { return v < rhs? TRUE: FALSE; }
|
||||
public LuaValue lt( int rhs ) { return v < rhs? TRUE: FALSE; }
|
||||
public boolean lt_b( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.lt_b(rhs): (n.isinttype()? v < n.tolong(): v < n.todouble()); }
|
||||
public boolean lt_b( int rhs ) { return v < rhs; }
|
||||
public boolean lt_b( double rhs ) { return v < rhs; }
|
||||
public LuaValue lteq( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.lteq(rhs): (n.isinttype()? (v <= n.tolong()? TRUE: FALSE): (v <= n.todouble()? TRUE: FALSE)); }
|
||||
public LuaValue lteq( double rhs ) { return v <= rhs? TRUE: FALSE; }
|
||||
public LuaValue lteq( int rhs ) { return v <= rhs? TRUE: FALSE; }
|
||||
public boolean lteq_b( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.lteq_b(rhs): (n.isinttype()? v <= n.tolong(): v <= n.todouble()); }
|
||||
public boolean lteq_b( int rhs ) { return v <= rhs; }
|
||||
public boolean lteq_b( double rhs ) { return v <= rhs; }
|
||||
public LuaValue gt( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.gt(rhs): (n.isinttype()? (v > n.tolong()? TRUE: FALSE): (v > n.todouble()? TRUE: FALSE)); }
|
||||
public LuaValue gt( double rhs ) { return v > rhs? TRUE: FALSE; }
|
||||
public LuaValue gt( int rhs ) { return v > rhs? TRUE: FALSE; }
|
||||
public boolean gt_b( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.gt_b(rhs): (n.isinttype()? v > n.tolong(): v > n.todouble()); }
|
||||
public boolean gt_b( int rhs ) { return v > rhs; }
|
||||
public boolean gt_b( double rhs ) { return v > rhs; }
|
||||
public LuaValue gteq( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.gteq(rhs): (n.isinttype()? (v >= n.tolong()? TRUE: FALSE): (v >= n.todouble()? TRUE: FALSE)); }
|
||||
public LuaValue gteq( double rhs ) { return v >= rhs? TRUE: FALSE; }
|
||||
public LuaValue gteq( int rhs ) { return v >= rhs? TRUE: FALSE; }
|
||||
public boolean gteq_b( LuaValue rhs ) { LuaValue n = rhs.tonumber(); return n.isnil()? super.gteq_b(rhs): (n.isinttype()? v >= n.tolong(): v >= n.todouble()); }
|
||||
public boolean gteq_b( int rhs ) { return v >= rhs; }
|
||||
public boolean gteq_b( double rhs ) { return v >= rhs; }
|
||||
|
||||
// string comparison
|
||||
public int strcmp( LuaString rhs ) { typerror("attempt to compare number with string"); return 0; }
|
||||
|
||||
public int checkint() {
|
||||
return (int) v;
|
||||
}
|
||||
public long checklong() {
|
||||
return v;
|
||||
}
|
||||
public double checkdouble() {
|
||||
return v;
|
||||
}
|
||||
public String checkjstring() {
|
||||
return String.valueOf(v);
|
||||
}
|
||||
public LuaString checkstring() {
|
||||
return valueOf( String.valueOf(v) );
|
||||
}
|
||||
|
||||
private static long luaFloorDiv(long lhs, long rhs) {
|
||||
if (rhs == 0) {
|
||||
throw new LuaError("attempt to divide by zero");
|
||||
}
|
||||
long quotient = lhs / rhs;
|
||||
long remainder = lhs % rhs;
|
||||
if (remainder != 0 && ((lhs ^ rhs) < 0)) {
|
||||
quotient--;
|
||||
}
|
||||
return quotient;
|
||||
}
|
||||
|
||||
private static long luaFloorMod(long lhs, long rhs) {
|
||||
if (rhs == 0) {
|
||||
throw new LuaError("attempt to divide by zero");
|
||||
}
|
||||
return lhs - rhs * luaFloorDiv(lhs, rhs);
|
||||
}
|
||||
|
||||
static long luaShiftLeft(long lhs, long rhs) {
|
||||
if (rhs < 0) {
|
||||
return luaShiftRight(lhs, -rhs);
|
||||
}
|
||||
return rhs >= Long.SIZE ? 0L : lhs << rhs;
|
||||
}
|
||||
|
||||
static long luaShiftRight(long lhs, long rhs) {
|
||||
if (rhs < 0) {
|
||||
return luaShiftLeft(lhs, -rhs);
|
||||
}
|
||||
return rhs >= Long.SIZE ? 0L : lhs >>> rhs;
|
||||
}
|
||||
|
||||
private static LuaError bitwiseError() {
|
||||
return new LuaError("number has no integer representation");
|
||||
}
|
||||
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaNil.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaNil.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -22,127 +22,87 @@
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Class to encapsulate behavior of the singleton instance {@code nil}
|
||||
* Class to encapsulate behavior of the singleton instance {@code nil}
|
||||
* <p>
|
||||
* There will be one instance of this class, {@link LuaValue#NIL}, per Java
|
||||
* virtual machine. However, the {@link Varargs} instance {@link LuaValue#NONE}
|
||||
* which is the empty list, is also considered treated as a nil value by
|
||||
* default.
|
||||
* There will be one instance of this class, {@link LuaValue#NIL},
|
||||
* per Java virtual machine.
|
||||
* However, the {@link Varargs} instance {@link LuaValue#NONE}
|
||||
* which is the empty list,
|
||||
* is also considered treated as a nil value by default.
|
||||
* <p>
|
||||
* Although it is possible to test for nil using Java == operator, the
|
||||
* recommended approach is to use the method {@link LuaValue#isnil()} instead.
|
||||
* By using that any ambiguities between {@link LuaValue#NIL} and
|
||||
* {@link LuaValue#NONE} are avoided.
|
||||
*
|
||||
* Although it is possible to test for nil using Java == operator,
|
||||
* the recommended approach is to use the method {@link LuaValue#isnil()}
|
||||
* instead. By using that any ambiguities between
|
||||
* {@link LuaValue#NIL} and {@link LuaValue#NONE} are avoided.
|
||||
* @see LuaValue
|
||||
* @see LuaValue#NIL
|
||||
*/
|
||||
public class LuaNil extends LuaValue {
|
||||
|
||||
|
||||
static final LuaNil _NIL = new LuaNil();
|
||||
|
||||
|
||||
public static LuaValue s_metatable;
|
||||
|
||||
|
||||
LuaNil() {}
|
||||
|
||||
@Override
|
||||
public int type() {
|
||||
return LuaValue.TNIL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "nil";
|
||||
return "nil";
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String typename() {
|
||||
return "nil";
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String tojstring() {
|
||||
return "nil";
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue not() {
|
||||
return LuaValue.TRUE;
|
||||
public LuaValue not() {
|
||||
return LuaValue.TRUE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean toboolean() {
|
||||
return false;
|
||||
|
||||
public boolean toboolean() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isnil() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean equals(Object o) {
|
||||
return o instanceof LuaNil;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue checknotnil() {
|
||||
public LuaValue checknotnil() {
|
||||
return argerror("value");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isvalidkey() {
|
||||
return false;
|
||||
}
|
||||
|
||||
// optional argument conversions - nil alwas falls badk to default value
|
||||
@Override
|
||||
public boolean optboolean(boolean defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaClosure optclosure(LuaClosure defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public double optdouble(double defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaFunction optfunction(LuaFunction defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public int optint(int defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaInteger optinteger(LuaInteger defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public long optlong(long defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaNumber optnumber(LuaNumber defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaTable opttable(LuaTable defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaThread optthread(LuaThread defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public String optjstring(String defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaString optstring(LuaString defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public Object optuserdata(Object defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public Object optuserdata(Class c, Object defval) { return defval; }
|
||||
|
||||
@Override
|
||||
public LuaValue optvalue(LuaValue defval) { return defval; }
|
||||
public boolean optboolean(boolean defval) { return defval; }
|
||||
public LuaClosure optclosure(LuaClosure defval) { return defval; }
|
||||
public double optdouble(double defval) { return defval; }
|
||||
public LuaFunction optfunction(LuaFunction defval) { return defval; }
|
||||
public int optint(int defval) { return defval; }
|
||||
public LuaInteger optinteger(LuaInteger defval) { return defval; }
|
||||
public long optlong(long defval) { return defval; }
|
||||
public LuaNumber optnumber(LuaNumber defval) { return defval; }
|
||||
public LuaTable opttable(LuaTable defval) { return defval; }
|
||||
public LuaThread optthread(LuaThread defval) { return defval; }
|
||||
public String optjstring(String defval) { return defval; }
|
||||
public LuaString optstring(LuaString defval) { return defval; }
|
||||
public Object optuserdata(Object defval) { return defval; }
|
||||
public Object optuserdata(Class c, Object defval) { return defval; }
|
||||
public LuaValue optvalue(LuaValue defval) { return defval; }
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaNumber.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaNumber.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,77 +21,61 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Base class for representing numbers as lua values directly.
|
||||
/**
|
||||
* Base class for representing numbers as lua values directly.
|
||||
* <p>
|
||||
* The main subclasses are {@link LuaInteger} which holds values that fit in a
|
||||
* java int, and {@link LuaDouble} which holds all other number values.
|
||||
*
|
||||
* The main subclasses are {@link LuaInteger} which holds values that fit in a java int,
|
||||
* and {@link LuaDouble} which holds all other number values.
|
||||
* @see LuaInteger
|
||||
* @see LuaDouble
|
||||
* @see LuaValue
|
||||
*
|
||||
*
|
||||
*/
|
||||
abstract public class LuaNumber extends LuaValue {
|
||||
abstract
|
||||
public class LuaNumber extends LuaValue {
|
||||
|
||||
/** Shared static metatable for all number values represented in lua. */
|
||||
public static LuaValue s_metatable;
|
||||
|
||||
@Override
|
||||
|
||||
public int type() {
|
||||
return TNUMBER;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String typename() {
|
||||
return "number";
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaNumber checknumber() {
|
||||
return this;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaNumber checknumber(String errmsg) {
|
||||
return this;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaNumber optnumber(LuaNumber defval) {
|
||||
return this;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaValue tonumber() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isnumber() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isstring() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue concat(LuaValue rhs) { return rhs.concatTo(this); }
|
||||
|
||||
@Override
|
||||
public Buffer concat(Buffer rhs) { return rhs.concatTo(this); }
|
||||
|
||||
@Override
|
||||
public LuaValue concatTo(LuaNumber lhs) { return strvalue().concatTo(lhs.strvalue()); }
|
||||
|
||||
@Override
|
||||
public LuaValue concatTo(LuaString lhs) { return strvalue().concatTo(lhs); }
|
||||
public LuaValue concat(LuaValue rhs) { return rhs.concatTo(this); }
|
||||
public Buffer concat(Buffer rhs) { return rhs.concatTo(this); }
|
||||
public LuaValue concatTo(LuaNumber lhs) { return strvalue().concatTo(lhs.strvalue()); }
|
||||
public LuaValue concatTo(LuaString lhs) { return strvalue().concatTo(lhs); }
|
||||
|
||||
}
|
||||
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaString.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaString.class
Normal file
Binary file not shown.
@@ -28,7 +28,7 @@ import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.PrintStream;
|
||||
|
||||
import org.luaj.vm2.lib.MathLib;
|
||||
import org.luaj.vm2.libs.MathLib;
|
||||
|
||||
/**
|
||||
* Subclass of {@link LuaValue} for representing lua strings.
|
||||
@@ -262,6 +262,7 @@ public class LuaString extends LuaValue {
|
||||
|
||||
// unary operators
|
||||
public LuaValue neg() { double d = scannumber(); return Double.isNaN(d)? super.neg(): valueOf(-d); }
|
||||
public LuaValue bnot() { double d = scannumber(); if (Double.isNaN(d)) return super.bnot(); if (d != (long) d) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(~((long) d)); }
|
||||
|
||||
// basic binary arithmetic
|
||||
public LuaValue add( LuaValue rhs ) { double d = scannumber(); return Double.isNaN(d)? arithmt(ADD,rhs): rhs.add(d); }
|
||||
@@ -280,9 +281,18 @@ public class LuaString extends LuaValue {
|
||||
public LuaValue powWith( double lhs ) { return MathLib.dpow(lhs, checkarith()); }
|
||||
public LuaValue powWith( int lhs ) { return MathLib.dpow(lhs, checkarith()); }
|
||||
public LuaValue div( LuaValue rhs ) { double d = scannumber(); return Double.isNaN(d)? arithmt(DIV,rhs): rhs.divInto(d); }
|
||||
public LuaValue idiv( LuaValue rhs ) { double d = scannumber(); return Double.isNaN(d)? arithmt(IDIV,rhs): rhs.idivInto(d); }
|
||||
public LuaValue div( double rhs ) { return LuaDouble.ddiv(checkarith(),rhs); }
|
||||
public LuaValue div( int rhs ) { return LuaDouble.ddiv(checkarith(),rhs); }
|
||||
public LuaValue divInto( double lhs ) { return LuaDouble.ddiv(lhs, checkarith()); }
|
||||
public LuaValue idiv( double rhs ) { return LuaDouble.didiv(checkarith(),rhs); }
|
||||
public LuaValue idiv( int rhs ) { return LuaDouble.didiv(checkarith(),rhs); }
|
||||
public LuaValue idivInto( double lhs ) { return LuaDouble.didiv(lhs, checkarith()); }
|
||||
public LuaValue band( LuaValue rhs ) { double d = scannumber(); if (Double.isNaN(d)) return super.band(rhs); if (d != (long) d) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.band(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) d) & n.tolong()); }
|
||||
public LuaValue bor( LuaValue rhs ) { double d = scannumber(); if (Double.isNaN(d)) return super.bor(rhs); if (d != (long) d) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bor(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) d) | n.tolong()); }
|
||||
public LuaValue bxor( LuaValue rhs ) { double d = scannumber(); if (Double.isNaN(d)) return super.bxor(rhs); if (d != (long) d) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.bxor(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(((long) d) ^ n.tolong()); }
|
||||
public LuaValue shl( LuaValue rhs ) { double d = scannumber(); if (Double.isNaN(d)) return super.shl(rhs); if (d != (long) d) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shl(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(LuaInteger.luaShiftLeft((long) d, n.tolong())); }
|
||||
public LuaValue shr( LuaValue rhs ) { double d = scannumber(); if (Double.isNaN(d)) return super.shr(rhs); if (d != (long) d) throw new LuaError("number has no integer representation"); LuaValue n = rhs.tonumber(); if (n.isnil()) return super.shr(rhs); if (!n.islong()) throw new LuaError("number has no integer representation"); return LuaInteger.valueOf(LuaInteger.luaShiftRight((long) d, n.tolong())); }
|
||||
public LuaValue mod( LuaValue rhs ) { double d = scannumber(); return Double.isNaN(d)? arithmt(MOD,rhs): rhs.modFrom(d); }
|
||||
public LuaValue mod( double rhs ) { return LuaDouble.dmod(checkarith(), rhs); }
|
||||
public LuaValue mod( int rhs ) { return LuaDouble.dmod(checkarith(), rhs); }
|
||||
@@ -340,10 +350,16 @@ public class LuaString extends LuaValue {
|
||||
return (int) (long) checkdouble();
|
||||
}
|
||||
public LuaInteger checkinteger() {
|
||||
return valueOf(checkint());
|
||||
double d = scannumber();
|
||||
if (Double.isNaN(d) || d != (long) d)
|
||||
argerror("integer");
|
||||
return LuaInteger.valueOf((long) d);
|
||||
}
|
||||
public long checklong() {
|
||||
return (long) checkdouble();
|
||||
double d = scannumber();
|
||||
if (Double.isNaN(d) || d != (long) d)
|
||||
argerror("integer");
|
||||
return (long) d;
|
||||
}
|
||||
public double checkdouble() {
|
||||
double d = scannumber();
|
||||
@@ -639,15 +655,9 @@ public class LuaString extends LuaValue {
|
||||
public static String decodeAsUtf8(byte[] bytes, int offset, int length) {
|
||||
int i,j,n,b;
|
||||
for ( i=offset,j=offset+length,n=0; i<j; ++n ) {
|
||||
byte v = bytes[i++];
|
||||
if ((v & 0xC0) == 0xC0) {
|
||||
++i;
|
||||
if ((v & 0xE0) == 0xE0) {
|
||||
++i;
|
||||
if ((v & 0xF0) == 0xF0) {
|
||||
++i;
|
||||
}
|
||||
}
|
||||
switch ( 0xE0 & bytes[i++] ) {
|
||||
case 0xE0: ++i;
|
||||
case 0xC0: ++i;
|
||||
}
|
||||
}
|
||||
char[] chars=new char[n];
|
||||
@@ -669,24 +679,11 @@ public class LuaString extends LuaValue {
|
||||
* @see #isValidUtf8()
|
||||
*/
|
||||
public static int lengthAsUtf8(char[] chars) {
|
||||
int i, b;
|
||||
int i,b;
|
||||
char c;
|
||||
for (i = 0, b = 0; i < chars.length; i++) {
|
||||
if ((c = chars[i]) < 0x80 || (c >= 0xdc00 && c < 0xe000)) {
|
||||
b += 1;
|
||||
} else if (c < 0x800) {
|
||||
b += 2;
|
||||
} else if (c >= 0xd800 && c < 0xdc00) {
|
||||
if (i + 1 < chars.length && chars[i+1] >= 0xdc00 && chars[i+1] < 0xe000) {
|
||||
b += 4;
|
||||
i++;
|
||||
} else {
|
||||
b += 1;
|
||||
}
|
||||
} else {
|
||||
b += 3;
|
||||
}
|
||||
}
|
||||
for ( i=b=chars.length; --i>=0; )
|
||||
if ( (c=chars[i]) >=0x80 )
|
||||
b += (c>=0x800)? 2: 1;
|
||||
return b;
|
||||
}
|
||||
|
||||
@@ -708,28 +705,16 @@ public class LuaString extends LuaValue {
|
||||
public static int encodeToUtf8(char[] chars, int nchars, byte[] bytes, int off) {
|
||||
char c;
|
||||
int j = off;
|
||||
for (int i = 0; i < nchars; i++) {
|
||||
if ((c = chars[i]) < 0x80) {
|
||||
for ( int i=0; i<nchars; i++ ) {
|
||||
if ( (c = chars[i]) < 0x80 ) {
|
||||
bytes[j++] = (byte) c;
|
||||
} else if (c < 0x800) {
|
||||
bytes[j++] = (byte) (0xC0 | ((c >> 6)));
|
||||
bytes[j++] = (byte) (0x80 | (c & 0x3f));
|
||||
} else if (c >= 0xd800 && c < 0xdc00) {
|
||||
if (i + 1 < nchars && chars[i+1] >= 0xdc00 && chars[i+1] < 0xe000) {
|
||||
int uc = 0x10000 + (((c & 0x3ff) << 10) | (chars[++i] & 0x3ff));
|
||||
bytes[j++] = (byte) (0xF0 | ((uc >> 18)));
|
||||
bytes[j++] = (byte) (0x80 | ((uc >> 12) & 0x3f));
|
||||
bytes[j++] = (byte) (0x80 | ((uc >> 6) & 0x3f));
|
||||
bytes[j++] = (byte) (0x80 | (uc & 0x3f));
|
||||
} else {
|
||||
bytes[j++] = (byte) '?';
|
||||
}
|
||||
} else if (c >= 0xdc00 && c < 0xe000) {
|
||||
bytes[j++] = (byte) '?';
|
||||
} else if ( c < 0x800 ) {
|
||||
bytes[j++] = (byte) (0xC0 | ((c>>6) & 0x1f));
|
||||
bytes[j++] = (byte) (0x80 | ( c & 0x3f));
|
||||
} else {
|
||||
bytes[j++] = (byte) (0xE0 | ((c >> 12)));
|
||||
bytes[j++] = (byte) (0x80 | ((c >> 6) & 0x3f));
|
||||
bytes[j++] = (byte) (0x80 | (c & 0x3f));
|
||||
bytes[j++] = (byte) (0xE0 | ((c>>12) & 0x0f));
|
||||
bytes[j++] = (byte) (0x80 | ((c>>6) & 0x3f));
|
||||
bytes[j++] = (byte) (0x80 | ( c & 0x3f));
|
||||
}
|
||||
}
|
||||
return j - off;
|
||||
@@ -742,16 +727,16 @@ public class LuaString extends LuaValue {
|
||||
* @see #decodeAsUtf8(byte[], int, int)
|
||||
*/
|
||||
public boolean isValidUtf8() {
|
||||
for (int i = m_offset, j = m_offset + m_length; i < j;) {
|
||||
for (int i=m_offset,j=m_offset+m_length; i<j;) {
|
||||
int c = m_bytes[i++];
|
||||
if (c >= 0)
|
||||
continue;
|
||||
if (((c & 0xE0) == 0xC0) && i < j && (m_bytes[i++] & 0xC0) == 0x80)
|
||||
continue;
|
||||
if (((c & 0xF0) == 0xE0) && i + 1 < j && (m_bytes[i++] & 0xC0) == 0x80 && (m_bytes[i++] & 0xC0) == 0x80)
|
||||
continue;
|
||||
if (((c & 0xF8) == 0xF0) && i + 2 < j && (m_bytes[i++] & 0xC0) == 0x80 && (m_bytes[i++] & 0xC0) == 0x80 && (m_bytes[i++] & 0xC0) == 0x80)
|
||||
continue;
|
||||
if ( c >= 0 ) continue;
|
||||
if ( ((c & 0xE0) == 0xC0)
|
||||
&& i<j
|
||||
&& (m_bytes[i++] & 0xC0) == 0x80) continue;
|
||||
if ( ((c & 0xF0) == 0xE0)
|
||||
&& i+1<j
|
||||
&& (m_bytes[i++] & 0xC0) == 0x80
|
||||
&& (m_bytes[i++] & 0xC0) == 0x80) continue;
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
@@ -780,87 +765,25 @@ public class LuaString extends LuaValue {
|
||||
double d = scannumber( base );
|
||||
return Double.isNaN(d)? NIL: valueOf(d);
|
||||
}
|
||||
|
||||
private boolean isspace(byte c) {
|
||||
return c == ' ' || (c >= '\t' && c <= '\r');
|
||||
}
|
||||
|
||||
private boolean isdigit(byte c) {
|
||||
return (c >= '0' && c <= '9');
|
||||
}
|
||||
|
||||
private boolean isxdigit(byte c) {
|
||||
return (c >= '0' && c <= '9') || (c >= 'a' && c <= 'f') || (c >= 'A' && c <= 'F');
|
||||
}
|
||||
|
||||
private int hexvalue(byte c) {
|
||||
return c <= '9' ? c - '0' : c <= 'F' ? c + 10 - 'A' : c + 10 - 'a';
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert to a number in base 10, or base 16 if the string starts with '0x',
|
||||
|
||||
/**
|
||||
* Convert to a number in base 10, or base 16 if the string starts with '0x',
|
||||
* or return Double.NaN if it cannot be converted to a number.
|
||||
* @return double value if conversion is valid, or Double.NaN if not
|
||||
*/
|
||||
public double scannumber() {
|
||||
int i = m_offset, j = m_offset + m_length;
|
||||
while (i < j && isspace(m_bytes[i]))
|
||||
++i;
|
||||
while (i < j && isspace(m_bytes[j - 1]))
|
||||
--j;
|
||||
if (i >= j)
|
||||
int i=m_offset,j=m_offset+m_length;
|
||||
while ( i<j && m_bytes[i]==' ' ) ++i;
|
||||
while ( i<j && m_bytes[j-1]==' ' ) --j;
|
||||
if ( i>=j )
|
||||
return Double.NaN;
|
||||
if (indexOf((byte) 'x', i - m_offset) != -1 || indexOf((byte) 'X', i - m_offset) != -1)
|
||||
return strx2number(i, j);
|
||||
return scandouble(i, j);
|
||||
}
|
||||
|
||||
private double strx2number(int start, int end) {
|
||||
double sgn = (m_bytes[start] == '-') ? -1.0 : 1.0;
|
||||
if (sgn == -1.0 || m_bytes[start] == '+')
|
||||
++start;
|
||||
if (start + 2 >= end)
|
||||
return Double.NaN;
|
||||
if (m_bytes[start++] != '0')
|
||||
return Double.NaN;
|
||||
if (m_bytes[start] != 'x' && m_bytes[start] != 'X')
|
||||
return Double.NaN;
|
||||
++start;
|
||||
double m = 0;
|
||||
int e = 0;
|
||||
boolean i = isxdigit(m_bytes[start]);
|
||||
while (start < end && isxdigit(m_bytes[start]))
|
||||
m = (m * 16) + hexvalue(m_bytes[start++]);
|
||||
if (start < end && m_bytes[start] == '.') {
|
||||
++start;
|
||||
while (start < end && isxdigit(m_bytes[start])) {
|
||||
m = (m * 16) + hexvalue(m_bytes[start++]);
|
||||
e -= 4;
|
||||
}
|
||||
int prefix = (m_bytes[i] == '+' || m_bytes[i] == '-') ? i + 1 : i;
|
||||
if (prefix + 1 < j && m_bytes[prefix]=='0' && (m_bytes[prefix+1]=='x'||m_bytes[prefix+1]=='X')) {
|
||||
double l = scanlong(16, prefix + 2, j, i != prefix);
|
||||
return Double.isNaN(l)? scandouble(i,j): l;
|
||||
}
|
||||
if (!i && e == 0)
|
||||
return Double.NaN;
|
||||
if (start < end && (m_bytes[start] == 'p' || m_bytes[start] == 'P')) {
|
||||
++start;
|
||||
int exp1 = 0;
|
||||
boolean neg1 = false;
|
||||
if (start < end) {
|
||||
if (m_bytes[start] == '-')
|
||||
neg1 = true;
|
||||
if (neg1 || m_bytes[start] == '+')
|
||||
++start;
|
||||
}
|
||||
if (start >= end || !isdigit(m_bytes[start]))
|
||||
return Double.NaN;
|
||||
while (start < end && isdigit(m_bytes[start]))
|
||||
exp1 = exp1 * 10 + m_bytes[start++] - '0';
|
||||
if (neg1)
|
||||
exp1 = -exp1;
|
||||
e += exp1;
|
||||
}
|
||||
if (start != end)
|
||||
return Double.NaN;
|
||||
return sgn * m * MathLib.dpow_d(2.0, e);
|
||||
double l = scanlong(10, i, j);
|
||||
return Double.isNaN(l)? scandouble(i,j): l;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -872,8 +795,8 @@ public class LuaString extends LuaValue {
|
||||
if ( base < 2 || base > 36 )
|
||||
return Double.NaN;
|
||||
int i=m_offset,j=m_offset+m_length;
|
||||
while ( i<j && isspace(m_bytes[i]) ) ++i;
|
||||
while ( i<j && isspace(m_bytes[j-1]) ) --j;
|
||||
while ( i<j && m_bytes[i]==' ' ) ++i;
|
||||
while ( i<j && m_bytes[j-1]==' ' ) --j;
|
||||
if ( i>=j )
|
||||
return Double.NaN;
|
||||
return scanlong( base, i, j );
|
||||
@@ -888,9 +811,14 @@ public class LuaString extends LuaValue {
|
||||
* or Double.NaN if not
|
||||
*/
|
||||
private double scanlong( int base, int start, int end ) {
|
||||
return scanlong(base, start, end, false);
|
||||
}
|
||||
|
||||
private double scanlong( int base, int start, int end, boolean hasSign ) {
|
||||
long x = 0;
|
||||
boolean neg = (m_bytes[start] == '-');
|
||||
if (neg || m_bytes[start] == '+') start++;
|
||||
boolean neg = hasSign && m_bytes[start - 1] == '-';
|
||||
if (start >= end)
|
||||
return Double.NaN;
|
||||
for ( int i=start; i<end; i++ ) {
|
||||
int digit = m_bytes[i] - (base<=10||(m_bytes[i]>='0'&&m_bytes[i]<='9')? '0':
|
||||
m_bytes[i]>='A'&&m_bytes[i]<='Z'? ('A'-10): ('a'-10));
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaTable$DeadSlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$DeadSlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$Entry.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$Entry.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$IntKeyEntry.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$IntKeyEntry.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$LinkSlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$LinkSlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$NormalEntry.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$NormalEntry.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$NumberValueEntry.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$NumberValueEntry.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$Slot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$Slot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable$StrongSlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable$StrongSlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaTable.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaTable.class
Normal file
Binary file not shown.
File diff suppressed because it is too large
Load Diff
BIN
core/src/main/java/org/luaj/vm2/LuaThread$State.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaThread$State.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaThread.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaThread.class
Normal file
Binary file not shown.
309
core/src/main/java/org/luaj/vm2/LuaThread.java
Normal file
309
core/src/main/java/org/luaj/vm2/LuaThread.java
Normal file
@@ -0,0 +1,309 @@
|
||||
/*******************************************************************************
|
||||
* Copyright (c) 2007-2012 LuaJ. All rights reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
import java.lang.ref.WeakReference;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.locks.Condition;
|
||||
import java.util.concurrent.locks.Lock;
|
||||
import java.util.concurrent.locks.ReentrantLock;
|
||||
|
||||
/**
|
||||
* Subclass of {@link LuaValue} that implements
|
||||
* a lua coroutine thread using Java Threads.
|
||||
* <p>
|
||||
* A LuaThread is typically created in response to a scripted call to
|
||||
* {@code coroutine.create()}
|
||||
* <p>
|
||||
* The threads must be initialized with the globals, so that
|
||||
* the global environment may be passed along according to rules of lua.
|
||||
* This is done via the constructor arguments {@link #LuaThread(Globals)} or
|
||||
* {@link #LuaThread(Globals, LuaValue)}.
|
||||
* <p>
|
||||
* The utility classes {@link org.luaj.vm2.libs.jse.JsePlatform} and
|
||||
* {@link org.luaj.vm2.libs.jme.JmePlatform}
|
||||
* see to it that this {@link Globals} are initialized properly.
|
||||
* <p>
|
||||
* The behavior of coroutine threads matches closely the behavior
|
||||
* of C coroutine library. However, because of the use of Java threads
|
||||
* to manage call state, it is possible to yield from anywhere in luaj.
|
||||
* <p>
|
||||
* Each Java thread wakes up at regular intervals and checks a weak reference
|
||||
* to determine if it can ever be resumed. If not, it throws
|
||||
* {@link OrphanedThread} which is an {@link java.lang.Error}.
|
||||
* Applications should not catch {@link OrphanedThread}, because it can break
|
||||
* the thread safety of luaj. The value controlling the polling interval
|
||||
* is {@link #thread_orphan_check_interval} and may be set by the user.
|
||||
* <p>
|
||||
* There are two main ways to abandon a coroutine. The first is to call
|
||||
* {@code yield()} from lua, or equivalently {@link Globals#yield(Varargs)},
|
||||
* and arrange to have it never resumed possibly by values passed to yield.
|
||||
* The second is to throw {@link OrphanedThread}, which should put the thread
|
||||
* in a dead state. In either case all references to the thread must be
|
||||
* dropped, and the garbage collector must run for the thread to be
|
||||
* garbage collected.
|
||||
*
|
||||
*
|
||||
* @see LuaValue
|
||||
* @see org.luaj.vm2.libs.jse.JsePlatform
|
||||
* @see org.luaj.vm2.libs.jme.JmePlatform
|
||||
* @see org.luaj.vm2.libs.CoroutineLib
|
||||
*/
|
||||
public class LuaThread extends LuaValue {
|
||||
|
||||
/** Shared metatable for lua threads. */
|
||||
public static LuaValue s_metatable;
|
||||
|
||||
/** The current number of coroutines. Should not be set. */
|
||||
public static int coroutine_count = 0;
|
||||
|
||||
/** Polling interval, in milliseconds, which each thread uses while waiting to
|
||||
* return from a yielded state to check if the lua threads is no longer
|
||||
* referenced and therefore should be garbage collected.
|
||||
* A short polling interval for many threads will consume server resources.
|
||||
* Orphaned threads cannot be detected and collected unless garbage
|
||||
* collection is run. This can be changed by Java startup code if desired.
|
||||
*/
|
||||
public static long thread_orphan_check_interval = 5000;
|
||||
|
||||
public static final String USE_PLATFORM_THREAD = "USE_PLATFORM_THREAD";
|
||||
|
||||
private static boolean SUPPORT_VIRTUAL_THREAD = false;
|
||||
|
||||
static {
|
||||
try {
|
||||
Thread.class.getMethod("ofVirtual");
|
||||
SUPPORT_VIRTUAL_THREAD = true;
|
||||
} catch (Exception e) {
|
||||
//e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
public static final int STATUS_INITIAL = 0;
|
||||
public static final int STATUS_SUSPENDED = 1;
|
||||
public static final int STATUS_RUNNING = 2;
|
||||
public static final int STATUS_NORMAL = 3;
|
||||
public static final int STATUS_DEAD = 4;
|
||||
public static final String[] STATUS_NAMES = {
|
||||
"suspended",
|
||||
"suspended",
|
||||
"running",
|
||||
"normal",
|
||||
"dead",};
|
||||
|
||||
public final State state;
|
||||
|
||||
public static final int MAX_CALLSTACK = 256;
|
||||
|
||||
/** Thread-local used by DebugLib to store debugging state.
|
||||
* This is an opaque value that should not be modified by applications. */
|
||||
public Object callstack;
|
||||
|
||||
public final Globals globals;
|
||||
|
||||
/** Error message handler for this thread, if any. */
|
||||
public LuaValue errorfunc;
|
||||
|
||||
/** Private constructor for main thread only */
|
||||
public LuaThread(Globals globals) {
|
||||
state = new State(globals, this, null);
|
||||
state.status = STATUS_RUNNING;
|
||||
this.globals = globals;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a LuaThread around a function and environment
|
||||
* @param func The function to execute
|
||||
*/
|
||||
public LuaThread(Globals globals, LuaValue func) {
|
||||
LuaValue.assert_(func != null, "function cannot be null");
|
||||
state = new State(globals, this, func);
|
||||
this.globals = globals;
|
||||
}
|
||||
|
||||
public int type() {
|
||||
return LuaValue.TTHREAD;
|
||||
}
|
||||
|
||||
public String typename() {
|
||||
return "thread";
|
||||
}
|
||||
|
||||
public boolean isthread() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public LuaThread optthread(LuaThread defval) {
|
||||
return this;
|
||||
}
|
||||
|
||||
public LuaThread checkthread() {
|
||||
return this;
|
||||
}
|
||||
|
||||
public LuaValue getmetatable() {
|
||||
return s_metatable;
|
||||
}
|
||||
|
||||
public String getStatus() {
|
||||
return STATUS_NAMES[state.status];
|
||||
}
|
||||
|
||||
public boolean isMainThread() {
|
||||
return this.state.function == null;
|
||||
}
|
||||
|
||||
public Varargs resume(Varargs args) {
|
||||
final LuaThread.State s = this.state;
|
||||
if (s.status > LuaThread.STATUS_SUSPENDED)
|
||||
return LuaValue.varargsOf(LuaValue.FALSE,
|
||||
LuaValue.valueOf("cannot resume "+(s.status==LuaThread.STATUS_DEAD? "dead": "non-suspended")+" coroutine"));
|
||||
return s.lua_resume(this, args);
|
||||
}
|
||||
|
||||
public static class State implements Runnable {
|
||||
private final Globals globals;
|
||||
final WeakReference lua_thread;
|
||||
public final LuaValue function;
|
||||
Varargs args = LuaValue.NONE;
|
||||
Varargs result = LuaValue.NONE;
|
||||
String error = null;
|
||||
|
||||
/** Hook function control state used by debug lib. */
|
||||
public LuaValue hookfunc;
|
||||
|
||||
public boolean hookline;
|
||||
public boolean hookcall;
|
||||
public boolean hookrtrn;
|
||||
public int hookcount;
|
||||
public boolean inhook;
|
||||
public int lastline;
|
||||
public int bytecodes;
|
||||
|
||||
public int status = LuaThread.STATUS_INITIAL;
|
||||
private Lock locker = new ReentrantLock();
|
||||
private Condition cond = locker.newCondition();
|
||||
|
||||
State(Globals globals, LuaThread lua_thread, LuaValue function) {
|
||||
this.globals = globals;
|
||||
this.lua_thread = new WeakReference(lua_thread);
|
||||
this.function = function;
|
||||
}
|
||||
|
||||
public void run() {
|
||||
locker.lock();
|
||||
try {
|
||||
try {
|
||||
Varargs a = this.args;
|
||||
this.args = LuaValue.NONE;
|
||||
this.result = function.invoke(a);
|
||||
} catch (Throwable t) {
|
||||
this.error = t.getMessage();
|
||||
} finally {
|
||||
this.status = LuaThread.STATUS_DEAD;
|
||||
cond.signal();
|
||||
}
|
||||
} finally {
|
||||
locker.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
public Varargs lua_resume(LuaThread new_thread, Varargs args) {
|
||||
locker.lock();
|
||||
try {
|
||||
LuaThread previous_thread = globals.running;
|
||||
try {
|
||||
globals.running = new_thread;
|
||||
this.args = args;
|
||||
if (this.status == STATUS_INITIAL) {
|
||||
this.status = STATUS_RUNNING;
|
||||
Thread t = null;
|
||||
if(SUPPORT_VIRTUAL_THREAD) {
|
||||
LuaValue setting = globals.get(USE_PLATFORM_THREAD);
|
||||
if(setting.isnil()) {//default
|
||||
if(Thread.currentThread().isVirtual()) {
|
||||
t = Thread.ofVirtual().name("Coroutine-"+(++coroutine_count)).start(this);
|
||||
}
|
||||
} else {
|
||||
if(!setting.toboolean()) {
|
||||
t = Thread.ofVirtual().name("Coroutine-"+(++coroutine_count)).start(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (t == null){
|
||||
new Thread(this, "Coroutine-"+(++coroutine_count)).start();
|
||||
}
|
||||
} else {
|
||||
cond.signal();
|
||||
}
|
||||
if (previous_thread != null)
|
||||
previous_thread.state.status = STATUS_NORMAL;
|
||||
this.status = STATUS_RUNNING;
|
||||
cond.await();
|
||||
return (this.error != null?
|
||||
LuaValue.varargsOf(LuaValue.FALSE, LuaValue.valueOf(this.error)):
|
||||
LuaValue.varargsOf(LuaValue.TRUE, this.result));
|
||||
} catch (InterruptedException ie) {
|
||||
throw new OrphanedThread();
|
||||
} finally {
|
||||
this.args = LuaValue.NONE;
|
||||
this.result = LuaValue.NONE;
|
||||
this.error = null;
|
||||
globals.running = previous_thread;
|
||||
if (previous_thread != null)
|
||||
globals.running.state.status =STATUS_RUNNING;
|
||||
}
|
||||
} finally {
|
||||
locker.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
public Varargs lua_yield(Varargs args) {
|
||||
locker.lock();
|
||||
try {
|
||||
try {
|
||||
this.result = args;
|
||||
this.status = STATUS_SUSPENDED;
|
||||
cond.signal();
|
||||
do {
|
||||
cond.await(thread_orphan_check_interval,TimeUnit.MILLISECONDS);
|
||||
if (this.lua_thread.get() == null) {
|
||||
this.status = STATUS_DEAD;
|
||||
throw new OrphanedThread();
|
||||
}
|
||||
} while (this.status == STATUS_SUSPENDED);
|
||||
return this.args;
|
||||
} catch (InterruptedException ie) {
|
||||
this.status = STATUS_DEAD;
|
||||
throw new OrphanedThread();
|
||||
} finally {
|
||||
this.args = LuaValue.NONE;
|
||||
this.result = LuaValue.NONE;
|
||||
}
|
||||
} finally {
|
||||
locker.unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaUserdata.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaUserdata.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,136 +21,106 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
|
||||
public class LuaUserdata extends LuaValue {
|
||||
|
||||
public Object m_instance;
|
||||
|
||||
public Object m_instance;
|
||||
public LuaValue m_metatable;
|
||||
|
||||
|
||||
public LuaUserdata(Object obj) {
|
||||
m_instance = obj;
|
||||
}
|
||||
|
||||
|
||||
public LuaUserdata(Object obj, LuaValue metatable) {
|
||||
m_instance = obj;
|
||||
m_metatable = metatable;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String tojstring() {
|
||||
return String.valueOf(m_instance);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public int type() {
|
||||
return LuaValue.TUSERDATA;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String typename() {
|
||||
return "userdata";
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return m_instance.hashCode();
|
||||
}
|
||||
|
||||
|
||||
public Object userdata() {
|
||||
return m_instance;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isuserdata() { return true; }
|
||||
|
||||
@Override
|
||||
public boolean isuserdata(Class c) { return c.isAssignableFrom(m_instance.getClass()); }
|
||||
|
||||
@Override
|
||||
public Object touserdata() { return m_instance; }
|
||||
|
||||
@Override
|
||||
public Object touserdata(Class c) { return c.isAssignableFrom(m_instance.getClass())? m_instance: null; }
|
||||
|
||||
@Override
|
||||
public Object optuserdata(Object defval) { return m_instance; }
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isuserdata() { return true; }
|
||||
public boolean isuserdata(Class c) { return c.isAssignableFrom(m_instance.getClass()); }
|
||||
public Object touserdata() { return m_instance; }
|
||||
public Object touserdata(Class c) { return c.isAssignableFrom(m_instance.getClass())? m_instance: null; }
|
||||
public Object optuserdata(Object defval) { return m_instance; }
|
||||
public Object optuserdata(Class c, Object defval) {
|
||||
if (!c.isAssignableFrom(m_instance.getClass()))
|
||||
typerror(c.getName());
|
||||
return m_instance;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaValue getmetatable() {
|
||||
return m_metatable;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue setmetatable(LuaValue metatable) {
|
||||
this.m_metatable = metatable;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object checkuserdata() {
|
||||
return m_instance;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object checkuserdata(Class c) {
|
||||
if (c.isAssignableFrom(m_instance.getClass()))
|
||||
return m_instance;
|
||||
|
||||
public Object checkuserdata(Class c) {
|
||||
if ( c.isAssignableFrom(m_instance.getClass()) )
|
||||
return m_instance;
|
||||
return typerror(c.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue get(LuaValue key) {
|
||||
return m_metatable != null? gettable(this, key): NIL;
|
||||
|
||||
public LuaValue get( LuaValue key ) {
|
||||
return m_metatable!=null? gettable(this,key): NIL;
|
||||
}
|
||||
|
||||
public void set( LuaValue key, LuaValue value ) {
|
||||
if ( m_metatable==null || ! settable(this,key,value) )
|
||||
error( "cannot set "+key+" for userdata" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public void set(LuaValue key, LuaValue value) {
|
||||
if (m_metatable == null || !settable(this, key, value))
|
||||
error("cannot set " + key + " for userdata");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object val) {
|
||||
if (this == val)
|
||||
public boolean equals( Object val ) {
|
||||
if ( this == val )
|
||||
return true;
|
||||
if (!(val instanceof LuaUserdata))
|
||||
if ( ! (val instanceof LuaUserdata) )
|
||||
return false;
|
||||
LuaUserdata u = (LuaUserdata) val;
|
||||
return m_instance.equals(u.m_instance);
|
||||
}
|
||||
|
||||
// equality w/ metatable processing
|
||||
@Override
|
||||
public LuaValue eq(LuaValue val) { return eq_b(val)? TRUE: FALSE; }
|
||||
|
||||
@Override
|
||||
public boolean eq_b(LuaValue val) {
|
||||
if (val.raweq(this))
|
||||
return true;
|
||||
if (m_metatable == null || !val.isuserdata())
|
||||
return false;
|
||||
public LuaValue eq( LuaValue val ) { return eq_b(val)? TRUE: FALSE; }
|
||||
public boolean eq_b( LuaValue val ) {
|
||||
if ( val.raweq(this) ) return true;
|
||||
if ( m_metatable == null || !val.isuserdata() ) return false;
|
||||
LuaValue valmt = val.getmetatable();
|
||||
return valmt != null && LuaValue.eqmtcall(this, m_metatable, val, valmt);
|
||||
return valmt!=null && LuaValue.eqmtcall(this, m_metatable, val, valmt);
|
||||
}
|
||||
|
||||
|
||||
// equality w/o metatable processing
|
||||
@Override
|
||||
public boolean raweq(LuaValue val) { return val.raweq(this); }
|
||||
|
||||
@Override
|
||||
public boolean raweq(LuaUserdata val) {
|
||||
return this == val || m_metatable == val.m_metatable && m_instance.equals(val.m_instance);
|
||||
public boolean raweq( LuaValue val ) { return val.raweq(this); }
|
||||
public boolean raweq( LuaUserdata val ) {
|
||||
return this == val || (m_metatable == val.m_metatable && m_instance.equals(val.m_instance));
|
||||
}
|
||||
|
||||
|
||||
// __eq metatag processing
|
||||
public boolean eqmt(LuaValue val) {
|
||||
return m_metatable != null && val.isuserdata()? LuaValue.eqmtcall(this, m_metatable, val, val.getmetatable())
|
||||
: false;
|
||||
public boolean eqmt( LuaValue val ) {
|
||||
return m_metatable!=null && val.isuserdata()? LuaValue.eqmtcall(this, m_metatable, val, val.getmetatable()): false;
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/LuaValue$None.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaValue$None.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/LuaValue.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/LuaValue.class
Normal file
Binary file not shown.
@@ -75,7 +75,7 @@ package org.luaj.vm2;
|
||||
* } </pre>
|
||||
* For this to work the file must be in the current directory, or in the class path,
|
||||
* dependening on the platform.
|
||||
* See {@link org.luaj.vm2.lib.jse.JsePlatform} and {@link org.luaj.vm2.lib.jme.JmePlatform} for details.
|
||||
* See {@link org.luaj.vm2.libs.jse.JsePlatform} and {@link org.luaj.vm2.libs.jme.JmePlatform} for details.
|
||||
* <p>
|
||||
* In general a {@link LuaError} may be thrown on any operation when the
|
||||
* types supplied to any operation are illegal from a lua perspective.
|
||||
@@ -99,10 +99,10 @@ package org.luaj.vm2;
|
||||
* {@link #INDEX}, {@link #NEWINDEX}, {@link #CALL}, {@link #MODE}, {@link #METATABLE},
|
||||
* {@link #ADD}, {@link #SUB}, {@link #DIV}, {@link #MUL}, {@link #POW},
|
||||
* {@link #MOD}, {@link #UNM}, {@link #LEN}, {@link #EQ}, {@link #LT},
|
||||
* {@link #LE}, {@link #TOSTRING}, {@link #CONCAT}, {@link PAIRS} and {@link IPAIRS}.
|
||||
* {@link #LE}, {@link #TOSTRING}, {@link #CONCAT}, {@link #PAIRS}, and {@link #IPAIRS}.
|
||||
*
|
||||
* @see org.luaj.vm2.lib.jse.JsePlatform
|
||||
* @see org.luaj.vm2.lib.jme.JmePlatform
|
||||
* @see org.luaj.vm2.libs.jse.JsePlatform
|
||||
* @see org.luaj.vm2.libs.jme.JmePlatform
|
||||
* @see LoadState
|
||||
* @see Varargs
|
||||
*/
|
||||
@@ -213,6 +213,27 @@ public class LuaValue extends Varargs {
|
||||
/** LuaString constant with value "__div" for use as metatag */
|
||||
public static final LuaString DIV = valueOf("__div");
|
||||
|
||||
/** LuaString constant with value "__idiv" for use as metatag */
|
||||
public static final LuaString IDIV = valueOf("__idiv");
|
||||
|
||||
/** LuaString constant with value "__band" for use as metatag */
|
||||
public static final LuaString BAND = valueOf("__band");
|
||||
|
||||
/** LuaString constant with value "__bor" for use as metatag */
|
||||
public static final LuaString BOR = valueOf("__bor");
|
||||
|
||||
/** LuaString constant with value "__bxor" for use as metatag */
|
||||
public static final LuaString BXOR = valueOf("__bxor");
|
||||
|
||||
/** LuaString constant with value "__shl" for use as metatag */
|
||||
public static final LuaString SHL = valueOf("__shl");
|
||||
|
||||
/** LuaString constant with value "__shr" for use as metatag */
|
||||
public static final LuaString SHR = valueOf("__shr");
|
||||
|
||||
/** LuaString constant with value "__bnot" for use as metatag */
|
||||
public static final LuaString BNOT = valueOf("__bnot");
|
||||
|
||||
/** LuaString constant with value "__mul" for use as metatag */
|
||||
public static final LuaString MUL = valueOf("__mul");
|
||||
|
||||
@@ -244,11 +265,11 @@ public class LuaValue extends Varargs {
|
||||
public static final LuaString CONCAT = valueOf("__concat");
|
||||
|
||||
/** LuaString constant with value "__pairs" for use as metatag */
|
||||
public static final LuaString PAIRS = valueOf("__pairs");
|
||||
public static final LuaString PAIRS = valueOf("__pairs");
|
||||
|
||||
/** LuaString constant with value "__ipairs" for use as metatag */
|
||||
public static final LuaString IPAIRS = valueOf("__ipairs");
|
||||
|
||||
public static final LuaString IPAIRS = valueOf("__ipairs");
|
||||
|
||||
/** LuaString constant with value "" */
|
||||
public static final LuaString EMPTYSTRING = valueOf("");
|
||||
|
||||
@@ -535,7 +556,7 @@ public class LuaValue extends Varargs {
|
||||
* @see #isstring()
|
||||
* @see #TSTRING
|
||||
*/
|
||||
public String tojstring() { return typename() + ": 0x" + Integer.toHexString(hashCode()); }
|
||||
public String tojstring() { return typename() + ": " + Integer.toHexString(hashCode()); }
|
||||
|
||||
/** Convert to userdata instance, or null.
|
||||
* @return userdata instance if userdata, or null if not {@link LuaUserdata}
|
||||
@@ -631,7 +652,7 @@ public class LuaValue extends Varargs {
|
||||
* @see #isclosure()
|
||||
* @see #TFUNCTION
|
||||
*/
|
||||
public LuaClosure optclosure(LuaClosure defval) { argerror("function"); return null; }
|
||||
public LuaClosure optclosure(LuaClosure defval) { argerror("closure"); return null; }
|
||||
|
||||
/** Check that optional argument is a number or string convertible to number and return as double
|
||||
* @param defval double to return if {@code this} is nil or none
|
||||
@@ -743,7 +764,7 @@ public class LuaValue extends Varargs {
|
||||
* @see #toString()
|
||||
* @see #TSTRING
|
||||
*/
|
||||
public String optjstring(String defval) { argerror("string"); return null; }
|
||||
public String optjstring(String defval) { argerror("String"); return null; }
|
||||
|
||||
/** Check that optional argument is a string or number and return as {@link LuaString}
|
||||
* @param defval {@link LuaString} to return if {@code this} is nil or none
|
||||
@@ -894,7 +915,7 @@ public class LuaValue extends Varargs {
|
||||
* @see #optint(int)
|
||||
* @see #TNUMBER
|
||||
*/
|
||||
public int checkint() { argerror("number"); return 0; }
|
||||
public int checkint() { argerror("int"); return 0; }
|
||||
|
||||
/** Check that the value is numeric, and convert and cast value to int, or throw {@link LuaError} if not numeric
|
||||
* <p>
|
||||
@@ -1059,7 +1080,7 @@ public class LuaValue extends Varargs {
|
||||
* @param expected String naming the type that was expected
|
||||
* @throws LuaError in all cases
|
||||
*/
|
||||
protected LuaValue argerror(String expected) { throw new LuaError("bad argument ("+expected+" expected, got "+typename()+")"); }
|
||||
protected LuaValue argerror(String expected) { throw new LuaError("bad argument: "+expected+" expected, got "+typename()); }
|
||||
|
||||
/**
|
||||
* Throw a {@link LuaError} indicating an invalid argument was supplied to a function
|
||||
@@ -2013,6 +2034,13 @@ public class LuaValue extends Varargs {
|
||||
* @throws LuaError if {@code this} is not a table or string, and has no {@link #UNM} metatag
|
||||
*/
|
||||
public LuaValue neg() { return checkmetatag(UNM, "attempt to perform arithmetic on ").call(this); }
|
||||
|
||||
/** Unary bitwise not: return bitwise inverse value {@code (~this)}.
|
||||
* @return numeric inverse as {@link LuaNumber} if integer-coercible,
|
||||
* or metatag processing result if {@link #BNOT} metatag is defined
|
||||
* @throws LuaError if {@code this} cannot be represented as an integer
|
||||
*/
|
||||
public LuaValue bnot() { return checkmetatag(BNOT, "attempt to perform bitwise operation on ").call(this); }
|
||||
|
||||
/** Length operator: return lua length of object {@code (#this)} including metatag processing as java int
|
||||
* @return length as defined by the lua # operator
|
||||
@@ -2144,6 +2172,15 @@ public class LuaValue extends Varargs {
|
||||
*/
|
||||
public boolean raweq( int val ) { return false; }
|
||||
|
||||
/** Equals: Perform direct equality comparison with a long value
|
||||
* without metatag processing.
|
||||
* @param val The long value to compare with.
|
||||
* @return true if {@code this} is a {@link LuaNumber}
|
||||
* whose value equals val,
|
||||
* otherwise false
|
||||
*/
|
||||
public boolean raweq( long val ) { return false; }
|
||||
|
||||
/** Perform equality testing metatag processing
|
||||
* @param lhs left-hand-side of equality expression
|
||||
* @param lhsmt metatag value for left-hand-side
|
||||
@@ -2404,6 +2441,18 @@ public class LuaValue extends Varargs {
|
||||
* @see #arithmt(LuaValue, LuaValue)
|
||||
*/
|
||||
public LuaValue div( LuaValue rhs ) { return arithmt(DIV,rhs); }
|
||||
|
||||
public LuaValue idiv( LuaValue rhs ) { return arithmt(IDIV,rhs); }
|
||||
|
||||
public LuaValue band( LuaValue rhs ) { return arithmt(BAND,rhs); }
|
||||
|
||||
public LuaValue bor( LuaValue rhs ) { return arithmt(BOR,rhs); }
|
||||
|
||||
public LuaValue bxor( LuaValue rhs ) { return arithmt(BXOR,rhs); }
|
||||
|
||||
public LuaValue shl( LuaValue rhs ) { return arithmt(SHL,rhs); }
|
||||
|
||||
public LuaValue shr( LuaValue rhs ) { return arithmt(SHR,rhs); }
|
||||
|
||||
/** Divide: Perform numeric divide operation by another value
|
||||
* of double type without metatag processing
|
||||
@@ -2419,6 +2468,18 @@ public class LuaValue extends Varargs {
|
||||
* @see #div(LuaValue)
|
||||
*/
|
||||
public LuaValue div( double rhs ) { return aritherror("div"); }
|
||||
|
||||
public LuaValue idiv( double rhs ) { return aritherror("idiv"); }
|
||||
|
||||
public LuaValue band( double rhs ) { return aritherror("band"); }
|
||||
|
||||
public LuaValue bor( double rhs ) { return aritherror("bor"); }
|
||||
|
||||
public LuaValue bxor( double rhs ) { return aritherror("bxor"); }
|
||||
|
||||
public LuaValue shl( double rhs ) { return aritherror("shl"); }
|
||||
|
||||
public LuaValue shr( double rhs ) { return aritherror("shr"); }
|
||||
|
||||
/** Divide: Perform numeric divide operation by another value
|
||||
* of int type without metatag processing
|
||||
@@ -2434,6 +2495,18 @@ public class LuaValue extends Varargs {
|
||||
* @see #div(LuaValue)
|
||||
*/
|
||||
public LuaValue div( int rhs ) { return aritherror("div"); }
|
||||
|
||||
public LuaValue idiv( int rhs ) { return aritherror("idiv"); }
|
||||
|
||||
public LuaValue band( int rhs ) { return aritherror("band"); }
|
||||
|
||||
public LuaValue bor( int rhs ) { return aritherror("bor"); }
|
||||
|
||||
public LuaValue bxor( int rhs ) { return aritherror("bxor"); }
|
||||
|
||||
public LuaValue shl( int rhs ) { return aritherror("shl"); }
|
||||
|
||||
public LuaValue shr( int rhs ) { return aritherror("shr"); }
|
||||
|
||||
/** Reverse-divide: Perform numeric divide operation into another value
|
||||
* with metatag processing
|
||||
@@ -2449,6 +2522,18 @@ public class LuaValue extends Varargs {
|
||||
* @see #div(int)
|
||||
*/
|
||||
public LuaValue divInto(double lhs) { return arithmtwith(DIV,lhs); }
|
||||
|
||||
public LuaValue idivInto(double lhs) { return arithmtwith(IDIV,lhs); }
|
||||
|
||||
public LuaValue bandInto(double lhs) { return arithmtwith(BAND,lhs); }
|
||||
|
||||
public LuaValue borInto(double lhs) { return arithmtwith(BOR,lhs); }
|
||||
|
||||
public LuaValue bxorInto(double lhs) { return arithmtwith(BXOR,lhs); }
|
||||
|
||||
public LuaValue shlInto(double lhs) { return arithmtwith(SHL,lhs); }
|
||||
|
||||
public LuaValue shrInto(double lhs) { return arithmtwith(SHR,lhs); }
|
||||
|
||||
/** Modulo: Perform numeric modulo operation with another value
|
||||
* of unknown type,
|
||||
@@ -2991,7 +3076,7 @@ public class LuaValue extends Varargs {
|
||||
return h.call(this, op1);
|
||||
if (LuaValue.LE.raweq(tag) && (!(h = metatag(LT)).isnil() || !(h = op1.metatag(LT)).isnil()))
|
||||
return h.call(op1, this).not();
|
||||
return error("bad argument: attempt to compare "+tag+" on "+typename()+" and "+op1.typename());
|
||||
return error("attempt to compare "+tag+" on "+typename()+" and "+op1.typename());
|
||||
}
|
||||
|
||||
/** Perform string comparison with another value
|
||||
@@ -3168,6 +3253,13 @@ public class LuaValue extends Varargs {
|
||||
* @return {@link LuaInteger} instance, possibly pooled, whose value is i
|
||||
*/
|
||||
public static LuaInteger valueOf(int i) { return LuaInteger.valueOf(i); }
|
||||
|
||||
/** Convert java long to a {@link LuaValue}.
|
||||
*
|
||||
* @param l long value to convert
|
||||
* @return {@link LuaInteger} instance, possibly pooled, whose value is l
|
||||
*/
|
||||
public static LuaInteger valueOf(long l) { return LuaInteger.valueOf(l); }
|
||||
|
||||
/** Convert java double to a {@link LuaValue}.
|
||||
* This may return a {@link LuaInteger} or {@link LuaDouble} depending
|
||||
@@ -3408,8 +3500,8 @@ public class LuaValue extends Varargs {
|
||||
switch ( v.length ) {
|
||||
case 0: return NONE;
|
||||
case 1: return v[0];
|
||||
case 2: return new Varargs.PairVarargs(v[0],v[1]);
|
||||
default: return new Varargs.ArrayVarargs(v,NONE);
|
||||
case 2: return new PairVarargs(v[0],v[1]);
|
||||
default: return new ArrayVarargs(v,NONE);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3425,12 +3517,12 @@ public class LuaValue extends Varargs {
|
||||
switch ( v.length ) {
|
||||
case 0: return r;
|
||||
case 1: return r.narg()>0?
|
||||
(Varargs) new Varargs.PairVarargs(v[0],r):
|
||||
(Varargs) new PairVarargs(v[0],r):
|
||||
(Varargs) v[0];
|
||||
case 2: return r.narg()>0?
|
||||
(Varargs) new Varargs.ArrayVarargs(v,r):
|
||||
(Varargs) new Varargs.PairVarargs(v[0],v[1]);
|
||||
default: return new Varargs.ArrayVarargs(v,r);
|
||||
(Varargs) new ArrayVarargs(v,r):
|
||||
(Varargs) new PairVarargs(v[0],v[1]);
|
||||
default: return new ArrayVarargs(v,r);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3447,8 +3539,8 @@ public class LuaValue extends Varargs {
|
||||
switch ( length ) {
|
||||
case 0: return NONE;
|
||||
case 1: return v[offset];
|
||||
case 2: return new Varargs.PairVarargs(v[offset+0],v[offset+1]);
|
||||
default: return new Varargs.ArrayPartVarargs(v, offset, length, NONE);
|
||||
case 2: return new PairVarargs(v[offset+0],v[offset+1]);
|
||||
default: return new ArrayPartVarargs(v, offset, length, NONE);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3469,12 +3561,12 @@ public class LuaValue extends Varargs {
|
||||
switch ( length ) {
|
||||
case 0: return more;
|
||||
case 1: return more.narg()>0?
|
||||
(Varargs) new Varargs.PairVarargs(v[offset],more):
|
||||
(Varargs) new PairVarargs(v[offset],more):
|
||||
(Varargs) v[offset];
|
||||
case 2: return more.narg()>0?
|
||||
(Varargs) new Varargs.ArrayPartVarargs(v,offset,length,more):
|
||||
(Varargs) new Varargs.PairVarargs(v[offset],v[offset+1]);
|
||||
default: return new Varargs.ArrayPartVarargs(v,offset,length,more);
|
||||
(Varargs) new ArrayPartVarargs(v,offset,length,more):
|
||||
(Varargs) new PairVarargs(v[offset],v[offset+1]);
|
||||
default: return new ArrayPartVarargs(v,offset,length,more);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3491,7 +3583,7 @@ public class LuaValue extends Varargs {
|
||||
public static Varargs varargsOf(LuaValue v, Varargs r) {
|
||||
switch ( r.narg() ) {
|
||||
case 0: return v;
|
||||
default: return new Varargs.PairVarargs(v,r);
|
||||
default: return new PairVarargs(v,r);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3508,8 +3600,8 @@ public class LuaValue extends Varargs {
|
||||
*/
|
||||
public static Varargs varargsOf(LuaValue v1,LuaValue v2,Varargs v3) {
|
||||
switch ( v3.narg() ) {
|
||||
case 0: return new Varargs.PairVarargs(v1,v2);
|
||||
default: return new Varargs.ArrayPartVarargs(new LuaValue[]{v1,v2}, 0, 2, v3);
|
||||
case 0: return new PairVarargs(v1,v2);
|
||||
default: return new ArrayPartVarargs(new LuaValue[]{v1,v2}, 0, 2, v3);
|
||||
}
|
||||
}
|
||||
|
||||
BIN
core/src/main/java/org/luaj/vm2/Metatable.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Metatable.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -29,23 +29,23 @@ import org.luaj.vm2.LuaTable.Slot;
|
||||
interface Metatable {
|
||||
|
||||
/** Return whether or not this table's keys are weak. */
|
||||
boolean useWeakKeys();
|
||||
public boolean useWeakKeys();
|
||||
|
||||
/** Return whether or not this table's values are weak. */
|
||||
boolean useWeakValues();
|
||||
public boolean useWeakValues();
|
||||
|
||||
/** Return this metatable as a LuaValue. */
|
||||
LuaValue toLuaValue();
|
||||
public LuaValue toLuaValue();
|
||||
|
||||
/** Return an instance of Slot appropriate for the given key and value. */
|
||||
Slot entry(LuaValue key, LuaValue value);
|
||||
public Slot entry( LuaValue key, LuaValue value );
|
||||
|
||||
/** Returns the given value wrapped in a weak reference if appropriate. */
|
||||
LuaValue wrap(LuaValue value);
|
||||
public LuaValue wrap( LuaValue value );
|
||||
|
||||
/**
|
||||
* Returns the value at the given index in the array, or null if it is a
|
||||
* weak reference that has been dropped.
|
||||
* Returns the value at the given index in the array, or null if it is a weak reference that
|
||||
* has been dropped.
|
||||
*/
|
||||
LuaValue arrayget(LuaValue[] array, int index);
|
||||
public LuaValue arrayget(LuaValue[] array, int index);
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/NonTableMetatable.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/NonTableMetatable.class
Normal file
Binary file not shown.
@@ -10,32 +10,26 @@ class NonTableMetatable implements Metatable {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean useWeakKeys() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean useWeakValues() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue toLuaValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot entry(LuaValue key, LuaValue value) {
|
||||
return LuaTable.defaultEntry(key, value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue wrap(LuaValue value) {
|
||||
return value;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue arrayget(LuaValue[] array, int index) {
|
||||
return array[index];
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/OrphanedThread.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/OrphanedThread.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -22,15 +22,14 @@
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* {@link java.lang.Error} sublcass that indicates a lua thread that is no
|
||||
* {@link Error} sublcass that indicates a lua thread that is no
|
||||
* longer referenced has been detected.
|
||||
* <p>
|
||||
* The java thread in which this is thrown should correspond to a
|
||||
* {@link LuaThread} being used as a coroutine that could not possibly be
|
||||
* resumed again because there are no more references to the LuaThread with
|
||||
* which it is associated. Rather than locking up resources forever, this error
|
||||
* is thrown, and should fall through all the way to the thread's
|
||||
* {@link Thread#run()} method.
|
||||
* is thrown, and should fall through all the way to the thread's {@link Thread#run()} method.
|
||||
* <p>
|
||||
* Java code mixed with the luaj vm should not catch this error because it may
|
||||
* occur when the coroutine is not running, so any processing done during error
|
||||
BIN
core/src/main/java/org/luaj/vm2/Print.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Print.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -25,96 +25,131 @@ import java.io.ByteArrayOutputStream;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* Debug helper class to pretty-print lua bytecodes.
|
||||
*
|
||||
* Debug helper class to pretty-print lua bytecodes.
|
||||
* @see Prototype
|
||||
* @see LuaClosure
|
||||
* @see LuaClosure
|
||||
*/
|
||||
public class Print extends Lua {
|
||||
|
||||
/** opcode names */
|
||||
private static final String STRING_FOR_NULL = "null";
|
||||
public static PrintStream ps = System.out;
|
||||
public static PrintStream ps = System.out;
|
||||
|
||||
/** String names for each lua opcode value. */
|
||||
public static final String[] OPNAMES = { "MOVE", "LOADK", "LOADKX", "LOADBOOL", "LOADNIL", "GETUPVAL", "GETTABUP",
|
||||
"GETTABLE", "SETTABUP", "SETUPVAL", "SETTABLE", "NEWTABLE", "SELF", "ADD", "SUB", "MUL", "DIV", "MOD",
|
||||
"POW", "UNM", "NOT", "LEN", "CONCAT", "JMP", "EQ", "LT", "LE", "TEST", "TESTSET", "CALL", "TAILCALL",
|
||||
"RETURN", "FORLOOP", "FORPREP", "TFORCALL", "TFORLOOP", "SETLIST", "CLOSURE", "VARARG", "EXTRAARG", null, };
|
||||
public static final String[] OPNAMES = {
|
||||
"MOVE",
|
||||
"LOADK",
|
||||
"LOADKX",
|
||||
"LOADBOOL",
|
||||
"LOADNIL",
|
||||
"GETUPVAL",
|
||||
"GETTABUP",
|
||||
"GETTABLE",
|
||||
"SETTABUP",
|
||||
"SETUPVAL",
|
||||
"SETTABLE",
|
||||
"NEWTABLE",
|
||||
"SELF",
|
||||
"ADD",
|
||||
"SUB",
|
||||
"MUL",
|
||||
"DIV",
|
||||
"MOD",
|
||||
"POW",
|
||||
"UNM",
|
||||
"NOT",
|
||||
"LEN",
|
||||
"CONCAT",
|
||||
"JMP",
|
||||
"EQ",
|
||||
"LT",
|
||||
"LE",
|
||||
"TEST",
|
||||
"TESTSET",
|
||||
"CALL",
|
||||
"TAILCALL",
|
||||
"RETURN",
|
||||
"FORLOOP",
|
||||
"FORPREP",
|
||||
"TFORCALL",
|
||||
"TFORLOOP",
|
||||
"SETLIST",
|
||||
"CLOSURE",
|
||||
"VARARG",
|
||||
"EXTRAARG",
|
||||
null,
|
||||
};
|
||||
|
||||
|
||||
static void printString(PrintStream ps, final LuaString s) {
|
||||
|
||||
|
||||
ps.print('"');
|
||||
for (int i = 0, n = s.m_length; i < n; i++) {
|
||||
int c = s.m_bytes[s.m_offset+i];
|
||||
if (c >= ' ' && c <= '~' && c != '\"' && c != '\\')
|
||||
if ( c >= ' ' && c <= '~' && c != '\"' && c != '\\' )
|
||||
ps.print((char) c);
|
||||
else {
|
||||
switch (c) {
|
||||
case '"':
|
||||
ps.print("\\\"");
|
||||
break;
|
||||
case '\\':
|
||||
ps.print("\\\\");
|
||||
break;
|
||||
case 0x0007: /* bell */
|
||||
ps.print("\\a");
|
||||
break;
|
||||
case '\b': /* backspace */
|
||||
ps.print("\\b");
|
||||
break;
|
||||
case '\f': /* form feed */
|
||||
ps.print("\\f");
|
||||
break;
|
||||
case '\t': /* tab */
|
||||
ps.print("\\t");
|
||||
break;
|
||||
case '\r': /* carriage return */
|
||||
ps.print("\\r");
|
||||
break;
|
||||
case '\n': /* newline */
|
||||
ps.print("\\n");
|
||||
break;
|
||||
case 0x000B: /* vertical tab */
|
||||
ps.print("\\v");
|
||||
break;
|
||||
default:
|
||||
ps.print('\\');
|
||||
ps.print(Integer.toString(1000+0xff & c).substring(1));
|
||||
break;
|
||||
case '"':
|
||||
ps.print("\\\"");
|
||||
break;
|
||||
case '\\':
|
||||
ps.print("\\\\");
|
||||
break;
|
||||
case 0x0007: /* bell */
|
||||
ps.print("\\a");
|
||||
break;
|
||||
case '\b': /* backspace */
|
||||
ps.print("\\b");
|
||||
break;
|
||||
case '\f': /* form feed */
|
||||
ps.print("\\f");
|
||||
break;
|
||||
case '\t': /* tab */
|
||||
ps.print("\\t");
|
||||
break;
|
||||
case '\r': /* carriage return */
|
||||
ps.print("\\r");
|
||||
break;
|
||||
case '\n': /* newline */
|
||||
ps.print("\\n");
|
||||
break;
|
||||
case 0x000B: /* vertical tab */
|
||||
ps.print("\\v");
|
||||
break;
|
||||
default:
|
||||
ps.print('\\');
|
||||
ps.print(Integer.toString(1000 + 0xff&c).substring(1));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
ps.print('"');
|
||||
}
|
||||
|
||||
static void printValue(PrintStream ps, LuaValue v) {
|
||||
static void printValue( PrintStream ps, LuaValue v ) {
|
||||
if (v == null) {
|
||||
ps.print("null");
|
||||
return;
|
||||
}
|
||||
switch (v.type()) {
|
||||
case LuaValue.TSTRING:
|
||||
printString(ps, (LuaString) v);
|
||||
break;
|
||||
default:
|
||||
ps.print(v.tojstring());
|
||||
|
||||
switch ( v.type() ) {
|
||||
case LuaValue.TSTRING: printString( ps, (LuaString) v ); break;
|
||||
default: ps.print( v.tojstring() );
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void printConstant(PrintStream ps, Prototype f, int i) {
|
||||
printValue(ps, i < f.k.length? f.k[i]: LuaValue.valueOf("UNKNOWN_CONST_" + i));
|
||||
printValue( ps, i < f.k.length ? f.k[i] : LuaValue.valueOf("UNKNOWN_CONST_" + i) );
|
||||
}
|
||||
|
||||
static void printUpvalue(PrintStream ps, Upvaldesc u) {
|
||||
ps.print(u.idx + " ");
|
||||
printValue(ps, u.name);
|
||||
ps.print( u.idx + " " );
|
||||
printValue( ps, u.name );
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Print the code in a prototype
|
||||
*
|
||||
* @param f the {@link Prototype}
|
||||
*/
|
||||
public static void printCode(Prototype f) {
|
||||
@@ -126,22 +161,20 @@ public class Print extends Lua {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Print an opcode in a prototype
|
||||
*
|
||||
* @param f the {@link Prototype}
|
||||
* @param f the {@link Prototype}
|
||||
* @param pc the program counter to look up and print
|
||||
* @return pc same as above or changed
|
||||
*/
|
||||
public static int printOpCode(Prototype f, int pc) {
|
||||
return printOpCode(ps, f, pc);
|
||||
return printOpCode(ps,f,pc);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Print an opcode in a prototype
|
||||
*
|
||||
* @param ps the {@link PrintStream} to print to
|
||||
* @param f the {@link Prototype}
|
||||
* @param f the {@link Prototype}
|
||||
* @param pc the program counter to look up and print
|
||||
* @return pc same as above or changed
|
||||
*/
|
||||
@@ -155,33 +188,33 @@ public class Print extends Lua {
|
||||
int bx = GETARG_Bx(i);
|
||||
int sbx = GETARG_sBx(i);
|
||||
int line = getline(f, pc);
|
||||
ps.print(" " + (pc+1) + " ");
|
||||
ps.print(" " + (pc + 1) + " ");
|
||||
if (line > 0)
|
||||
ps.print("[" + line + "] ");
|
||||
else
|
||||
ps.print("[-] ");
|
||||
if (o >= OPNAMES.length-1) {
|
||||
if (o >= OPNAMES.length - 1) {
|
||||
ps.print("UNKNOWN_OP_" + o + " ");
|
||||
} else {
|
||||
ps.print(OPNAMES[o] + " ");
|
||||
switch (getOpMode(o)) {
|
||||
case iABC:
|
||||
ps.print(a);
|
||||
ps.print( a );
|
||||
if (getBMode(o) != OpArgN)
|
||||
ps.print(" " + (ISK(b)? -1-INDEXK(b): b));
|
||||
ps.print(" "+(ISK(b) ? (-1 - INDEXK(b)) : b));
|
||||
if (getCMode(o) != OpArgN)
|
||||
ps.print(" " + (ISK(c)? -1-INDEXK(c): c));
|
||||
ps.print(" "+(ISK(c) ? (-1 - INDEXK(c)) : c));
|
||||
break;
|
||||
case iABx:
|
||||
if (getBMode(o) == OpArgK) {
|
||||
ps.print(a + " " + (-1-bx));
|
||||
ps.print(a + " " + (-1 - bx));
|
||||
} else {
|
||||
ps.print(a + " " + bx);
|
||||
ps.print(a + " " + (bx));
|
||||
}
|
||||
break;
|
||||
case iAsBx:
|
||||
if (o == OP_JMP)
|
||||
ps.print(sbx);
|
||||
ps.print( sbx );
|
||||
else
|
||||
ps.print(a + " " + sbx);
|
||||
break;
|
||||
@@ -198,7 +231,7 @@ public class Print extends Lua {
|
||||
printUpvalue(ps, f.upvalues[b]);
|
||||
} else {
|
||||
ps.print("UNKNOWN_UPVALUE_" + b);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case OP_GETTABUP:
|
||||
ps.print(" ; ");
|
||||
@@ -243,6 +276,12 @@ public class Print extends Lua {
|
||||
case OP_SUB:
|
||||
case OP_MUL:
|
||||
case OP_DIV:
|
||||
case OP_IDIV:
|
||||
case OP_BAND:
|
||||
case OP_BOR:
|
||||
case OP_BXOR:
|
||||
case OP_SHL:
|
||||
case OP_SHR:
|
||||
case OP_POW:
|
||||
case OP_EQ:
|
||||
case OP_LT:
|
||||
@@ -263,7 +302,7 @@ public class Print extends Lua {
|
||||
case OP_JMP:
|
||||
case OP_FORLOOP:
|
||||
case OP_FORPREP:
|
||||
ps.print(" ; to " + (sbx+pc+2));
|
||||
ps.print(" ; to " + (sbx + pc + 2));
|
||||
break;
|
||||
case OP_CLOSURE:
|
||||
if (bx < f.p.length) {
|
||||
@@ -274,13 +313,13 @@ public class Print extends Lua {
|
||||
break;
|
||||
case OP_SETLIST:
|
||||
if (c == 0)
|
||||
ps.print(" ; " + code[++pc] + " (stored in the next OP)");
|
||||
ps.print(" ; " + ((int) code[++pc]) + " (stored in the next OP)");
|
||||
else
|
||||
ps.print(" ; " + c);
|
||||
ps.print(" ; " + ((int) c));
|
||||
break;
|
||||
case OP_VARARG:
|
||||
ps.print(" ; is_vararg=" + f.is_vararg);
|
||||
break;
|
||||
ps.print( " ; is_vararg="+ f.is_vararg );
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -289,7 +328,7 @@ public class Print extends Lua {
|
||||
}
|
||||
|
||||
private static int getline(Prototype f, int pc) {
|
||||
return pc > 0 && f.lineinfo != null && pc < f.lineinfo.length? f.lineinfo[pc]: -1;
|
||||
return pc>0 && f.lineinfo!=null && pc<f.lineinfo.length? f.lineinfo[pc]: -1;
|
||||
}
|
||||
|
||||
static void printHeader(Prototype f) {
|
||||
@@ -300,20 +339,23 @@ public class Print extends Lua {
|
||||
s = "(bstring)";
|
||||
else
|
||||
s = "(string)";
|
||||
String a = f.linedefined == 0? "main": "function";
|
||||
ps.print("\n%" + a + " <" + s + ":" + f.linedefined + "," + f.lastlinedefined + "> (" + f.code.length
|
||||
+ " instructions, " + f.code.length*4 + " bytes at " + id(f) + ")\n");
|
||||
ps.print(f.numparams + " param, " + f.maxstacksize + " slot, " + f.upvalues.length + " upvalue, ");
|
||||
ps.print(f.locvars.length + " local, " + f.k.length + " constant, " + f.p.length + " function\n");
|
||||
String a = (f.linedefined == 0) ? "main" : "function";
|
||||
ps.print("\n%" + a + " <" + s + ":" + f.linedefined + ","
|
||||
+ f.lastlinedefined + "> (" + f.code.length + " instructions, "
|
||||
+ f.code.length * 4 + " bytes at " + id(f) + ")\n");
|
||||
ps.print(f.numparams + " param, " + f.maxstacksize + " slot, "
|
||||
+ f.upvalues.length + " upvalue, ");
|
||||
ps.print(f.locvars.length + " local, " + f.k.length
|
||||
+ " constant, " + f.p.length + " function\n");
|
||||
}
|
||||
|
||||
static void printConstants(Prototype f) {
|
||||
int i, n = f.k.length;
|
||||
ps.print("constants (" + n + ") for " + id(f) + ":\n");
|
||||
for (i = 0; i < n; i++) {
|
||||
ps.print(" " + (i+1) + " ");
|
||||
printValue(ps, f.k[i]);
|
||||
ps.print("\n");
|
||||
ps.print(" " + (i + 1) + " ");
|
||||
printValue( ps, f.k[i] );
|
||||
ps.print( "\n");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -321,8 +363,7 @@ public class Print extends Lua {
|
||||
int i, n = f.locvars.length;
|
||||
ps.print("locals (" + n + ") for " + id(f) + ":\n");
|
||||
for (i = 0; i < n; i++) {
|
||||
ps.println(
|
||||
" " + i + " " + f.locvars[i].varname + " " + (f.locvars[i].startpc+1) + " " + (f.locvars[i].endpc+1));
|
||||
ps.println(" "+i+" "+f.locvars[i].varname+" "+(f.locvars[i].startpc+1)+" "+(f.locvars[i].endpc+1));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -334,20 +375,18 @@ public class Print extends Lua {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Pretty-prints contents of a Prototype.
|
||||
*
|
||||
/** Pretty-prints contents of a Prototype.
|
||||
*
|
||||
* @param prototype Prototype to print.
|
||||
*/
|
||||
public static void print(Prototype prototype) {
|
||||
printFunction(prototype, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Pretty-prints contents of a Prototype in short or long form.
|
||||
*
|
||||
|
||||
/** Pretty-prints contents of a Prototype in short or long form.
|
||||
*
|
||||
* @param prototype Prototype to print.
|
||||
* @param full true to print all fields, false to print short form.
|
||||
* @param full true to print all fields, false to print short form.
|
||||
*/
|
||||
public static void printFunction(Prototype prototype, boolean full) {
|
||||
int i, n = prototype.p.length;
|
||||
@@ -362,45 +401,43 @@ public class Print extends Lua {
|
||||
printFunction(prototype.p[i], full);
|
||||
}
|
||||
|
||||
private static void format(String s, int maxcols) {
|
||||
private static void format( String s, int maxcols ) {
|
||||
int n = s.length();
|
||||
if (n > maxcols)
|
||||
ps.print(s.substring(0, maxcols));
|
||||
if ( n > maxcols )
|
||||
ps.print( s.substring(0,maxcols) );
|
||||
else {
|
||||
ps.print(s);
|
||||
for (int i = maxcols-n; --i >= 0;)
|
||||
ps.print(' ');
|
||||
ps.print( s );
|
||||
for ( int i=maxcols-n; --i>=0; )
|
||||
ps.print( ' ' );
|
||||
}
|
||||
}
|
||||
|
||||
private static String id(Prototype f) {
|
||||
return "Proto";
|
||||
}
|
||||
|
||||
private void _assert(boolean b) {
|
||||
if (!b)
|
||||
if ( !b )
|
||||
throw new NullPointerException("_assert failed");
|
||||
}
|
||||
|
||||
/**
|
||||
* Print the state of a {@link LuaClosure} that is being executed
|
||||
*
|
||||
* @param cl the {@link LuaClosure}
|
||||
* @param pc the program counter
|
||||
* @param stack the stack of {@link LuaValue}
|
||||
* @param top the top of the stack
|
||||
* @param cl the {@link LuaClosure}
|
||||
* @param pc the program counter
|
||||
* @param stack the stack of {@link LuaValue}
|
||||
* @param top the top of the stack
|
||||
* @param varargs any {@link Varargs} value that may apply
|
||||
*/
|
||||
public static void printState(LuaClosure cl, int pc, LuaValue[] stack, int top, Varargs varargs) {
|
||||
// print opcode into buffer
|
||||
PrintStream previous = ps;
|
||||
ByteArrayOutputStream baos = new ByteArrayOutputStream();
|
||||
ps = new PrintStream(baos);
|
||||
printOpCode(cl.p, pc);
|
||||
ps = new PrintStream( baos );
|
||||
printOpCode( cl.p, pc );
|
||||
ps.flush();
|
||||
ps.close();
|
||||
ps = previous;
|
||||
format(baos.toString(), 50);
|
||||
format( baos.toString(), 50 );
|
||||
printStack(stack, top, varargs);
|
||||
ps.println();
|
||||
}
|
||||
@@ -408,38 +445,38 @@ public class Print extends Lua {
|
||||
public static void printStack(LuaValue[] stack, int top, Varargs varargs) {
|
||||
// print stack
|
||||
ps.print('[');
|
||||
for (int i = 0; i < stack.length; i++) {
|
||||
for ( int i=0; i<stack.length; i++ ) {
|
||||
LuaValue v = stack[i];
|
||||
if (v == null)
|
||||
if ( v == null )
|
||||
ps.print(STRING_FOR_NULL);
|
||||
else
|
||||
switch (v.type()) {
|
||||
case LuaValue.TSTRING:
|
||||
LuaString s = v.checkstring();
|
||||
ps.print(s.length() < 48? s.tojstring()
|
||||
: s.substring(0, 32).tojstring() + "...+" + (s.length()-32) + "b");
|
||||
break;
|
||||
case LuaValue.TFUNCTION:
|
||||
ps.print(v.tojstring());
|
||||
break;
|
||||
case LuaValue.TUSERDATA:
|
||||
Object o = v.touserdata();
|
||||
if (o != null) {
|
||||
String n = o.getClass().getName();
|
||||
n = n.substring(n.lastIndexOf('.')+1);
|
||||
ps.print(n + ": " + Integer.toHexString(o.hashCode()));
|
||||
} else {
|
||||
ps.print(v.toString());
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ps.print(v.tojstring());
|
||||
else switch ( v.type() ) {
|
||||
case LuaValue.TSTRING:
|
||||
LuaString s = v.checkstring();
|
||||
ps.print( s.length() < 48?
|
||||
s.tojstring():
|
||||
s.substring(0, 32).tojstring()+"...+"+(s.length()-32)+"b");
|
||||
break;
|
||||
case LuaValue.TFUNCTION:
|
||||
ps.print( v.tojstring() );
|
||||
break;
|
||||
case LuaValue.TUSERDATA:
|
||||
Object o = v.touserdata();
|
||||
if ( o != null ) {
|
||||
String n = o.getClass().getName();
|
||||
n = n.substring(n.lastIndexOf('.')+1);
|
||||
ps.print( n+": "+Integer.toHexString(o.hashCode()) );
|
||||
} else {
|
||||
ps.print( v.toString() );
|
||||
}
|
||||
if (i+1 == top)
|
||||
break;
|
||||
default:
|
||||
ps.print(v.tojstring());
|
||||
}
|
||||
if ( i+1 == top )
|
||||
ps.print(']');
|
||||
ps.print(" | ");
|
||||
ps.print( " | " );
|
||||
}
|
||||
ps.print(varargs);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/Prototype.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Prototype.class
Normal file
Binary file not shown.
146
core/src/main/java/org/luaj/vm2/Prototype.java
Normal file
146
core/src/main/java/org/luaj/vm2/Prototype.java
Normal file
@@ -0,0 +1,146 @@
|
||||
/*******************************************************************************
|
||||
* Copyright (c) 2009-2011 Luaj.org. All rights reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Prototype representing compiled lua code.
|
||||
*
|
||||
* <p>
|
||||
* This is both a straight translation of the corresponding C type,
|
||||
* and the main data structure for execution of compiled lua bytecode.
|
||||
*
|
||||
* <p>
|
||||
* Generally, the {@link Prototype} is not constructed directly is an intermediate result
|
||||
* as lua code is loaded using {@link Globals#load(java.io.Reader, String)}:
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* globals.load( new StringReader("print 'hello'"), "main.lua" ).call();
|
||||
* } </pre>
|
||||
*
|
||||
* <p>
|
||||
* To create a {@link Prototype} directly, a compiler such as
|
||||
* {@link org.luaj.vm2.compiler.LuaC} may be used:
|
||||
* <pre> {@code
|
||||
* InputStream is = new ByteArrayInputStream("print('hello,world')".getBytes());
|
||||
* Prototype p = LuaC.instance.compile(is, "script");
|
||||
* }</pre>
|
||||
*
|
||||
* To simplify loading, the {@link Globals#compilePrototype(java.io.InputStream, String)} method may be used:
|
||||
* <pre> {@code
|
||||
* Prototype p = globals.compileProtoytpe(is, "script");
|
||||
* }</pre>
|
||||
*
|
||||
* It may also be loaded from a {@link java.io.Reader} via {@link Globals#compilePrototype(java.io.Reader, String)}:
|
||||
* <pre> {@code
|
||||
* Prototype p = globals.compileProtoytpe(new StringReader(script), "script");
|
||||
* }</pre>
|
||||
*
|
||||
* To un-dump a binary file known to be a binary lua file that has been dumped to a string,
|
||||
* the {@link Globals.Undumper} interface may be used:
|
||||
* <pre> {@code
|
||||
* FileInputStream lua_binary_file = new FileInputStream("foo.lc"); // Known to be compiled lua.
|
||||
* Prototype p = globals.undumper.undump(lua_binary_file, "foo.lua");
|
||||
* }</pre>
|
||||
*
|
||||
* To execute the code represented by the {@link Prototype} it must be supplied to
|
||||
* the constructor of a {@link LuaClosure}:
|
||||
* <pre> {@code
|
||||
* Globals globals = JsePlatform.standardGlobals();
|
||||
* LuaClosure f = new LuaClosure(p, globals);
|
||||
* f.call();
|
||||
* }</pre>
|
||||
*
|
||||
* To simplify the debugging of prototype values, the contents may be printed using {@link Print#print}:
|
||||
* <pre> {@code
|
||||
* Print.print(p);
|
||||
* }</pre>
|
||||
* <p>
|
||||
*
|
||||
* @see LuaClosure
|
||||
* @see Globals
|
||||
* @see Globals#undumper
|
||||
* @see Globals#compiler
|
||||
* @see Print#print
|
||||
*/
|
||||
|
||||
public class Prototype {
|
||||
/* constants used by the function */
|
||||
public LuaValue[] k;
|
||||
public int[] code;
|
||||
/* functions defined inside the function */
|
||||
public Prototype[] p;
|
||||
/* map from opcodes to source lines */
|
||||
public int[] lineinfo;
|
||||
/* information about local variables */
|
||||
public LocVars[] locvars;
|
||||
/* upvalue information */
|
||||
public Upvaldesc[] upvalues;
|
||||
public LuaString source;
|
||||
public int linedefined;
|
||||
public int lastlinedefined;
|
||||
public int numparams;
|
||||
public int is_vararg;
|
||||
public int maxstacksize;
|
||||
private static final Upvaldesc[] NOUPVALUES = {};
|
||||
private static final Prototype[] NOSUBPROTOS = {};
|
||||
|
||||
public Prototype() {
|
||||
p = NOSUBPROTOS;
|
||||
upvalues = NOUPVALUES;
|
||||
}
|
||||
|
||||
public Prototype(int n_upvalues) {
|
||||
p = NOSUBPROTOS;
|
||||
upvalues = new Upvaldesc[n_upvalues];
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return source + ":" + linedefined+"-"+lastlinedefined;
|
||||
}
|
||||
|
||||
/** Get the name of a local variable.
|
||||
*
|
||||
* @param number the local variable number to look up
|
||||
* @param pc the program counter
|
||||
* @return the name, or null if not found
|
||||
*/
|
||||
public LuaString getlocalname(int number, int pc) {
|
||||
int i;
|
||||
for (i = 0; i<locvars.length && locvars[i].startpc <= pc; i++) {
|
||||
if (pc < locvars[i].endpc) { /* is variable active? */
|
||||
number--;
|
||||
if (number == 0)
|
||||
return locvars[i].varname;
|
||||
}
|
||||
}
|
||||
return null; /* not found */
|
||||
}
|
||||
|
||||
public String shortsource() {
|
||||
String name = source.tojstring();
|
||||
if ( name.startsWith("@") || name.startsWith("=") )
|
||||
name = name.substring(1);
|
||||
else if ( name.startsWith("\033") )
|
||||
name = "binary string";
|
||||
return name;
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/TailcallVarargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/TailcallVarargs.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -22,43 +22,44 @@
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Subclass of {@link Varargs} that represents a lua tail call in a Java library
|
||||
* function execution environment.
|
||||
* Subclass of {@link Varargs} that represents a lua tail call
|
||||
* in a Java library function execution environment.
|
||||
* <p>
|
||||
* Since Java doesn't have direct support for tail calls, any lua function whose
|
||||
* {@link Prototype} contains the {@link Lua#OP_TAILCALL} bytecode needs a
|
||||
* mechanism for tail calls when converting lua-bytecode to java-bytecode.
|
||||
* Since Java doesn't have direct support for tail calls,
|
||||
* any lua function whose {@link Prototype} contains the
|
||||
* {@link Lua#OP_TAILCALL} bytecode needs a mechanism
|
||||
* for tail calls when converting lua-bytecode to java-bytecode.
|
||||
* <p>
|
||||
* The tail call holds the next function and arguments, and the client a call to
|
||||
* {@link #eval()} executes the function repeatedly until the tail calls are
|
||||
* completed.
|
||||
* The tail call holds the next function and arguments,
|
||||
* and the client a call to {@link #eval()} executes the function
|
||||
* repeatedly until the tail calls are completed.
|
||||
* <p>
|
||||
* Normally, users of luaj need not concern themselves with the details of this
|
||||
* mechanism, as it is built into the core execution framework.
|
||||
*
|
||||
* @see Prototype
|
||||
* Normally, users of luaj need not concern themselves with the
|
||||
* details of this mechanism, as it is built into the core
|
||||
* execution framework.
|
||||
* @see Prototype
|
||||
* @see org.luaj.vm2.luajc.LuaJC
|
||||
*/
|
||||
public class TailcallVarargs extends Varargs {
|
||||
|
||||
private LuaValue func;
|
||||
private Varargs args;
|
||||
private Varargs result;
|
||||
|
||||
private Varargs args;
|
||||
private Varargs result;
|
||||
|
||||
public TailcallVarargs(LuaValue f, Varargs args) {
|
||||
this.func = f;
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
|
||||
public TailcallVarargs(LuaValue object, LuaValue methodname, Varargs args) {
|
||||
this.func = object.get(methodname);
|
||||
this.args = LuaValue.varargsOf(object, args);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isTailcall() { return true; }
|
||||
|
||||
@Override
|
||||
|
||||
public boolean isTailcall() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public Varargs eval() {
|
||||
while ( result == null ) {
|
||||
Varargs r = func.onInvoke(args);
|
||||
@@ -66,40 +67,37 @@ public class TailcallVarargs extends Varargs {
|
||||
TailcallVarargs t = (TailcallVarargs) r;
|
||||
func = t.func;
|
||||
args = t.args;
|
||||
} else {
|
||||
result = r;
|
||||
}
|
||||
else {
|
||||
result = r;
|
||||
func = null;
|
||||
args = null;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue arg(int i) {
|
||||
if (result == null)
|
||||
|
||||
public LuaValue arg( int i ) {
|
||||
if ( result == null )
|
||||
eval();
|
||||
return result.arg(i);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public LuaValue arg1() {
|
||||
if (result == null)
|
||||
eval();
|
||||
return result.arg1();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public int narg() {
|
||||
if (result == null)
|
||||
eval();
|
||||
return result.narg();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Varargs subargs(int start) {
|
||||
if (result == null)
|
||||
eval();
|
||||
return result.subargs(start);
|
||||
}
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/UpValue.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/UpValue.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -21,62 +21,60 @@
|
||||
******************************************************************************/
|
||||
package org.luaj.vm2;
|
||||
|
||||
/**
|
||||
* Upvalue used with Closure formulation
|
||||
|
||||
/** Upvalue used with Closure formulation
|
||||
* <p>
|
||||
*
|
||||
* @see LuaClosure
|
||||
* @see Prototype
|
||||
*/
|
||||
public final class UpValue {
|
||||
|
||||
LuaValue[] array; // initially the stack, becomes a holder
|
||||
int index;
|
||||
LuaValue[] array; // initially the stack, becomes a holder
|
||||
int index;
|
||||
|
||||
/**
|
||||
* Create an upvalue relative to a stack
|
||||
*
|
||||
* Create an upvalue relative to a stack
|
||||
* @param stack the stack
|
||||
* @param index the index on the stack for the upvalue
|
||||
*/
|
||||
public UpValue(LuaValue[] stack, int index) {
|
||||
public UpValue( LuaValue[] stack, int index) {
|
||||
this.array = stack;
|
||||
this.index = index;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return index + "/" + array.length + " " + array[index];
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
/**
|
||||
* Convert this upvalue to a Java String
|
||||
*
|
||||
* @return the Java String for this upvalue.
|
||||
* @see LuaValue#tojstring()
|
||||
*/
|
||||
public String tojstring() {
|
||||
return array[index].tojstring();
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the value of the upvalue
|
||||
*
|
||||
* @return the {@link LuaValue} for this upvalue
|
||||
*/
|
||||
public LuaValue getValue() { return array[index]; }
|
||||
|
||||
public final LuaValue getValue() {
|
||||
return array[index];
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the value of the upvalue
|
||||
*
|
||||
* @param value the {@link LuaValue} to set it to
|
||||
*/
|
||||
public void setValue(LuaValue value) { array[index] = value; }
|
||||
|
||||
public final void setValue( LuaValue value ) {
|
||||
array[index] = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Close this upvalue so it is no longer on the stack
|
||||
*/
|
||||
public void close() {
|
||||
public final void close() {
|
||||
LuaValue[] old = array;
|
||||
array = new LuaValue[] { old[index] };
|
||||
old[index] = null;
|
||||
BIN
core/src/main/java/org/luaj/vm2/Upvaldesc.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Upvaldesc.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -25,21 +25,20 @@ public class Upvaldesc {
|
||||
|
||||
/* upvalue name (for debug information) */
|
||||
public LuaString name;
|
||||
|
||||
|
||||
/* whether it is in stack */
|
||||
public final boolean instack;
|
||||
|
||||
|
||||
/* index of upvalue (in stack or in outer function's list) */
|
||||
public final short idx;
|
||||
|
||||
|
||||
public Upvaldesc(LuaString name, boolean instack, int idx) {
|
||||
this.name = name;
|
||||
this.instack = instack;
|
||||
this.idx = (short) idx;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public String toString() {
|
||||
return idx+(instack? " instack ": " closed ")+String.valueOf(name);
|
||||
return idx + (instack? " instack ": " closed ") + String.valueOf(name);
|
||||
}
|
||||
}
|
||||
BIN
core/src/main/java/org/luaj/vm2/Varargs$ArrayPartVarargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Varargs$ArrayPartVarargs.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Varargs$ArrayVarargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Varargs$ArrayVarargs.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Varargs$PairVarargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Varargs$PairVarargs.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Varargs$SubVarargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Varargs$SubVarargs.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/Varargs.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/Varargs.class
Normal file
Binary file not shown.
File diff suppressed because it is too large
Load Diff
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakKeySlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakKeySlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakSlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakSlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakUserdata.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakUserdata.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakValue.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakValue.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakValueSlot.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable$WeakValueSlot.class
Normal file
Binary file not shown.
BIN
core/src/main/java/org/luaj/vm2/WeakTable.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/WeakTable.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -27,40 +27,39 @@ import org.luaj.vm2.LuaTable.Slot;
|
||||
import org.luaj.vm2.LuaTable.StrongSlot;
|
||||
|
||||
/**
|
||||
* Subclass of {@link LuaTable} that provides weak key and weak value semantics.
|
||||
* Subclass of {@link LuaTable} that provides weak key and weak value semantics.
|
||||
* <p>
|
||||
* Normally these are not created directly, but indirectly when changing the mode
|
||||
* of a {@link LuaTable} as lua script executes.
|
||||
* <p>
|
||||
* Normally these are not created directly, but indirectly when changing the
|
||||
* mode of a {@link LuaTable} as lua script executes.
|
||||
* <p>
|
||||
* However, calling the constructors directly when weak tables are required from
|
||||
* Java will reduce overhead.
|
||||
* However, calling the constructors directly when weak tables are required from
|
||||
* Java will reduce overhead.
|
||||
*/
|
||||
public class WeakTable implements Metatable {
|
||||
|
||||
private final boolean weakkeys, weakvalues;
|
||||
private final LuaValue backing;
|
||||
private boolean weakkeys, weakvalues;
|
||||
private LuaValue backing;
|
||||
|
||||
public static LuaTable make(boolean weakkeys, boolean weakvalues) {
|
||||
LuaString mode;
|
||||
if (weakkeys && weakvalues) {
|
||||
if ( weakkeys && weakvalues ) {
|
||||
mode = LuaString.valueOf("kv");
|
||||
} else if (weakkeys) {
|
||||
} else if ( weakkeys ) {
|
||||
mode = LuaString.valueOf("k");
|
||||
} else if (weakvalues) {
|
||||
} else if ( weakvalues ) {
|
||||
mode = LuaString.valueOf("v");
|
||||
} else {
|
||||
return LuaValue.tableOf();
|
||||
return LuaTable.tableOf();
|
||||
}
|
||||
LuaTable table = LuaValue.tableOf();
|
||||
LuaTable mt = LuaValue.tableOf(new LuaValue[] { LuaValue.MODE, mode });
|
||||
LuaTable table = LuaTable.tableOf();
|
||||
LuaTable mt = LuaTable.tableOf(new LuaValue[] { LuaValue.MODE, mode });
|
||||
table.setmetatable(mt);
|
||||
return table;
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a table with weak keys, weak values, or both
|
||||
*
|
||||
* @param weakkeys true to let the table have weak keys
|
||||
* @param weakkeys true to let the table have weak keys
|
||||
* @param weakvalues true to let the table have weak values
|
||||
*/
|
||||
public WeakTable(boolean weakkeys, boolean weakvalues, LuaValue backing) {
|
||||
@@ -69,44 +68,40 @@ public class WeakTable implements Metatable {
|
||||
this.backing = backing;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean useWeakKeys() {
|
||||
return weakkeys;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean useWeakValues() {
|
||||
return weakvalues;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue toLuaValue() {
|
||||
return backing;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot entry(LuaValue key, LuaValue value) {
|
||||
value = value.strongvalue();
|
||||
if (value == null)
|
||||
if ( value == null )
|
||||
return null;
|
||||
if (weakkeys && !(key.isnumber() || key.isstring() || key.isboolean())) {
|
||||
if (weakvalues && !(value.isnumber() || value.isstring() || value.isboolean())) {
|
||||
return new WeakKeyAndValueSlot(key, value, null);
|
||||
if ( weakkeys && !( key.isnumber() || key.isstring() || key.isboolean() )) {
|
||||
if ( weakvalues && !( value.isnumber() || value.isstring() || value.isboolean() )) {
|
||||
return new WeakKeyAndValueSlot( key, value, null );
|
||||
} else {
|
||||
return new WeakKeySlot(key, value, null);
|
||||
return new WeakKeySlot( key, value, null );
|
||||
}
|
||||
}
|
||||
if (weakvalues && !(value.isnumber() || value.isstring() || value.isboolean())) {
|
||||
return new WeakValueSlot(key, value, null);
|
||||
if ( weakvalues && ! (value.isnumber() || value.isstring() || value.isboolean() )) {
|
||||
return new WeakValueSlot( key, value, null );
|
||||
}
|
||||
return LuaTable.defaultEntry(key, value);
|
||||
return LuaTable.defaultEntry( key, value );
|
||||
}
|
||||
|
||||
public static abstract class WeakSlot implements Slot {
|
||||
|
||||
protected Object key;
|
||||
protected Object value;
|
||||
protected Slot next;
|
||||
protected Slot next;
|
||||
|
||||
protected WeakSlot(Object key, Object value, Slot next) {
|
||||
this.key = key;
|
||||
@@ -114,93 +109,87 @@ public class WeakTable implements Metatable {
|
||||
this.next = next;
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract int keyindex(int hashMask);
|
||||
public abstract int keyindex( int hashMask );
|
||||
|
||||
public abstract Slot set(LuaValue value);
|
||||
|
||||
@Override
|
||||
public StrongSlot first() {
|
||||
LuaValue key = strongkey();
|
||||
LuaValue value = strongvalue();
|
||||
if (key != null && value != null) {
|
||||
if ( key != null && value != null ) {
|
||||
return new LuaTable.NormalEntry(key, value);
|
||||
} else {
|
||||
this.key = null;
|
||||
this.value = null;
|
||||
if ( key == null ) {
|
||||
this.key = null;
|
||||
}
|
||||
if ( value == null ) {
|
||||
this.value = null;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public StrongSlot find(LuaValue key) {
|
||||
StrongSlot first = first();
|
||||
return first != null? first.find(key): null;
|
||||
return ( first != null ) ? first.find( key ) : null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean keyeq(LuaValue key) {
|
||||
StrongSlot first = first();
|
||||
return first != null && first.keyeq(key);
|
||||
return ( first != null ) && first.keyeq( key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot rest() {
|
||||
return next;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int arraykey(int max) {
|
||||
// Integer keys can never be weak.
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot set(StrongSlot target, LuaValue value) {
|
||||
LuaValue key = strongkey();
|
||||
if (key != null && target.find(key) != null) {
|
||||
return set(value);
|
||||
} else if (key != null) {
|
||||
if ( key != null && target.find( key ) != null ) {
|
||||
return set( value );
|
||||
} else if ( key != null ) {
|
||||
// Our key is still good.
|
||||
next = next.set(target, value);
|
||||
next = next.set( target, value );
|
||||
return this;
|
||||
} else {
|
||||
// our key was dropped, remove ourselves from the chain.
|
||||
return next.set(target, value);
|
||||
return next.set( target, value );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot add(Slot entry) {
|
||||
next = next != null? next.add(entry): entry;
|
||||
if (strongkey() != null && strongvalue() != null) {
|
||||
public Slot add( Slot entry ) {
|
||||
next = ( next != null ) ? next.add( entry ) : entry;
|
||||
if ( strongkey() != null && strongvalue() != null ) {
|
||||
return this;
|
||||
} else {
|
||||
return next;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot remove(StrongSlot target) {
|
||||
public Slot remove( StrongSlot target ) {
|
||||
LuaValue key = strongkey();
|
||||
if (key == null) {
|
||||
return next.remove(target);
|
||||
} else if (target.keyeq(key)) {
|
||||
if ( key == null ) {
|
||||
return next.remove( target );
|
||||
} else if ( target.keyeq( key ) ) {
|
||||
this.value = null;
|
||||
return this;
|
||||
} else {
|
||||
next = next.remove(target);
|
||||
next = next.remove( target );
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot relink(Slot rest) {
|
||||
if (strongkey() != null && strongvalue() != null) {
|
||||
if (rest == null && this.next == null) {
|
||||
public Slot relink( Slot rest ) {
|
||||
if ( strongkey() != null && strongvalue() != null ) {
|
||||
if ( rest == null && this.next == null ) {
|
||||
return this;
|
||||
} else {
|
||||
return copy(rest);
|
||||
return copy( rest );
|
||||
}
|
||||
} else {
|
||||
return rest;
|
||||
@@ -215,74 +204,66 @@ public class WeakTable implements Metatable {
|
||||
return (LuaValue) value;
|
||||
}
|
||||
|
||||
protected abstract WeakSlot copy(Slot next);
|
||||
protected abstract WeakSlot copy( Slot next );
|
||||
}
|
||||
|
||||
static class WeakKeySlot extends WeakSlot {
|
||||
|
||||
private final int keyhash;
|
||||
|
||||
protected WeakKeySlot(LuaValue key, LuaValue value, Slot next) {
|
||||
protected WeakKeySlot( LuaValue key, LuaValue value, Slot next ) {
|
||||
super(weaken(key), value, next);
|
||||
keyhash = key.hashCode();
|
||||
}
|
||||
|
||||
protected WeakKeySlot(WeakKeySlot copyFrom, Slot next) {
|
||||
super(copyFrom.key, copyFrom.value, next);
|
||||
protected WeakKeySlot( WeakKeySlot copyFrom, Slot next ) {
|
||||
super( copyFrom.key, copyFrom.value, next );
|
||||
this.keyhash = copyFrom.keyhash;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int keyindex(int mask) {
|
||||
return LuaTable.hashmod(keyhash, mask);
|
||||
public int keyindex( int mask ) {
|
||||
return LuaTable.hashmod( keyhash, mask );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot set(LuaValue value) {
|
||||
this.value = value;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongkey() {
|
||||
return strengthen(key);
|
||||
return strengthen( key );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected WeakSlot copy(Slot rest) {
|
||||
return new WeakKeySlot(this, rest);
|
||||
protected WeakSlot copy( Slot rest ) {
|
||||
return new WeakKeySlot( this, rest );
|
||||
}
|
||||
}
|
||||
|
||||
static class WeakValueSlot extends WeakSlot {
|
||||
|
||||
protected WeakValueSlot(LuaValue key, LuaValue value, Slot next) {
|
||||
super(key, weaken(value), next);
|
||||
protected WeakValueSlot( LuaValue key, LuaValue value, Slot next ) {
|
||||
super( key, weaken(value), next);
|
||||
}
|
||||
|
||||
protected WeakValueSlot(WeakValueSlot copyFrom, Slot next) {
|
||||
super(copyFrom.key, copyFrom.value, next);
|
||||
protected WeakValueSlot( WeakValueSlot copyFrom, Slot next ) {
|
||||
super( copyFrom.key, copyFrom.value, next );
|
||||
}
|
||||
|
||||
@Override
|
||||
public int keyindex(int mask) {
|
||||
return LuaTable.hashSlot(strongkey(), mask);
|
||||
public int keyindex( int mask ) {
|
||||
return LuaTable.hashSlot( strongkey(), mask );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot set(LuaValue value) {
|
||||
this.value = weaken(value);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongvalue() {
|
||||
return strengthen(value);
|
||||
return strengthen( value );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected WeakSlot copy(Slot next) {
|
||||
return new WeakValueSlot(this, next);
|
||||
return new WeakValueSlot( this, next );
|
||||
}
|
||||
}
|
||||
|
||||
@@ -290,83 +271,73 @@ public class WeakTable implements Metatable {
|
||||
|
||||
private final int keyhash;
|
||||
|
||||
protected WeakKeyAndValueSlot(LuaValue key, LuaValue value, Slot next) {
|
||||
super(weaken(key), weaken(value), next);
|
||||
protected WeakKeyAndValueSlot( LuaValue key, LuaValue value, Slot next ) {
|
||||
super( weaken(key), weaken(value), next );
|
||||
keyhash = key.hashCode();
|
||||
}
|
||||
|
||||
protected WeakKeyAndValueSlot(WeakKeyAndValueSlot copyFrom, Slot next) {
|
||||
super(copyFrom.key, copyFrom.value, next);
|
||||
super( copyFrom.key, copyFrom.value, next );
|
||||
keyhash = copyFrom.keyhash;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int keyindex(int hashMask) {
|
||||
return LuaTable.hashmod(keyhash, hashMask);
|
||||
public int keyindex( int hashMask ) {
|
||||
return LuaTable.hashmod( keyhash, hashMask );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Slot set(LuaValue value) {
|
||||
this.value = weaken(value);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongkey() {
|
||||
return strengthen(key);
|
||||
return strengthen( key );
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongvalue() {
|
||||
return strengthen(value);
|
||||
return strengthen( value );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected WeakSlot copy(Slot next) {
|
||||
return new WeakKeyAndValueSlot(this, next);
|
||||
protected WeakSlot copy( Slot next ) {
|
||||
return new WeakKeyAndValueSlot( this, next );
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Self-sent message to convert a value to its weak counterpart
|
||||
*
|
||||
* @param value value to convert
|
||||
* @return {@link LuaValue} that is a strong or weak reference, depending on
|
||||
* type of {@code value}
|
||||
* @return {@link LuaValue} that is a strong or weak reference, depending on type of {@code value}
|
||||
*/
|
||||
protected static LuaValue weaken(LuaValue value) {
|
||||
switch (value.type()) {
|
||||
case LuaValue.TFUNCTION:
|
||||
case LuaValue.TTHREAD:
|
||||
case LuaValue.TTABLE:
|
||||
return new WeakValue(value);
|
||||
case LuaValue.TUSERDATA:
|
||||
return new WeakUserdata(value);
|
||||
default:
|
||||
return value;
|
||||
protected static LuaValue weaken( LuaValue value ) {
|
||||
switch ( value.type() ) {
|
||||
case LuaValue.TFUNCTION:
|
||||
case LuaValue.TTHREAD:
|
||||
case LuaValue.TTABLE:
|
||||
return new WeakValue(value);
|
||||
case LuaValue.TUSERDATA:
|
||||
return new WeakUserdata(value);
|
||||
default:
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Unwrap a LuaValue from a WeakReference and/or WeakUserdata.
|
||||
*
|
||||
* @param ref reference to convert
|
||||
* @return LuaValue or null
|
||||
* @see #weaken(LuaValue)
|
||||
*/
|
||||
protected static LuaValue strengthen(Object ref) {
|
||||
if (ref instanceof WeakReference) {
|
||||
if ( ref instanceof WeakReference ) {
|
||||
ref = ((WeakReference) ref).get();
|
||||
}
|
||||
if (ref instanceof WeakValue) {
|
||||
if ( ref instanceof WeakValue ) {
|
||||
return ((WeakValue) ref).strongvalue();
|
||||
}
|
||||
return (LuaValue) ref;
|
||||
}
|
||||
|
||||
/**
|
||||
* Internal class to implement weak values.
|
||||
*
|
||||
/** Internal class to implement weak values.
|
||||
* @see WeakTable
|
||||
*/
|
||||
static class WeakValue extends LuaValue {
|
||||
@@ -376,44 +347,37 @@ public class WeakTable implements Metatable {
|
||||
ref = new WeakReference(value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int type() {
|
||||
illegal("type", "weak value");
|
||||
illegal("type","weak value");
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String typename() {
|
||||
illegal("typename", "weak value");
|
||||
illegal("typename","weak value");
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "weak<" + ref.get() + ">";
|
||||
return "weak<"+ref.get()+">";
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongvalue() {
|
||||
Object o = ref.get();
|
||||
return (LuaValue) o;
|
||||
return (LuaValue)o;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean raweq(LuaValue rhs) {
|
||||
Object o = ref.get();
|
||||
return o != null && rhs.raweq((LuaValue) o);
|
||||
return o!=null && rhs.raweq((LuaValue)o);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Internal class to implement weak userdata values.
|
||||
*
|
||||
/** Internal class to implement weak userdata values.
|
||||
* @see WeakTable
|
||||
*/
|
||||
static final class WeakUserdata extends WeakValue {
|
||||
private final WeakReference ob;
|
||||
private final LuaValue mt;
|
||||
private final LuaValue mt;
|
||||
|
||||
private WeakUserdata(LuaValue value) {
|
||||
super(value);
|
||||
@@ -421,14 +385,13 @@ public class WeakTable implements Metatable {
|
||||
mt = value.getmetatable();
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue strongvalue() {
|
||||
Object u = ref.get();
|
||||
if (u != null)
|
||||
if ( u != null )
|
||||
return (LuaValue) u;
|
||||
Object o = ob.get();
|
||||
if (o != null) {
|
||||
LuaValue ud = LuaValue.userdataOf(o, mt);
|
||||
if ( o != null ) {
|
||||
LuaValue ud = LuaValue.userdataOf(o,mt);
|
||||
ref = new WeakReference(ud);
|
||||
return ud;
|
||||
} else {
|
||||
@@ -437,12 +400,10 @@ public class WeakTable implements Metatable {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue wrap(LuaValue value) {
|
||||
return weakvalues? weaken(value): value;
|
||||
return weakvalues ? weaken( value ) : value;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LuaValue arrayget(LuaValue[] array, int index) {
|
||||
LuaValue value = array[index];
|
||||
if (value != null) {
|
||||
BIN
core/src/main/java/org/luaj/vm2/compiler/Constants.class
Normal file
BIN
core/src/main/java/org/luaj/vm2/compiler/Constants.class
Normal file
Binary file not shown.
@@ -10,7 +10,7 @@
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
@@ -31,146 +31,158 @@ import org.luaj.vm2.Upvaldesc;
|
||||
|
||||
/**
|
||||
* Constants used by the LuaC compiler and related classes.
|
||||
*
|
||||
*
|
||||
* @see LuaC
|
||||
* @see FuncState
|
||||
*/
|
||||
public class Constants extends Lua {
|
||||
|
||||
|
||||
/** Maximum stack size of a luaj vm interpreter instance. */
|
||||
public static final int MAXSTACK = 250;
|
||||
public static final int MAXSTACK = 1024;
|
||||
|
||||
static final int LUAI_MAXUPVAL = 0xff;
|
||||
static final int LUAI_MAXVARS = 200;
|
||||
static final int NO_REG = MAXARG_A;
|
||||
static final int LUAI_MAXVARS = 1024;
|
||||
static final int NO_REG = MAXARG_A;
|
||||
|
||||
|
||||
/* OpMode - basic instruction format */
|
||||
static final int iABC = 0, iABx = 1, iAsBx = 2;
|
||||
static final int
|
||||
iABC = 0,
|
||||
iABx = 1,
|
||||
iAsBx = 2;
|
||||
|
||||
/* OpArgMask */
|
||||
static final int OpArgN = 0, /* argument is not used */
|
||||
OpArgU = 1, /* argument is used */
|
||||
OpArgR = 2, /* argument is a register or a jump offset */
|
||||
OpArgK = 3; /* argument is a constant or register/constant */
|
||||
static final int
|
||||
OpArgN = 0, /* argument is not used */
|
||||
OpArgU = 1, /* argument is used */
|
||||
OpArgR = 2, /* argument is a register or a jump offset */
|
||||
OpArgK = 3; /* argument is a constant or register/constant */
|
||||
|
||||
|
||||
protected static void _assert(boolean b) {
|
||||
if (!b)
|
||||
throw new LuaError("compiler assert failed");
|
||||
}
|
||||
|
||||
static void SET_OPCODE(InstructionPtr i, int o) {
|
||||
i.set(i.get() & MASK_NOT_OP | o<<POS_OP & MASK_OP);
|
||||
static void SET_OPCODE(InstructionPtr i,int o) {
|
||||
i.set( ( i.get() & (MASK_NOT_OP)) | ((o << POS_OP) & MASK_OP) );
|
||||
}
|
||||
|
||||
|
||||
static void SETARG_A(int[] code, int index, int u) {
|
||||
code[index] = code[index] & MASK_NOT_A | u<<POS_A & MASK_A;
|
||||
code[index] = (code[index] & (MASK_NOT_A)) | ((u << POS_A) & MASK_A);
|
||||
}
|
||||
|
||||
static void SETARG_A(InstructionPtr i, int u) {
|
||||
i.set(i.get() & MASK_NOT_A | u<<POS_A & MASK_A);
|
||||
static void SETARG_A(InstructionPtr i,int u) {
|
||||
i.set( ( i.get() & (MASK_NOT_A)) | ((u << POS_A) & MASK_A) );
|
||||
}
|
||||
|
||||
static void SETARG_B(InstructionPtr i, int u) {
|
||||
i.set(i.get() & MASK_NOT_B | u<<POS_B & MASK_B);
|
||||
static void SETARG_B(InstructionPtr i,int u) {
|
||||
i.set( ( i.get() & (MASK_NOT_B)) | ((u << POS_B) & MASK_B) );
|
||||
}
|
||||
|
||||
static void SETARG_C(InstructionPtr i, int u) {
|
||||
i.set(i.get() & MASK_NOT_C | u<<POS_C & MASK_C);
|
||||
static void SETARG_C(InstructionPtr i,int u) {
|
||||
i.set( ( i.get() & (MASK_NOT_C)) | ((u << POS_C) & MASK_C) );
|
||||
}
|
||||
|
||||
static void SETARG_Bx(InstructionPtr i, int u) {
|
||||
i.set(i.get() & MASK_NOT_Bx | u<<POS_Bx & MASK_Bx);
|
||||
|
||||
static void SETARG_Bx(InstructionPtr i,int u) {
|
||||
i.set( ( i.get() & (MASK_NOT_Bx)) | ((u << POS_Bx) & MASK_Bx) );
|
||||
}
|
||||
|
||||
static void SETARG_sBx(InstructionPtr i, int u) {
|
||||
SETARG_Bx(i, u+MAXARG_sBx);
|
||||
|
||||
static void SETARG_sBx(InstructionPtr i,int u) {
|
||||
SETARG_Bx( i, u + MAXARG_sBx );
|
||||
}
|
||||
|
||||
static int CREATE_ABC(int o, int a, int b, int c) {
|
||||
return o<<POS_OP & MASK_OP | a<<POS_A & MASK_A | b<<POS_B & MASK_B | c<<POS_C & MASK_C;
|
||||
return ((o << POS_OP) & MASK_OP) |
|
||||
((a << POS_A) & MASK_A) |
|
||||
((b << POS_B) & MASK_B) |
|
||||
((c << POS_C) & MASK_C) ;
|
||||
}
|
||||
|
||||
|
||||
static int CREATE_ABx(int o, int a, int bc) {
|
||||
return o<<POS_OP & MASK_OP | a<<POS_A & MASK_A | bc<<POS_Bx & MASK_Bx;
|
||||
}
|
||||
|
||||
return ((o << POS_OP) & MASK_OP) |
|
||||
((a << POS_A) & MASK_A) |
|
||||
((bc << POS_Bx) & MASK_Bx) ;
|
||||
}
|
||||
|
||||
static int CREATE_Ax(int o, int a) {
|
||||
return o<<POS_OP & MASK_OP | a<<POS_Ax & MASK_Ax;
|
||||
}
|
||||
return ((o << POS_OP) & MASK_OP) |
|
||||
((a << POS_Ax) & MASK_Ax) ;
|
||||
}
|
||||
|
||||
// vector reallocation
|
||||
|
||||
|
||||
static LuaValue[] realloc(LuaValue[] v, int n) {
|
||||
LuaValue[] a = new LuaValue[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static Prototype[] realloc(Prototype[] v, int n) {
|
||||
Prototype[] a = new Prototype[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static LuaString[] realloc(LuaString[] v, int n) {
|
||||
LuaString[] a = new LuaString[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static LocVars[] realloc(LocVars[] v, int n) {
|
||||
LocVars[] a = new LocVars[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static Upvaldesc[] realloc(Upvaldesc[] v, int n) {
|
||||
Upvaldesc[] a = new Upvaldesc[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static LexState.Vardesc[] realloc(LexState.Vardesc[] v, int n) {
|
||||
LexState.Vardesc[] a = new LexState.Vardesc[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static LexState.Labeldesc[] grow(LexState.Labeldesc[] v, int min_n) {
|
||||
return v == null? new LexState.Labeldesc[2]: v.length < min_n? realloc(v, v.length*2): v;
|
||||
return v == null ? new LexState.Labeldesc[2] : v.length < min_n ? realloc(v, v.length*2) : v;
|
||||
}
|
||||
|
||||
|
||||
static LexState.Labeldesc[] realloc(LexState.Labeldesc[] v, int n) {
|
||||
LexState.Labeldesc[] a = new LexState.Labeldesc[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static int[] realloc(int[] v, int n) {
|
||||
int[] a = new int[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static byte[] realloc(byte[] v, int n) {
|
||||
byte[] a = new byte[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
static char[] realloc(char[] v, int n) {
|
||||
char[] a = new char[n];
|
||||
if (v != null)
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length, n));
|
||||
if ( v != null )
|
||||
System.arraycopy(v, 0, a, 0, Math.min(v.length,n));
|
||||
return a;
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user