Commit faff9b04 by Ian Lance Taylor

Check for errors from Gogo::call_builtin.

From-SVN: r167891
parent 0c5be64e
...@@ -505,6 +505,8 @@ Expression::convert_interface_to_interface(Translate_context* context, ...@@ -505,6 +505,8 @@ Expression::convert_interface_to_interface(Translate_context* context,
lhs_type_descriptor, lhs_type_descriptor,
TREE_TYPE(rhs_type_descriptor), TREE_TYPE(rhs_type_descriptor),
rhs_type_descriptor); rhs_type_descriptor);
if (call == error_mark_node)
return error_mark_node;
// This will panic if the interface conversion fails. // This will panic if the interface conversion fails.
TREE_NOTHROW(assert_interface_decl) = 0; TREE_NOTHROW(assert_interface_decl) = 0;
elt->value = fold_convert_loc(location, TREE_TYPE(field), call); elt->value = fold_convert_loc(location, TREE_TYPE(field), call);
...@@ -535,6 +537,8 @@ Expression::convert_interface_to_interface(Translate_context* context, ...@@ -535,6 +537,8 @@ Expression::convert_interface_to_interface(Translate_context* context,
lhs_type_descriptor, lhs_type_descriptor,
TREE_TYPE(rhs_type_descriptor), TREE_TYPE(rhs_type_descriptor),
rhs_type_descriptor); rhs_type_descriptor);
if (call == error_mark_node)
return error_mark_node;
// This will panic if the interface conversion fails. // This will panic if the interface conversion fails.
TREE_NOTHROW(convert_interface_decl) = 0; TREE_NOTHROW(convert_interface_decl) = 0;
elt->value = fold_convert_loc(location, TREE_TYPE(field), call); elt->value = fold_convert_loc(location, TREE_TYPE(field), call);
...@@ -599,6 +603,8 @@ Expression::convert_interface_to_type(Translate_context* context, ...@@ -599,6 +603,8 @@ Expression::convert_interface_to_type(Translate_context* context,
rhs_type_descriptor, rhs_type_descriptor,
TREE_TYPE(rhs_inter_descriptor), TREE_TYPE(rhs_inter_descriptor),
rhs_inter_descriptor); rhs_inter_descriptor);
if (call == error_mark_node)
return error_mark_node;
// This call will panic if the conversion is invalid. // This call will panic if the conversion is invalid.
TREE_NOTHROW(check_interface_type_decl) = 0; TREE_NOTHROW(check_interface_type_decl) = 0;
...@@ -6012,6 +6018,8 @@ Expression::comparison_tree(Translate_context* context, Operator op, ...@@ -6012,6 +6018,8 @@ Expression::comparison_tree(Translate_context* context, Operator op,
descriptor, descriptor,
ptr_type_node, ptr_type_node,
arg); arg);
if (left_tree == error_mark_node)
return error_mark_node;
// This can panic if the type is not comparable. // This can panic if the type is not comparable.
TREE_NOTHROW(empty_interface_value_compare_decl) = 0; TREE_NOTHROW(empty_interface_value_compare_decl) = 0;
} }
...@@ -6029,6 +6037,8 @@ Expression::comparison_tree(Translate_context* context, Operator op, ...@@ -6029,6 +6037,8 @@ Expression::comparison_tree(Translate_context* context, Operator op,
descriptor, descriptor,
ptr_type_node, ptr_type_node,
arg); arg);
if (left_tree == error_mark_node)
return error_mark_node;
// This can panic if the type is not comparable. // This can panic if the type is not comparable.
TREE_NOTHROW(interface_value_compare_decl) = 0; TREE_NOTHROW(interface_value_compare_decl) = 0;
} }
...@@ -6054,6 +6064,8 @@ Expression::comparison_tree(Translate_context* context, Operator op, ...@@ -6054,6 +6064,8 @@ Expression::comparison_tree(Translate_context* context, Operator op,
left_tree, left_tree,
TREE_TYPE(right_tree), TREE_TYPE(right_tree),
right_tree); right_tree);
if (left_tree == error_mark_node)
return error_mark_node;
// This can panic if the type is uncomparable. // This can panic if the type is uncomparable.
TREE_NOTHROW(empty_interface_compare_decl) = 0; TREE_NOTHROW(empty_interface_compare_decl) = 0;
} }
...@@ -6070,6 +6082,8 @@ Expression::comparison_tree(Translate_context* context, Operator op, ...@@ -6070,6 +6082,8 @@ Expression::comparison_tree(Translate_context* context, Operator op,
left_tree, left_tree,
TREE_TYPE(right_tree), TREE_TYPE(right_tree),
right_tree); right_tree);
if (left_tree == error_mark_node)
return error_mark_node;
// This can panic if the type is uncomparable. // This can panic if the type is uncomparable.
TREE_NOTHROW(interface_compare_decl) = 0; TREE_NOTHROW(interface_compare_decl) = 0;
} }
...@@ -7415,6 +7429,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context) ...@@ -7415,6 +7429,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context)
"__go_print_space", "__go_print_space",
0, 0,
void_type_node); void_type_node);
if (call == error_mark_node)
return error_mark_node;
append_to_statement_list(call, &stmt_list); append_to_statement_list(call, &stmt_list);
} }
...@@ -7513,8 +7529,9 @@ Builtin_call_expression::do_get_tree(Translate_context* context) ...@@ -7513,8 +7529,9 @@ Builtin_call_expression::do_get_tree(Translate_context* context)
void_type_node, void_type_node,
TREE_TYPE(arg), TREE_TYPE(arg),
arg); arg);
if (call != error_mark_node) if (call == error_mark_node)
append_to_statement_list(call, &stmt_list); return error_mark_node;
append_to_statement_list(call, &stmt_list);
} }
} }
...@@ -7526,6 +7543,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context) ...@@ -7526,6 +7543,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context)
"__go_print_nl", "__go_print_nl",
0, 0,
void_type_node); void_type_node);
if (call == error_mark_node)
return error_mark_node;
append_to_statement_list(call, &stmt_list); append_to_statement_list(call, &stmt_list);
} }
...@@ -7552,6 +7571,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context) ...@@ -7552,6 +7571,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context)
void_type_node, void_type_node,
TREE_TYPE(arg_tree), TREE_TYPE(arg_tree),
arg_tree); arg_tree);
if (call == error_mark_node)
return error_mark_node;
// This function will throw an exception. // This function will throw an exception.
TREE_NOTHROW(panic_fndecl) = 0; TREE_NOTHROW(panic_fndecl) = 0;
// This function will not return. // This function will not return.
...@@ -7604,6 +7625,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context) ...@@ -7604,6 +7625,8 @@ Builtin_call_expression::do_get_tree(Translate_context* context)
0, 0,
empty_tree); empty_tree);
} }
if (call == error_mark_node)
return error_mark_node;
return fold_build3_loc(location, COND_EXPR, empty_tree, arg_tree, return fold_build3_loc(location, COND_EXPR, empty_tree, arg_tree,
call, empty_nil_tree); call, empty_nil_tree);
} }
...@@ -9404,6 +9427,8 @@ String_index_expression::do_get_tree(Translate_context* context) ...@@ -9404,6 +9427,8 @@ String_index_expression::do_get_tree(Translate_context* context)
start_tree, start_tree,
length_type, length_type,
end_tree); end_tree);
if (ret == error_mark_node)
return error_mark_node;
// This will panic if the bounds are out of range for the // This will panic if the bounds are out of range for the
// string. // string.
TREE_NOTHROW(strslice_fndecl) = 0; TREE_NOTHROW(strslice_fndecl) = 0;
...@@ -9573,6 +9598,8 @@ Map_index_expression::get_value_pointer(Translate_context* context, ...@@ -9573,6 +9598,8 @@ Map_index_expression::get_value_pointer(Translate_context* context,
(insert (insert
? boolean_true_node ? boolean_true_node
: boolean_false_node)); : boolean_false_node));
if (call == error_mark_node)
return error_mark_node;
// This can panic on a map of interface type if the interface holds // This can panic on a map of interface type if the interface holds
// an uncomparable or unhashable type. // an uncomparable or unhashable type.
TREE_NOTHROW(map_index_fndecl) = 0; TREE_NOTHROW(map_index_fndecl) = 0;
...@@ -11129,6 +11156,8 @@ Map_construction_expression::do_get_tree(Translate_context* context) ...@@ -11129,6 +11156,8 @@ Map_construction_expression::do_get_tree(Translate_context* context)
TYPE_SIZE_UNIT(TREE_TYPE(val_field)), TYPE_SIZE_UNIT(TREE_TYPE(val_field)),
const_ptr_type_node, const_ptr_type_node,
fold_convert(const_ptr_type_node, valaddr)); fold_convert(const_ptr_type_node, valaddr));
if (call == error_mark_node)
return error_mark_node;
tree ret; tree ret;
if (make_tmp == NULL) if (make_tmp == NULL)
......
...@@ -341,7 +341,8 @@ Gogo::register_gc_vars(const std::vector<Named_object*>& var_gc, ...@@ -341,7 +341,8 @@ Gogo::register_gc_vars(const std::vector<Named_object*>& var_gc,
void_type_node, void_type_node,
build_pointer_type(root_list_type), build_pointer_type(root_list_type),
build_fold_addr_expr(decl)); build_fold_addr_expr(decl));
append_to_statement_list(call, init_stmt_list); if (call != error_mark_node)
append_to_statement_list(call, init_stmt_list);
} }
// Build the decl for the initialization function. // Build the decl for the initialization function.
...@@ -1684,7 +1685,8 @@ Function::build_defer_wrapper(Gogo* gogo, Named_object* named_function, ...@@ -1684,7 +1685,8 @@ Function::build_defer_wrapper(Gogo* gogo, Named_object* named_function,
void_type_node, void_type_node,
ptr_type_node, ptr_type_node,
this->defer_stack(end_loc)); this->defer_stack(end_loc));
append_to_statement_list(call, &stmt_list); if (call != error_mark_node)
append_to_statement_list(call, &stmt_list);
tree retval = this->return_value(gogo, named_function, end_loc, &stmt_list); tree retval = this->return_value(gogo, named_function, end_loc, &stmt_list);
tree set; tree set;
...@@ -1723,7 +1725,8 @@ Function::build_defer_wrapper(Gogo* gogo, Named_object* named_function, ...@@ -1723,7 +1725,8 @@ Function::build_defer_wrapper(Gogo* gogo, Named_object* named_function,
void_type_node, void_type_node,
ptr_type_node, ptr_type_node,
this->defer_stack(end_loc)); this->defer_stack(end_loc));
TREE_NOTHROW(undefer_fndecl) = 0; if (undefer_fndecl != NULL_TREE)
TREE_NOTHROW(undefer_fndecl) = 0;
tree defer = Gogo::call_builtin(&check_fndecl, tree defer = Gogo::call_builtin(&check_fndecl,
end_loc, end_loc,
...@@ -2867,6 +2870,8 @@ Gogo::runtime_error(int code, source_location location) ...@@ -2867,6 +2870,8 @@ Gogo::runtime_error(int code, source_location location)
void_type_node, void_type_node,
integer_type_node, integer_type_node,
build_int_cst(integer_type_node, code)); build_int_cst(integer_type_node, code));
if (ret == error_mark_node)
return error_mark_node;
// The runtime error function panics and does not return. // The runtime error function panics and does not return.
TREE_NOTHROW(runtime_error_fndecl) = 0; TREE_NOTHROW(runtime_error_fndecl) = 0;
TREE_THIS_VOLATILE(runtime_error_fndecl) = 1; TREE_THIS_VOLATILE(runtime_error_fndecl) = 1;
...@@ -2904,6 +2909,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select, ...@@ -2904,6 +2909,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select,
(for_select (for_select
? boolean_true_node ? boolean_true_node
: boolean_false_node)); : boolean_false_node));
if (ret == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a // This can panic if there are too many operations on a
// closed channel. // closed channel.
TREE_NOTHROW(send_small_fndecl) = 0; TREE_NOTHROW(send_small_fndecl) = 0;
...@@ -2922,6 +2929,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select, ...@@ -2922,6 +2929,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select,
channel, channel,
uint64_type_node, uint64_type_node,
val); val);
if (ret == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a // This can panic if there are too many operations on a
// closed channel. // closed channel.
TREE_NOTHROW(send_nonblocking_small_fndecl) = 0; TREE_NOTHROW(send_nonblocking_small_fndecl) = 0;
...@@ -2967,6 +2976,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select, ...@@ -2967,6 +2976,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select,
(for_select (for_select
? boolean_true_node ? boolean_true_node
: boolean_false_node)); : boolean_false_node));
if (call == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a // This can panic if there are too many operations on a
// closed channel. // closed channel.
TREE_NOTHROW(send_big_fndecl) = 0; TREE_NOTHROW(send_big_fndecl) = 0;
...@@ -2984,6 +2995,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select, ...@@ -2984,6 +2995,8 @@ Gogo::send_on_channel(tree channel, tree val, bool blocking, bool for_select,
channel, channel,
ptr_type_node, ptr_type_node,
val); val);
if (call == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a // This can panic if there are too many operations on a
// closed channel. // closed channel.
TREE_NOTHROW(send_nonblocking_big_fndecl) = 0; TREE_NOTHROW(send_nonblocking_big_fndecl) = 0;
...@@ -3025,6 +3038,8 @@ Gogo::receive_from_channel(tree type_tree, tree channel, bool for_select, ...@@ -3025,6 +3038,8 @@ Gogo::receive_from_channel(tree type_tree, tree channel, bool for_select,
(for_select (for_select
? boolean_true_node ? boolean_true_node
: boolean_false_node)); : boolean_false_node));
if (call == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a closed // This can panic if there are too many operations on a closed
// channel. // channel.
TREE_NOTHROW(receive_small_fndecl) = 0; TREE_NOTHROW(receive_small_fndecl) = 0;
...@@ -3057,6 +3072,8 @@ Gogo::receive_from_channel(tree type_tree, tree channel, bool for_select, ...@@ -3057,6 +3072,8 @@ Gogo::receive_from_channel(tree type_tree, tree channel, bool for_select,
(for_select (for_select
? boolean_true_node ? boolean_true_node
: boolean_false_node)); : boolean_false_node));
if (call == error_mark_node)
return error_mark_node;
// This can panic if there are too many operations on a closed // This can panic if there are too many operations on a closed
// channel. // channel.
TREE_NOTHROW(receive_big_fndecl) = 0; TREE_NOTHROW(receive_big_fndecl) = 0;
...@@ -3114,6 +3131,8 @@ Gogo::make_trampoline(tree fnaddr, tree closure, source_location location) ...@@ -3114,6 +3131,8 @@ Gogo::make_trampoline(tree fnaddr, tree closure, source_location location)
ptr_type_node, ptr_type_node,
fold_convert_loc(location, ptr_type_node, fold_convert_loc(location, ptr_type_node,
closure)); closure));
if (x == error_mark_node)
return error_mark_node;
x = save_expr(x); x = save_expr(x);
......
...@@ -4216,6 +4216,8 @@ Select_clauses::get_tree(Translate_context* context, ...@@ -4216,6 +4216,8 @@ Select_clauses::get_tree(Translate_context* context,
chans_arg, chans_arg,
pointer_boolean_type_tree, pointer_boolean_type_tree,
is_sends_arg); is_sends_arg);
if (call == error_mark_node)
return error_mark_node;
tree stmt_list = NULL_TREE; tree stmt_list = NULL_TREE;
......
...@@ -5094,6 +5094,8 @@ Map_type::do_make_expression_tree(Translate_context* context, ...@@ -5094,6 +5094,8 @@ Map_type::do_make_expression_tree(Translate_context* context,
context->gogo()->map_descriptor(this), context->gogo()->map_descriptor(this),
sizetype, sizetype,
expr_tree); expr_tree);
if (ret == error_mark_node)
return error_mark_node;
// This can panic if the capacity is out of range. // This can panic if the capacity is out of range.
TREE_NOTHROW(new_map_fndecl) = 0; TREE_NOTHROW(new_map_fndecl) = 0;
...@@ -5344,6 +5346,8 @@ Channel_type::do_make_expression_tree(Translate_context* context, ...@@ -5344,6 +5346,8 @@ Channel_type::do_make_expression_tree(Translate_context* context,
element_size_tree, element_size_tree,
sizetype, sizetype,
expr_tree); expr_tree);
if (ret == error_mark_node)
return error_mark_node;
// This can panic if the capacity is out of range. // This can panic if the capacity is out of range.
TREE_NOTHROW(new_channel_fndecl) = 0; TREE_NOTHROW(new_channel_fndecl) = 0;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment